I need to write a function performing linear interpolating between two Euler angles in 2D, perfectly without the use of quaternions as conversion seems to be an overkill for such a simple task.
Here's what I came up with:
// Calculate difference on a wrapped number line
function difference(a, b, width) {
const d = a - b;
const ad0 = Math.abs(d);
const ad1 = width - ad0;
if (ad1 < ad0)
return -Math.sign(d) * ad1;
return d;
}
Number.prototype.mod = function(n) {
return ((this % n) + n) % n;
};
const fullAngle = 2 * Math.PI;
// Linear interpolation
function slerp(a, b, t) {
a = a.mod(fullAngle);
b = b.mod(fullAngle);
return (a + difference(b, a, fullAngle) * t).mod(fullAngle);
}
function toRadians(a) {
return a * Math.PI / 180.0;
}
function toDegrees(a) {
return a * 180.0 / Math.PI;
}
document.write(toDegrees(slerp(toRadians(20), toRadians(350), .25)));
The expected output is an angle linearly interpolated from one angle to another using specified t
value.
In the example above the output is correct: The smallest angle difference between 350° and 20° is 30° (-30° with a sign).
20° + (-30°) * .25 = 20° - 7.5° = 12.5°
Is the code above correct? Could it be simplified?
12.499999999999984
)? \$\endgroup\$