If you have not read the previous article, you can move to see: iOS 3D Engine SceneKit Development (4) – Some questions about rotation (1)
We used cabasicanimation to simulate the sun-Earth-Moon celestial movement. The movement of the Moon around the sun and the moon around the earth can be seen as a circular movement around the other point. (Of course, there is elliptical motion, there is apogee, perigee, here we treat as a circular motion)
A point around another point for circular motion is not familiar. Yes, that's what we learned before, and we can do it with mathematical knowledge.
Relevant mathematical knowledge points: Any point a (x, y), around a coordinate point B (rx0,ry0) counterclockwise rotation a angle after the new coordinates set to C (x0, y0), there is a formula:
x0= (x - rx0)*cos(a) - (y - ry0)*sin(a) + rx0 ;y0= (x - rx0)*sin(a) + (y - ry0)*cos(a) + ry0 ;
OK, there are these mathematical basis, then we will do well, we let the Moon system around the sun to the effect of the mathematical method to achieve. The Sun (Sunnode) is the b point, the Moon System (Earthgroupnode) is a point, we add the lunar system to the sun:
[_sunNode addChildNode:_earthGroupNode];
So relative to a point, the coordinates of the B point is (0,0), and then we calculate the C point, so that the coordinates of the C point is re-assigned to Earthgroupnode position can be. The code is as follows:
//Custom Action floatTotalduration =10.0f;//10s around the earth one lap floatDuration = totalduration/ the;//Every duration second to execute onceScnaction *customaction = [scnaction customactionwithduration:duration actionblock:^ (SCNNode * _Nonnull node, CGFloat ElapsedTime) {if(elapsedtime==duration) {SCNVector3 position = node.position;floatrx0 =0;//Origin is 0 floatRy0 =0;floatAngle =1.0f/ the*M_PI;floatx = (position.x-rx0) *Cos(angle)-(POSITION.Z-RY0) *Sin(angle) + rx0;floatz = (position.x-rx0) *Sin(angle) + (POSITION.Z-RY0) *Cos(angle) + ry0; Node.position = Scnvector3make (x, NODE.POSITION.Y, z); } }]; Scnaction *repeataction = [Scnaction repeatactionforever:customaction]; [_earthgroupnode runaction:repeataction];
From the above can be seen we use the Scenekit API scnaction to loop calculation assignment, in fact, the main thing is actionblock inside the code, you can also completely use the thread sleep and nstimer to achieve.
Final results:
The problem arises: we can see the limitations of the mathematical method above, the value of the y-axis has not changed, because three celestial bodies are in the x-z plane, if they are not the same Y value, not in the x-z this plane. That is, a three-dimensional point around another three-dimensional point to do circular motion, how to achieve the mathematical method?
Demo code has been uploaded to GitHub
Https://github.com/pzhtpf/SceneKitRoationDemo
iOS 3D engine SceneKit Development (5)--Some questions about rotation (2)