Thursday, December 17, 2009

Irrlicht – my third person camera

Currently I work on my own RPG game and I hope after gaining enough experience with it I’ll try to make my own MMORPG. Am I humble enough?

There are many MMORPG games on the market and all of them can work as an inspiration. My first task was to make a third person camera or more precisely third person camera animator. You don’t need to make an animator to use this logic. Creating an animator leads to some complications that I won’t discuss here.

We will use the right mouse button to orbit around the object and the scroller to zoom in and out. You need to add something like this in your event receiver or in OnEvent function of the animator:

 case EMIE_RMOUSE_PRESSED_DOWN:
  MouseKeys[2] = true;

  break;
 case EMIE_RMOUSE_LEFT_UP:
  MouseKeys[2] = false;

  break;
 case EMIE_MOUSE_MOVED:
  MousePos = CursorControl->getRelativePosition();

  break;
 case EMIE_MOUSE_WHEEL:
  Zoom = Zoom + event.MouseInput.Wheel*ZoomSpeed;

  if (Zoom < TargetMinDistance)
   Zoom = TargetMinDistance;

  if (Zoom > TargetMaxDistance)
      Zoom = TargetMaxDistance;

Now, when we have the input data, we must implement the logic. You must add this in animateNode function of your animator, or in some update method if you don’t use an animator.

 core::vector3df target = targetNode->getPosition();

 f32 nRotX = RotX;
 f32 nRotY = RotY;

 if (isMouseKeyDown(2))
 {
  if (!Rotating)

  {
   RotateStart = MousePos;
   Rotating = true;

   nRotX = RotX;
   nRotY = RotY;
  }

  else
  {
   nRotX += (RotateStart.X - MousePos.X) * RotateSpeed;

   nRotY += (RotateStart.Y - MousePos.Y) * RotateSpeed;

  }
 }
 else if(Rotating)
 {

  RotX += (RotateStart.X - MousePos.X) * RotateSpeed;

  RotY += (RotateStart.Y - MousePos.Y) * RotateSpeed;

  nRotX = RotX;
  nRotY = RotY;
  Rotating = false;

 }

 target = targetNode->getPosition();

 Pos.X = Zoom + target.X;
 Pos.Y = Zoom + target.Y;

 Pos.Z = target.Z;

 Pos.rotateXYBy(nRotY, target);

 Pos.rotateXZBy(-nRotX, target);

 camera->setPosition(Pos);

 camera->setTarget(target); 

This is very basic functionality but you will grasp the logic. I’ve used the Maya animator the get the idea. My code have a nasty flip on the top and the bottom, you can fix it if you want with restricting the camera movement or changing the up vector. And don’t make the camera parent or child of the target.

No comments: