3D grid from different camera angles and only 4 directions of movement

Started by
4 comments, last by Spa8nky 14 years ago
If I'm looking at 3D grid but I can only move a cursor using 4 keys then one dimension will have to be ignorned. If the camera forward vector is (0,0,1) then: Left Arrow key moves (-1, 0, 0) Right Arrow key moves (1, 0, 0) Up Arrow key moves (0, 1, 0) Down Arrow key moves (0, -1, 0) I understand that I can get the direction of movement using cross products and the camera's forward vector:

            Vector3 up = Vector3.Cross(Vector3.UnitY, camera.Forward);

            if (up.LengthSquared() < Math_Util.EPSILON)
            {
                up = Vector3.Cross(-Vector3.UnitZ, camera.Forward);
            }

            up.Normalize();

            Vector3 right = Vector3.Cross(up, camera.Forward);
            right.Normalize();



How do I then make sure the direction is axis aligned? Should I take the maximum value of x, y and z for the up and right vector and use that as the axis. In other words, if x is max then the direction is (1,0,0). How would you guys suggest tackling this?
Advertisement
Im confused by what your aiming to achieve using the corss product, from my understanding of your problem you want to view a grid from 4 different sides and still want to move around in the same way using WASD, like you would in say roller coaster tycoon, the sims and that kind of stuff.

Or you want a camera like you would have in say an fps, were the camera moves forward/backward when you press W/S and A/D makes the camera moves sideways regardles of the cameras orienatation?
Apologies for the confusion, hopefully this might be a little clearer.

The camera already moves left, right, up, down correctly and isn't a problem.

The problem I am having is that I would like to traverse a 3D grid but I only have the 4 arrow keys to do this.

Based on the camera's view direction I would like move "up", "down", "left" and "right" using the arrow keys. However, "up", "down", "left" and "right" will change based on the camera's view direction.

For example:

If I view a 2D grid from one side (camera.Forward), the left key would move (-1,0,0) or "left" from the camera's viewpoint. If the camera now looks at the 2D grid from the opposite side (-camera.Forward) the left key would still move (-1,0,0) but the direction would be "right" from the camera's viewpoint.

I would like to have the left arrow always move the grid node cursor "left" no matter what the camera forward is, the same goes for the other 3 keys.

The problem is, the movement must always be axis aligned.

All this can be ignored, if you or anybody knows of a much easier way to traverse a 3D grid using 4 arrows keys. I'm just going with what I thought would work best, which probably isn't the best way. :)
I think I've cracked it.

Let's take "left" and "right" movement in the 3D array:

- Grab the camera's right axis
- Find out which is the largest of the 3 component absolute values
- If the largest component is negative, negate the direction of array traversal

            int xIndex = Math_Util.Max3Index(Math.Abs(camera.Right.X), Math.Abs(camera.Right.Y), Math.Abs(camera.Right.Z));            if (InputState.Global.IsKeyHit(PlayerIndex.One, Keys.Left))            {                switch (xIndex)                {                    case 0:                        {                            x += camera.Right.X < 0 ? 1 : -1;                            break;                        }                    case 1:                        {                            y += camera.Right.Y < 0 ? 1 : -1;                            break;                        }                    case 2:                        {                            z += camera.Right.Z < 0 ? 1 : -1;                            break;                        }                }            }            else if (InputState.Global.IsKeyHit(PlayerIndex.One, Keys.Right))            {                switch (xIndex)                {                    case 0:                        {                            x += camera.Right.X < 0 ? -1 : 1;                            break;                        }                    case 1:                        {                            y += camera.Right.Y < 0 ? -1 : 1;                            break;                        }                    case 2:                        {                            z += camera.Right.Z < 0 ? -1 : 1;                            break;                        }                }            }


It seems to work just fine, but if anyone has any problems with this method or anything they would like to add, now's the time to shout!
If if i understand correctly you want the camera to be free rotating, but movement constrained to the world axii?

//psuedoif(VK_LEFT) camera.translate(Vector(-1.0f,0.0f,0.0f), false)if(VK_UP)   camera.translate(Vector(0.0f,0.0f,1.0f), false)camera::translate(vector tvect, bool local) {   switch(local) {   case true:      camera.position += camera.forward * tvect.z;      camera.position += camera.up * tvect.y;      camera.position += camera.right * tvect.x;      break;   case false:      camera.position += tvect;   }}



edit: After rereading OP's question it seems that the camera is not what should move, but the grid? ( or the selected quad from the grid) if so then why is the camera involved at all... x is x, y is y...

Quote:Original post by Burnt_Fyr
edit: After rereading OP's question it seems that the camera is not what should move, but the grid? ( or the selected quad from the grid) if so then why is the camera involved at all... x is x, y is y...


The cursor that highlights the selected cube/quads is what is moving. The camera will move around the level and face different directions, therefore x still be x but left is no longer left.

This topic is closed to new replies.

Advertisement