📄 jvoiphrtflocalisation.cpp
字号:
{ int val; val = ((int)(samplebuf[i]*leftamp))+32767; if (val > 65535) val = 65535; else if (val < 0) val = 0; newdata[j] = (unsigned char)((val>>8)&0xFF); newdata[j+1] = (unsigned char)(val&0xFF); val = ((int)(samplebuf2[i]*rightamp))+32767; if (val > 65535) val = 65535; else if (val < 0) val = 0; newdata[j+2] = (unsigned char)((val>>8)&0xFF); newdata[j+3] = (unsigned char)(val&0xFF); } } vb->SetSamples(newdata,newdatalen); vb->SetNumSamples(newnumsamples); vb->SetStereo(true); vb->SetSampleRate(JVOIPHRTFLOCALISATION_SAMPLERATE); vb->SetBytesPerSample(bytespersample); delete [] samplebuf; delete [] samplebuf2; return 0;}bool JVOIPHRTFLocalisation::SupportsOutputSamplingRate(int orate){ if (!init) return false; if (orate != JVOIPHRTFLOCALISATION_SAMPLERATE) return false; return true;}int JVOIPHRTFLocalisation::SetOutputSamplingRate(int orate){ if (!init) return ERR_JVOIPLIB_GENERAL_COMPONENTNOTINIT; if (orate != JVOIPHRTFLOCALISATION_SAMPLERATE) return ERR_JVOIPLIB_HRTFLOC_UNSUPPORTEDSAMPLERATE; return 0;}bool JVOIPHRTFLocalisation::SupportsOutputBytesPerSample(int outputbytespersample){ if (!init) return false; return true;}int JVOIPHRTFLocalisation::SetOutputBytesPerSample(int outputbytespersample){ if (!init) return ERR_JVOIPLIB_GENERAL_COMPONENTNOTINIT; bytespersample = outputbytespersample; return 0;}int JVOIPHRTFLocalisation::GetComponentState(JVOIPComponentState **compstate){ // NOTE: nothing to do... *compstate = NULL; return 0;}int JVOIPHRTFLocalisation::SetComponentState(JVOIPComponentState *compstate){ // NOTE: nothing to do... return 0;}std::string JVOIPHRTFLocalisation::GetComponentName(){ return std::string("JVOIPHRTFLocalisation");}std::string JVOIPHRTFLocalisation::GetComponentDescription(){ return std::string("JVOIPLIB Internal basic localisation module");}std::vector<JVOIPCompParamInfo> *JVOIPHRTFLocalisation::GetComponentParameters() throw (JVOIPException){ return NULL;}void JVOIPHRTFLocalisation::CalculateDistances(){ double pos[3]; double diff; int i; // calculate the right ear distance to the sound source for (i = 0 ; i < 3 ; i++) pos[i] = localpos[i]+righteardir[i]*JVOIPHRTFLOCALISATION_HEADRADIUS; righteardist = 0; for (i = 0 ; i < 3 ; i++) { diff = pos[i]-remotepos[i]; righteardist += diff*diff; } righteardist = sqrt(righteardist); if (righteardist < JVOIPHRTFLOCALISATION_HEADRADIUS) righteardist = JVOIPHRTFLOCALISATION_HEADRADIUS; // calculate the left ear distance to the sound source for (i = 0 ; i < 3 ; i++) pos[i] = localpos[i]-righteardir[i]*JVOIPHRTFLOCALISATION_HEADRADIUS; lefteardist = 0; for (i = 0 ; i < 3 ; i++) { diff = pos[i]-remotepos[i]; lefteardist += diff*diff; } lefteardist = sqrt(lefteardist); if (lefteardist < JVOIPHRTFLOCALISATION_HEADRADIUS) lefteardist = JVOIPHRTFLOCALISATION_HEADRADIUS;}int JVOIPHRTFLocalisation::AllocateNewBuffer(){ double rateratio; rateratio = ((double)JVOIPHRTFLOCALISATION_SAMPLERATE)/((double)vblock->GetSampleRate()); newnumsamples = (int)((((double)vblock->GetNumSamples())*rateratio)+0.5); newnumsamples += 128; // for the 'tail' of the convolution filter newdatalen = newnumsamples*2; // we'll be using stereo if (bytespersample != 1) newdatalen *= 2; newdata = new unsigned char[newdatalen]; if (newdata == NULL) return ERR_JVOIPLIB_GENERAL_OUTOFMEM; samplebuf = new float[newnumsamples]; if (samplebuf == NULL) { delete [] newdata; return ERR_JVOIPLIB_GENERAL_OUTOFMEM; } samplebuf2 = new float[newnumsamples]; if (samplebuf2 == NULL) { delete [] samplebuf; delete [] newdata; } return 0;}int JVOIPHRTFLocalisation::CreateConvolutionFilters(){ int elev,i,j,num; filterdata = new JVOIPHRTFLocalisation::ElevationData[14]; if (filterdata == NULL) return ERR_JVOIPLIB_GENERAL_OUTOFMEM; for (i = 0, elev = -40 ; elev <= 90 ; i++,elev += 10) { JVOIPHRTFLocalisation::AzimuthData *data; JVOIPHRTFLocalisation::OrigAzimuthData *origdata; num = elevationdata[i].numazimuths; filterdata[i].elevation = elev; filterdata[i].numazimuths = num; data = new JVOIPHRTFLocalisation::AzimuthData[num]; if (data == NULL) { delete [] filterdata; return ERR_JVOIPLIB_GENERAL_OUTOFMEM; } filterdata[i].azimuths = data; origdata = elevationdata[i].azimuthdata; for (j = 0 ; j < num ; j++) { data[j].azimuth = origdata[j].azimuth; data[j].numvalues = 128; data[j].leftvalues = new float[128]; if (data[j].leftvalues == NULL) { delete [] filterdata; return ERR_JVOIPLIB_GENERAL_OUTOFMEM; } data[j].rightvalues = new float[128]; if (data[j].rightvalues == NULL) { delete [] filterdata; return ERR_JVOIPLIB_GENERAL_OUTOFMEM; } int *src; float *dst; int k; src = origdata[j].leftresponse; dst = data[j].leftvalues; for (k = 0 ; k < 128 ; k++) { float v; v = (float)src[k]; v /= 32768.0; dst[k] = v; } src = origdata[j].rightresponse; dst = data[j].rightvalues; for (k = 0 ; k < 128 ; k++) { float v; v = (float)src[k]; v /= 32768.0; dst[k] = v; } } } return 0;}void JVOIPHRTFLocalisation::DestroyConvolutionFilters(){ delete [] filterdata;}#define TORAD(x) ((x)*3.1415926535897932384626433832795/180.0)#define FROMRAD(x) ((x)*180.0/3.1415926535897932384626433832795)double ArcCos(double x){ double angle; if (x > 0.999999) angle = 0.0; else if (x < -0.999999) angle = 180.0; else angle = FROMRAD(acos(x)); if (angle < 0.00001) angle = 0; return angle;}void JVOIPHRTFLocalisation::CalculateAzimuthAndElevation(){ double cosangle,prjlen; double angle,elev; double vect[3],vect2[3],remoteprj[3]; double length; // get vector to remote position, starting from local position vect[0] = remotepos[0]-localpos[0]; vect[1] = remotepos[1]-localpos[1]; vect[2] = remotepos[2]-localpos[2]; // get the vector length length = sqrt(vect[0]*vect[0]+vect[1]*vect[1]+vect[2]*vect[2]); // calculate the angle with the updir vector vect2[0] = vect[0]/length; vect2[1] = vect[1]/length; vect2[2] = vect[2]/length; cosangle = vect2[0]*updir[0]+vect2[1]*updir[1]+vect2[2]*updir[2]; angle = ArcCos(cosangle); elev = 90.0-angle; elevation = 10*((int)((elev/10.0)+0.5)); if (elevation < -40) elevation = -40; else if (elevation > 90) elevation = 90; // calculate the azimuth // first, we get the projection of the remote soundsource position into the // azimuth plane, which is formed by the righteardir and frontdir vectors prjlen = vect[0]*updir[0]+vect[1]*updir[1]+vect[2]*updir[2]; remoteprj[0] = vect[0]-prjlen*updir[0]; remoteprj[1] = vect[1]-prjlen*updir[1]; remoteprj[2] = vect[2]-prjlen*updir[2]; // now, we calculate the angle of this vector with the frontdir vector length = sqrt(remoteprj[0]*remoteprj[0]+remoteprj[1]*remoteprj[1]+remoteprj[2]*remoteprj[2]); vect2[0] = remoteprj[0]/length; vect2[1] = remoteprj[1]/length; vect2[2] = remoteprj[2]/length; cosangle = vect2[0]*frontdir[0]+vect2[1]*frontdir[1]+vect2[2]*frontdir[2]; angle = ArcCos(cosangle); azimuth = (int)angle; if (azimuth < 0) azimuth = 0; else if (azimuth > 180) azimuth = 180; // now, we check if its the azimuth at the right ear side or at the left ear side cosangle = vect2[0]*righteardir[0]+vect2[1]*righteardir[1]+vect2[2]*righteardir[2]; if (cosangle < 0) leftear = true; else leftear = false;}#endif // JVOIPDISABLE_LOCALISATION_HRTF
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -