You need to enable JavaScript to run this app.
导航

【Java】降噪/去混响-V2

最近更新时间2023.03.16 11:40:12

首次发布时间2023.03.16 11:40:12

使用步骤

1. 创建handle

算法模型详见降噪/去混响/去啸叫介绍小节

samiCore = new SAMICore();
// 创建句柄
SAMICoreExecutorContextCreateParameter parameter = new SAMICoreExecutorContextCreateParameter();
parameter.sampleRate = sampleRate;
parameter.numChannel = numChannel;
parameter.maxBlockSize = max_block_size;
parameter.modelBuffer = FunctionHelper.readBinaryFile(modelFileName,context);
parameter.modelLen = parameter.modelBuffer.length;
int ret = samiCore.SAMICoreCreateHandleByIdentify(
        SAMICoreIdentify.SAMICoreIdentify_DENOISE_V2_SPEECH44k, parameter);
if (ret != SAMICoreCode.SAMI_OK) {
    System.out.println("Create DenoiseV2 handle failed, ret " + ret);
    return ret;
}else{
    createHandleDone = true;
}

parameter.maxBlockSize:表示每一次处理单个通道的最大sample数

2. 设置参数

参数介绍
SAMICorePropertyID_Denoise_V2_Rate降噪比率:可选范围 0.0 ~ 1.0,默认是1.0,降噪比例最大。

SAMICorePropertyID_Denoise_V2_Mode

多声道独立降噪。该模式会对每个声道单独进行降噪处理。(denoise_mode 为 1)
多声道混合后再降噪。该模式会先mix所有声道音频,进行降噪处理,再将降噪结果拷贝到所有声道。(denoise_mode 为 0)

float denoise_rate = 1.0f;
SAMICoreProperty samiCoreProperty = new SAMICoreProperty();
samiCoreProperty.id = SAMICorePropertyId.SAMICorePropertyID_Denoise_V2_Rate;
samiCoreProperty.type = SAMICoreDataType.SAMICoreDataType_Float;
samiCoreProperty.dataObjectArray = new Object[1];
samiCoreProperty.dataObjectArray[0] = denoise_rate;
samiCoreProperty.dataArrayLen = 1;
ret = samiCore.SAMICoreSetProperty(SAMICorePropertyId.SAMICorePropertyID_Denoise_V2,samiCoreProperty);
if (ret != SAMICoreCode.SAMI_OK) {
    System.out.println("SAMICoreSetProperty failed, ret " + ret);
    return ret;
}

float denoise_mode = 1.0f;
SAMICoreProperty samiCoreProperty_mode = new SAMICoreProperty();
samiCoreProperty_mode.id = SAMICorePropertyId.SAMICorePropertyID_Denoise_V2_Mode;
samiCoreProperty_mode.type = SAMICoreDataType.SAMICoreDataType_Float;
samiCoreProperty_mode.dataObjectArray = new Object[1];
samiCoreProperty_mode.dataObjectArray[0] = denoise_mode;
samiCoreProperty_mode.dataArrayLen = 1;
ret = samiCore.SAMICoreSetProperty(SAMICorePropertyId.SAMICorePropertyID_Denoise_V2,samiCoreProperty_mode);
if (ret != SAMICoreCode.SAMI_OK) {
    System.out.println("SAMICoreSetProperty failed, ret " + ret);
    return ret;
}

3. 初始化buffer

inBlock = new SAMICoreBlock();
outBlock = new SAMICoreBlock();

inBlock.dataType = SAMICoreDataType.SAMICoreDataType_AudioBuffer;
inAudioBuffer = new SAMICoreAudioBuffer();
inAudioBuffer.numberChannels = numChannel;
inAudioBuffer.numberSamples = max_block_size;
inAudioBuffer.data = new float[(int) inAudioBuffer.numberChannels][(int) inAudioBuffer.numberSamples];
inBlock.audioData = new SAMICoreAudioBuffer[1];
inBlock.audioData[0] = inAudioBuffer;

outBlock.dataType = SAMICoreDataType.SAMICoreDataType_AudioBuffer;
outAudioBuffer = new SAMICoreAudioBuffer();
outAudioBuffer.numberChannels = numChannel;
outAudioBuffer.numberSamples = max_block_size;
outAudioBuffer.data = new float[(int) outAudioBuffer.numberChannels][(int) outAudioBuffer.numberSamples];
outBlock.audioData = new SAMICoreAudioBuffer[1];
outBlock.audioData[0] = outAudioBuffer;

numberChannels : 需要跟创建handle设置的一致
numberSamples:每一个处理的实际帧数,要求 numberSamples<= parameter.maxBlockSize

4. 处理数据

for (int numSamples = 0; numSamples < totalNumSamples;) {
    //更新实际输入输出的帧数
    if((numSamples + inAudioBuffer.numberSamples) > totalNumSamples) {
        inAudioBuffer.numberSamples = totalNumSamples - numSamples;
        outAudioBuffer.numberSamples = totalNumSamples - numSamples;
    }
    
    //拷贝处理数据到要处理的buffer
    for (int i = 0; i < inAudioBuffer.numberChannels; i++) {
        for (int j = 0; j < inAudioBuffer.numberSamples; j++) {
            inAudioBuffer.data[i][j] = in_planar_float_data[i][numSamples + j];
        }
    }

    //调用处理函数
    int ret = samiCore.SAMICoreProcess(inBlock, outBlock);
    if (ret != SAMICoreCode.SAMI_OK) {
        System.out.println("DenoiseV2 process audio data failed, ret " + ret);
        return ret;
    }

    //从outAudioBuffer获取处理后的数据
    for (int i = 0; i < inAudioBuffer.numberChannels; i++) {
        for (int j = 0; j < inAudioBuffer.numberSamples; j++) {
            out_planar_float_data[i][j+numSamples] = outAudioBuffer.data[i][j];
        }
    }
    numSamples = numSamples + inAudioBuffer.numberSamples;
}

注意检查 SAMICoreProcess 函数的返回值,处理输入不正确或者内部处理错误都会有返回值,错误码可以查看错误检查一节

5. 释放handle

if (createHandleDone){
    samiCore.SAMICoreDestroyHandle();
}