Recently, I was creating a model of the solar system and used two different methods to position the planets and to draw their orbits. In both cases, I used a lookup table to determine - for any given day - the cumulative degrees travelled and the distance from the sun.
For the planets, I used linked objects. Object1, centered at the sun, is the rotator. Object2 is the planet. Object2 is linked to Object1. I use the lookup tables to rotate Object1 along the y-axis and to determine the z.distance of Object2 from Object1. Where the Object1 y-rotation is 0 and the Object2 z-distance is a negative value, Object2, is positioned straight ahead (North). Increasing Object1 y-rotation causes the Object2 to orbit the Sun in an anticlockwise direction. (This might have been a problem elsewhere, but was okay because the planets orbit in an anticlockwise direction.)
To draw the orbits, I created a series of lines using the following routine - which is fairly standard:
var positions = [];
for (var i = 0; i <= xxxmax; i++) {
r = Mod360(cumulativedegrees[i]+90)*DegRad;
d = radius*factor[i];
x = d*Math.cos(r);
z = d*Math.sin(r);
positions.push(x, 0, -z);
}
geometry = new THREE.BufferGeometry();
geometry.setAttribute('position',new THREE.BufferAttribute(new Float32Array(positions),3)
);
material = new THREE.LineBasicMaterial({color: 0xffffff});
mesh = new THREE.Line(geometry, material);
object.add(mesh);
In the above code Mod360() limits results to a range of 0 to 360 and DegRad converts degrees to radians.
However I discovered that the orbit did not match the path of Object2 until I made two changes. First, I had to add 90 degrees to the rotation - which indicates that the origin of rotation is to the Right (East). Second, if I used a negative number for distance (d), I had to make the x-position a negative number (last line in the loop). I instead opted to use a positive number for distance, which required me to make the z-position a negative number.
Thus, it appears that there are two different coordinate systems for positioning/rotating objects and for positioning lines and points. Is that correct or am I missing something? I searched and found several examples where this seems to have created unresolved problems but did not find a good explanation of these differences.
As a programmer, I am somewhat surprised that three.js does not have a “built-in” routine for drawing points and lines. The idea of pushing and popping values seems like something you would find in 8086 assembly language, not in high-level programs. Ideally, the routines would modify the inputs so that the coordinate systems match.
Or perhaps there is a better way to draw lines and points in three.js using an object-oriented method? (I did end up attaching the lines to an object, so they will behave like an object from now on.)
Sorry to be a bit long-winded, but I thought that the example of the program I am working on would help illustrate the difference.
ADDENDUM - 4/7/23
Since posting this, I have discovered that the “pushing and popping” and use of different coordinate systems are primarily for the benefit of the GPU - to increase execution speed. As someone who spent a good portion of my life working in assembly language, I wholeheartedly support this objective. Thus, this is an “inconvenience” that I am happy to live with - even if it means a little more work.