41 minutes ago, the incredible smoker said:
Your code has many maths, trig functions, also division.
I see things like acos, sin cos,
The trig is to convert to spherical coords so i can apply the angle limits. But it would better to store 4 planes instead angles and to project the target vector to those planes if it is in the wrong half space, like so:
if (1) // angle limits, but using planes to avoid trig
{
vec dir = turret.mountOrientation.Unrotate(targetDir); // move to local mount space
float distanceToPlane = turret.planeLimitLeft.Dot(dir); // actually we do not need a plane but just a unit legnth direction, because the planes lie at the origin of mount space (i assume the mount space origin to be the center of rotation)
if (distanceToPlane > 0) // wrong half space?
{
dir -= dir * distanceToPlane; // now dir is projected to the limit plane to prevent the turret from rotating out of limits
}
// do the same with the 3 other planes, normalize dir but care for the case it has zero length
targetDir = turret.mountOrientation.Rotate(dir); // back to global space
}
Notice you get the distance to the plane using the dot product, this is the most important thing to understand the dot product. Extending this thought, you can understand geometrically how a 3x3 matrix times 3D vector multiplication rotates the vector, as it uses 3 dot products to find the distances along 3 basis vectors and their planes to calculate the transformed (rotated) resulting vector.
Understanding that, you can also understand 3x3 matrix multiplication, which is just rotating the 3 basis vectors of one matrix to the other. So this is how matrix rotations works.
I mention this because i guess you're not there yet and i remember how much it helped me figuring this out. The same works in 2D.
The final acos is used to determinate an angle, because the OP requested rotating at max angular speed. Without this requirement, we could get rid of this as well. To prevent the turret from snapping to the target in an instant, we could just use simple interpolation with previous state:
vec newTurretDir = prevTurretDir * 0.98 + targetDir * 0.02; // behaviour depends on rate of updates!
Then construct the orientation from newDir (as we did in your last topic) with an additional up vector.
... but notice an acos here and there will nor affect your performance. Also this is just gameplay logic, not engine code. Use a profiler to find your real bottlenecks ![;) ;)](https://uploads.gamedev.net/emoticons/wink.png)
1 hour ago, the incredible smoker said:
Why dont you take a position that follows the target position ?
You need to replace this line: static vec target (10, 3, 0); with your real target.
1 hour ago, the incredible smoker said:
And how do you handle without limits ?, is the turret very dumb ?
The most recent code contains limits (to restrict rotational freedom of the turret), earlier versions did not.
The turret is dump, it only rotates towards a given target at constant max speed. To handle moving targets, you would need to calculate a offset to the target, e.g. using Alvaros tutorial he has linked to.