📄 jsdirectionalsample.java
字号:
* * Find Factor * * *****************/ /* * Interpolates the correct attenuation scale factor given a 'distance' * value. This version used both front and back attenuation distance * and scale factor arrays (if non-null) in its calculation of the * the distance attenuation. * If the back attenuation arrays are null then this executes the * PointSoundRetained version of this method. * This method finds the intesection of the ray from the sound source * to the center-ear, with the ellipses defined by the two sets (front * and back) of distance attenuation arrays. * This method looks at pairs of intersection distance values to find * which pair the input distance argument is between: * [intersectionDistance[index] and intersectionDistance[index+1] * The index is used to get factorArray[index] and factorArray[index+1]. * Then the ratio of the 'distance' between this pair of intersection * values is used to scale the two found factorArray values proportionally. */ float findFactor(double distanceToHead, double[] maxDistanceArray, float[] maxFactorArray, double[] minDistanceArray, float[] minFactorArray) { int index, lowIndex, highIndex, indexMid; double returnValue; if (debugFlag) { debugPrint("JSDirectionalSample.findFactor entered:"); debugPrint(" distance to head = " + distanceToHead); } if (minDistanceArray == null || minFactorArray == null) { /* * Execute the PointSoundRetained version of this method. * Assume it will check for other error conditions. */ return ( this.findFactor(distanceToHead, maxDistanceArray, maxFactorArray) ); } /* * Error checking */ if (maxDistanceArray == null || maxFactorArray == null) { if (debugFlag) debugPrint(" findFactor: arrays null"); return -1.0f; } // Assuming length > 1 already tested in set attenuation arrays methods int arrayLength = maxDistanceArray.length; if (arrayLength < 2) { if (debugFlag) debugPrint(" findFactor: arrays length < 2"); return -1.0f; } int largestIndex = arrayLength - 1; /* * Calculate distanceGain scale factor */ /* * distanceToHead is larger than greatest distance in maxDistanceArray * so head is beyond the outer-most ellipse. */ if (distanceToHead >= maxDistanceArray[largestIndex]) { if (debugFlag) debugPrint(" findFactor: distance > " + maxDistanceArray[largestIndex]); if (debugFlag) debugPrint(" maxDistanceArray length = " + maxDistanceArray.length); if (debugFlag) debugPrint(" findFactor returns ****** " + maxFactorArray[largestIndex] + " ******"); return maxFactorArray[largestIndex]; } /* * distanceToHead is smaller than least distance in minDistanceArray * so head is inside the inner-most ellipse. */ if (distanceToHead <= minDistanceArray[0]) { if (debugFlag) debugPrint(" findFactor: distance < " + maxDistanceArray[0]); if (debugFlag) debugPrint(" findFactor returns ****** " + minFactorArray[0] + " ******"); return minFactorArray[0]; } /* * distanceToHead is between points within attenuation arrays. * Use binary halfing of distance attenuation arrays. */ { double[] distanceArray = new double[arrayLength]; float[] factorArray = new float[arrayLength]; boolean[] intersectionCalculated = new boolean[arrayLength]; // initialize intersection calculated array flags to false for (int i=0; i<arrayLength; i++) intersectionCalculated[i] = false; boolean intersectionOnEllipse = false; int factorIndex = -1; /* * Using binary halving to find the two index values in the * front and back distance arrays that the distanceToHead * parameter (from sound source position to head) fails between. * Changing the the current low and high index values * calculate the intesection of ellipses (defined by this * min/max distance values) with the ray (sound source to * head). Put the resulting value into the distanceArray. */ /* * initialize the lowIndex to first index of distance arrays. * initialize the highIndex to last index of distance arrays. */ lowIndex = 0; highIndex = largestIndex; if (debugFlag) debugPrint(" while loop to find index that's closest: "); while (lowIndex < (highIndex-1)) { if (debugFlag) debugPrint(" lowIndex " + lowIndex + ", highIndex " + highIndex); /* * Calculate the Intersection of Ellipses (defined by this * min/max values) with the ray from the sound source to the * head. Put the resulting value into the distanceArray. */ if (!intersectionCalculated[lowIndex]) { distanceArray[lowIndex] = this.intersectEllipse( maxDistanceArray[lowIndex], minDistanceArray[lowIndex]); // If return intersection distance is < 0 an error occurred. if (distanceArray[lowIndex] >= 0.0) intersectionCalculated[lowIndex] = true; else { /* * Error in ellipse intersection calculation. Use * average of max/min difference for intersection value. */ distanceArray[lowIndex] = (minDistanceArray[lowIndex] + maxDistanceArray[lowIndex])*0.5; if (internalErrors) debugPrint( "Internal Error in intersectEllipse; use " + distanceArray[lowIndex] + " for intersection value " ); // Rather than aborting, just use average and go on... intersectionCalculated[lowIndex] = true; } } // end of if intersection w/ lowIndex not already calculated if (!intersectionCalculated[highIndex]) { distanceArray[highIndex] = this.intersectEllipse( maxDistanceArray[highIndex],minDistanceArray[highIndex]); // If return intersection distance is < 0 an error occurred. if (distanceArray[highIndex] >= 0.0f) intersectionCalculated[highIndex] = true; else { /* * Error in ellipse intersection calculation. Use * average of max/min difference for intersection value. */ distanceArray[highIndex] = (minDistanceArray[highIndex]+ maxDistanceArray[highIndex])*0.5f; if (internalErrors) debugPrint( "Internal Error in intersectEllipse; use " + distanceArray[highIndex] + " for intersection value " ); // Rather than aborting, just use average and go on... intersectionCalculated[highIndex] = true; } } // end of if intersection w/ highIndex not already calculated /* * Test for intersection points being the same as head position * distanceArray[lowIndex] and distanceArray[highIndex], if so * return factor value directly from array */ if (distanceArray[lowIndex] >= distanceToHead) { if ((lowIndex != 0) && (distanceToHead < distanceArray[lowIndex])) { if (internalErrors) debugPrint( "Internal Error: binary halving in " + "findFactor failed; distance < low " + "index value"); } if (debugFlag) { debugPrint(" distanceArray[lowIndex] >= " + "distanceToHead" ); debugPrint( " factorIndex = " + lowIndex); } intersectionOnEllipse = true; factorIndex = lowIndex; break; } else if (distanceArray[highIndex] <= distanceToHead) { if ((highIndex != largestIndex) && (distanceToHead > distanceArray[highIndex])) { if (internalErrors) debugPrint( "Internal Error: binary halving in " + "findFactor failed; distance > high " + "index value"); } if (debugFlag) { debugPrint(" distanceArray[highIndex] >= " + "distanceToHead" ); debugPrint( " factorIndex = " + highIndex); } intersectionOnEllipse = true; factorIndex = highIndex; break; } if (distanceToHead > distanceArray[lowIndex] && distanceToHead < distanceArray[highIndex] ) { indexMid = lowIndex + ((highIndex - lowIndex) / 2); if (distanceToHead <= distanceArray[indexMid]) // value of distance in lower "half" of list highIndex = indexMid; else // value if distance in upper "half" of list lowIndex = indexMid; } } /* of while */ /* * First check to see if distanceToHead is beyond min or max * ellipses, or on an ellipse. * If so, factor is calculated using the distance Ratio * (distanceToHead - min) / (max-min) * where max = maxDistanceArray[factorIndex], and * min = minDistanceArray[factorIndex] */ if (intersectionOnEllipse && factorIndex >= 0) { if (debugFlag) { debugPrint( " ratio calculated using factorIndex " + factorIndex); debugPrint( " d.A. max pair for factorIndex " + maxDistanceArray[factorIndex] + ", " + maxFactorArray[factorIndex]); debugPrint( " d.A. min pair for lowIndex " +
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -