📄 iiii.c
字号:
if(k>(BotNumber-20))break;
Total[h]+=fft[k-2];
Total[h]+=fft[k-1];
Total[h]+=fft[k];
Total[h]+=fft[k+1];
Total[h]+=fft[k+2];
}
if(int_flag==1)SoundOut();
}
//和的最大值
MaxAdd=0;
h=0;
for(i=0;i<TotalNumber;i++)
{
if(MaxAdd<Total[i])
{
MaxAdd=Total[i];
h=i;
}
if(int_flag==1)SoundOut();
}
MaxAdd/=WMAXVAL;
SpeechVal=h+ComputerStart;
PitchSearchAll();
if(Old==1)
{ if((SpeechVal>SpeechValMin)&&(SpeechVal<SpeechValMax)&&
(MaxAdd>MaxNumber*sumX) &&(sumX>AmMin)&&(Maxfft>MicroMaxfft)&&(Averagefft>MicroAveragefft)
&&(AverageNumber>MicroAverageNumber)&&(fftNumber>MicrofftNumber)
&&(fftHNumber<1)) //第一种方式 */
{
PitchFlag=1;
}
else if((Min>=SpeechValMin)&&(Min<=SpeechValMax)&&
(MaxAdd>MaxNumber*sumX)&&(sumX>AmMin)&&(Maxfft>MicroMaxfft)
&&(Averagefft>MicroAveragefft)
&&(AverageNumber>MicroAverageNumber)&&(fftNumber>MicrofftNumber)
&&(fftHNumber<1)) //第二种方式 */
{
PitchFlag=1;
}
else
{
PitchFlag=0;
}
}
if(Old==0)
{//判断并设置亮灯标志
if((Maxfft>MicroMaxfft)&&(Averagefft>MicroAveragefft)
&&(AverageNumber>MicroAverageNumber)&&(PitchNew2==1) )
//&&(fftNumber>MicrofftNumber)
//&&(fftNumber<30)&&(fftHNumber<1)) //第一种方式
{
PitchFlag=1;
}
else if((Maxfft>MicroMaxfft)
&&(Averagefft>MicroAveragefft)
&&(AverageNumber>MicroAverageNumber)&&(PitchNew2==1) )
//&&(fftNumber>MicrofftNumber)
// &&(fftNumber<30)&&(fftHNumber<1)) //第二种方式
{
PitchFlag=1;
}
else
{
PitchFlag=0;
}
}
}
/*------------------------ 时域---频域转换 ------------------------*/
static void PitchCep(void)
{
int i;
int a;
//数据输入
for(i=0;i<WindowsLong;i++)
{
fft[i]=PitchDataIn[i];
if(int_flag==1)SoundOut();
}
for(i=0;i<WindowsLong;i++)
{
fftNew[i]=PitchDataVer[i];
if(int_flag==1)SoundOut();
}
/*
桢移
if(FilterTwo!=0)
{
for(i=0;i<WindowsLong;i++)
{
PitchDataIn[i]=PitchDataIn[i+WindowsLong/2];
if(int_flag==1)SoundOut();
}
}
if(FilterTwo!=0)
{
for(i=0;i<WindowsLong;i++)
{
PitchDataVer[i]=PitchDataVer[i+WindowsLong/2];
if(int_flag==1)SoundOut();
}
}
*/
//**************** KIll ******************************
IRQ_globalDisable();
rfft(fft,WindowsLong,SCALE); // 求傅立叶变换
IRQ_globalEnable();
//******************************************************
/*
IRQ_globalDisable();
rfft(fftNew,N,SCALE); // 求傅立叶变换
IRQ_globalEnable();
*/
for(i=0;i<WindowsLong;i++) // 求前X个FFT数据的绝对值
{
if(fft[i]<0)
fft[i]=-(fft[i]);
if(int_flag==1)SoundOut();
}
fft[0]=0;
for(i=0;i<WindowsLong;i++) // 求前X个FFT数据的绝对值
{
fft[i]=16*fft[i];
if(int_flag==1)SoundOut();
}
/*
for(i=0;i<WindowsLong;i++) // 求前X个FFT数据的绝对值
{
if(fftNew[i]<0)
fftNew[i]=-(fftNew[i]);
if(int_flag==1)SoundOut();
}
for(i=0;i<200;i++) // 求前X个FFT数据的绝对值差
{
fftError[i]=(fft[i]-fftNew[i]);
if(fftError[i]<0)
fftError[i]=(fftNew[i]-fft[i]);
if(int_flag==1)SoundOut();
}
for(i=200;i<WindowsLong;i++) // 求前X个FFT数据的绝对值
{
fftError[i]=0;
if(int_flag==1)SoundOut();
}
fftError[0]=0;
*/
/*
IRQ_globalDisable();
rifft(fftError,WindowsLong,SCALE); // 求傅立叶变换
IRQ_globalEnable();
fftError[0]=fftError[1];
a=SegNew*WindowsLong;
for(i=0;i<WindowsLong;i++)
{
MikeOut[a+i]=128*fftError[i];
} */
SegNew++;
if(SegNew>=32)
SegNew=0;
/*
for(i=0;i<WindowsLong;i++) //
{
fft[i]=20*fftError[i];
if(int_flag==1)SoundOut();
}
for(i=1;i<WindowsLong-1;i++) // 滤波
{
fftError[i]=0.25*fft[i-1]+0.5*fft[i]+0.25*fft[i+1];
if(int_flag==1)SoundOut();
}
for(i=1;i<WindowsLong;i++) // 求前X个FFT数据的绝对值
{
fft[i]=fftError[i]; //+0.5*fft[i]+0.25*fft[i+1];
if(int_flag==1)SoundOut();
}
*/
FftSubLong();
FftSubAverge();
//SearchPitchMax();
//PitchJudge();
/**************** KIll ******************************
IRQ_globalDisable();
rfft(fft,WindowsLong,SCALE); // 求傅立叶变换
IRQ_globalEnable();
*****************************************************/
}
void FftSubLong(void)
{
int i;float k;
TimeLong++;
if(TimeLong>=AdptiveLength)
TimeLong=AdptiveLength;
//转为浮点数
// IRQ_globalDisable();
q15tofl(&fft[FFTMIN],fftSource,FftLength);
// IRQ_globalEnable();
//保护数据
for(i=FFTMIN;i<FFTMAX;i++)
{
FftLong1[i-FFTMIN]=fftSource[i-FFTMIN];
}
//减区长期噪声数据
for(i=FFTMIN;i<FFTMAX;i++)
{
fftSource[i]-=FftLong[i-FFTMIN];
if(fftSource[i]<0)
fftSource[i]=0;
}
//修改长期噪声数据
k=(float)(TimeLong-1)/TimeLong;
for(i=FFTMIN;i<FFTMAX;i++)
{
FftLong[i-FFTMIN]=FftLong[i-FFTMIN]*k;
}
k=1-k;
for(i=FFTMIN;i<FFTMAX;i++)
{
FftLong1[i-FFTMIN]=FftLong1[i-FFTMIN]*k;
}
for(i=FFTMIN;i<FFTMAX;i++)
{
FftLong[i-FFTMIN]+=FftLong1[i-FFTMIN];
}
// IRQ_globalDisable();
fltoq15(fftSource,&fft[FFTMIN],FftLength);
// IRQ_globalEnable();
}
void FftSubAverge(void)
{
int i;
long unsigned int a=0;
for(i=FFTMIN;i<FFTMAX;i++)
{
a+=fft[i];
}
a/=(FFTMAX-FFTMIN);
for(i=FFTMIN;i<FFTMAX;i++)
{
fft[i]-=2*a;
if(fft[i]<0)
fft[i]=0;
}
}
void FftLongInit(void)
{
int i;
for(i=FFTMIN;i<FFTMAX;i++)
{
FftLong[i-FFTMIN]=0;
}
}
//////////////////////// 计算最接近的一个频率点数 //////////////////////////////////
// ApexMov[] 峰值时的位移
//
static void Near(void)
{
Uint16 i,m;
Uint16 X[5],X1;
Uint16 Y[5];
m=1;
for(i=0;i<5;i++)
{
X[i]=0;
Y[i]=0;
}
//如果第一个数小于16,从第二个数计算
if(ApexMov[0]<16)
{
m=2;
}
// 如果第一个有效数在15, 35之间
if((ApexMov[m-1]<=35)&&(ApexMov[m-1]>15))
{
i=m;
while(i<=3)
{
X[0]=X[0]+abs(ApexMov[i]-(i+1)*ApexMov[m-1]);
i++;
if(int_flag==1)SoundOut();
}
Y[0]=ApexMov[m-1];
i=m;
while(i<=3) //计算第一个值
{
X[1]=X[1]+abs(ApexMov[i]-(i+1)*(ApexMov[m-1]-1));
i++;
if(int_flag==1)SoundOut();
}
Y[1]=ApexMov[m-1]-1; // 基音峰
i=m;
while(i<=3)
{
X[2]=X[2]+abs(ApexMov[i]-(i+1)*(ApexMov[m-1]+1));
i++;
if(int_flag==1)SoundOut();
}
Y[2]=ApexMov[m-1]+1;
i=m;
while(i<=3)
{
X[3]=X[3]+abs(ApexMov[i]-(i+1)*(ApexMov[m-1]-2));
i++;
if(int_flag==1)SoundOut();
}
Y[3]=ApexMov[m-1]-2;
i=m;
while(i<=3)
{
X[4]=X[4]+abs(ApexMov[i]-(i+1)*(ApexMov[m-1]+2));
i++;
if(int_flag==1)SoundOut();
}
Y[4]=ApexMov[m-1]+2;
}
Min=0;
X1=512;
for(i=0;i<4;i++)
{
if(X[i]<X1) //取最小值
{
X1=X[i];
Min=Y[i];
}
}
if((X1>=MircoMin)||(ApexMov[1]==0)) //如果值超出范围为无效让Min=0
Min=0;
}
/**************************************************************
变量初始化 */
void bianliang_chushihua(void)
{
uint i;
ZhenYi_F=0;
PitchFlag=0;
for(i=0;i<LpcNumber;i++)
{
CEP[i]=0;
ALF[i]=0;
PRECEPD[i]=0;
}
for(i=0;i<WindowsLong;i++)
fft[i]=0;
for(i=0;i<WindowsLong;i++)
{
VoiceIn[i]=0;
VoicePreEmphasisOut[i]=0;
// CanCHa[i]=0;
if(int_flag==1)SoundOut();
}
}
/********************************************************************/
/*********************************************************************/
/* 基音周期检测并设置亮灯标志 */
// 将第一个位置的数值(及相邻的4个)加上
// 它的2倍位置的数值(及相邻的4个)
//
/**************************************************************/
static void Speech(void)
{
Uint16 i,j,k,h;
Uint16 Total[TotalNumber];
Uint16 MaxAdd;
Uint32 sum;
Uint16 sumX;
SpeechVal=0;
//清0
for(i=0;i<TotalNumber;i++)
{
Total[i]=0;
}
//18--128 平均值
sum=0;
for(i=ComputerStart;i<(ComputerStart+BotNumber);i++)
{
sum+=fft[i];
if(int_flag==1)SoundOut();
}
sumX=sum/BotNumber;
//从18开始,
for(j=ComputerStart;j<ComputerEnd;j++)
{
h=j-ComputerStart;
for(i=1;i<5;i++)
{
k=i*j;
if(k>(BotNumber-20))break;
Total[h]+=fft[k-2];
Total[h]+=fft[k-1];
Total[h]+=fft[k];
Total[h]+=fft[k+1];
Total[h]+=fft[k+2];
}
if(int_flag==1)SoundOut();
}
//和的最大值
MaxAdd=0;
h=0;
for(i=0;i<TotalNumber;i++)
{
if(MaxAdd<Total[i])
{
MaxAdd=Total[i];
h=i;
}
if(int_flag==1)SoundOut();
}
MaxAdd/=WMAXVAL;
SpeechVal=h+ComputerStart;
//判断并设置亮灯标志
if((SpeechVal>SpeechValMin)&&(SpeechVal<SpeechValMax)&&
(MaxAdd>MaxNumber*sumX) &&(sumX>AmMin)) //第一种方式
{
PitchFlag=1;
}
else if((Min>=SpeechValMin)&&(Min<=SpeechValMax)&&
(MaxAdd>MaxNumber*sumX)&&(sumX>AmMin)) //第二种方式
{
PitchFlag=1;
}
else
{
PitchFlag=0;
}
}
///////////////////////////////END////////////////////////////////////
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -