Page 1 of 3

Smooth FPS camera

Posted: Mon Apr 19, 2004 2:19 pm
by warui
Hi!

As we all know rotation in Irrlichts default cameras is really jerky. There are two reasons for that:
1) small mouse position changes are not regonized
2) rotation angle may differ between frames because of aproximation (ex: if you move your mouse with a speed of 3.5 pixels per frame in one frame it will be treated as you had moved 3 pixel and in next frame as 4 pixels)

Ad.1
Quite easy to fix. Just change this lines in
CCameraFPSSceneNode::animate() (CCameraFPSSceneNode.cpp)

Code: Select all

if (cursorpos.X < 0.49f || cursorpos.X > 0.51f ||
    cursorpos.Y < 0.49f || cursorpos.Y > 0.51f)
to

Code: Select all

if (cursorpos.X < 0.5f || cursorpos.X > 0.5f ||
    cursorpos.Y < 0.5f || cursorpos.Y > 0.5f)
Ad.2
The way to solve this is taking average mouse posiotion change of last 3 frames instead of only last one.

First we have to add to tables to hold last two mouse positions and a variable to checkif it is the first time we make rotation. Just put this into CCameraFPSSceneNode definition (CCameraFPSSceneNode.h)

Code: Select all

f32 rotX[3];
f32 rotY[3];
bool firstRot;
Then in CCameraFPSSceneNode::animate() (CCameraFPSSceneNode.cpp) change the following:

Code: Select all

	// Update rotation

	Target.set(0,0,1);

	if (!CursorControl)
		return;

	RelativeRotation.X *= -1.0f;
	RelativeRotation.Y *= -1.0f;

	if (InputReceiverEnabled)
	{
		core::position2d<f32> cursorpos = CursorControl->getRelativePosition();
		
		if(firstRot) // it checks if it is the first time camera rotates and than fill tables with proper values
		{
      rotX[0] = rotX[1] = 0.5f - cursorpos.X;
      rotY[0] = rotY[1] = 0.5f - cursorpos.Y;
      firstRot=false;
		}
		
		rotX[2] = 0.5f - cursorpos.X; // puts values from this frame
		rotY[2] = 0.5f - cursorpos.Y;// into table

		if (cursorpos.X < 0.5 || cursorpos.X > 0.5 ||
			cursorpos.Y < 0.5 || cursorpos.Y > 0.5 )
		{
			RelativeRotation.Y += (rotX[0]+rotX[1]+rotX[2])/3 * RotateSpeed; // here we use the average value i mentioned before
			RelativeRotation.X += (rotY[0]+rotY[1]+rotY[2])/3 * RotateSpeed; // and here too ;)
			CursorControl->setPosition(0.5f, 0.5f);

			if (RelativeRotation.X > 89.0f) RelativeRotation.X = 89.0f;
			if (RelativeRotation.X < -89.0f) RelativeRotation.X = -89.0f;
		}
		
		rotX[0] = rotX[1]; // finaly we move values to make room for a new ones
		rotX[1] = rotX[2];
		
		rotY[0] = rotY[1];
		rotY[1] = rotY[2];
	}

	// set target
Now compile and enjoy smooth rotation :) It's still not perfect but works well most of the time.

If you find some bugs or have some improvements i'll be glad to read them.

To Nico: How about adding it to SDK ? And another thing. Why default value for FOV is set to 45 degrees ? With it camera works like in alien mode form AvP ;) Set it to 90 or something. I know it's easy to change via FOV(), but some newbies might have problems with "what's wrong with the camer" while watching techdemo or examples.

Posted: Thu May 27, 2004 7:18 pm
by afecelis
thnx for that code warui! I tried it and indeed it makes the camera much smoother!!

sweet!

I merged it into my Irrlich source and made it my standard!!

great!! i

I'm using it here:
http://irrlicht.sourceforge.net/phpBB2/ ... php?t=2538

Posted: Fri May 28, 2004 9:49 am
by warui
I'm glad someone found it useful.

Posted: Fri May 28, 2004 1:16 pm
by afecelis
more than useful, it's kick ass!

thnx thnx thnx

Posted: Fri Jul 02, 2004 6:00 pm
by VeneX
hmm, camera already works good i think so

Posted: Fri Jul 02, 2004 6:10 pm
by bal
VeneX wrote:hmm, camera already works good i think so
Nah, just tested with the 2 different dll's. The original one doesn't react when I move my mouse a little bit. The second (with this code) does.
But I have another problem with the FPS-cam. I changed the FOV-value to 90 like some ppl told me. The strange effect is gone but now the camera is like "zoomed in".

Screens do tell 1000 words :P:

FOV45 (good view but moving mouse up/down doesn't seem to be correct)
Image

FOV90 (correct up/down moving but view is weird, it's like they pushed on top and bottom)
Image

Pictures are made on exactly the same position.

Posted: Tue Jul 13, 2004 4:17 am
by Darklance
That certainly sounds useful....can you provide a compiled dll/lib of this fix? I'm not sure how to compile them myself.

Posted: Tue Jul 13, 2004 4:25 am
by thesmileman
bal, I could be wrong but the second image looks exactly like I would expect after lowering your field of view.

Posted: Tue Jul 13, 2004 8:01 am
by Rocketeer
thesmileman wrote:bal, I could be wrong but the second image looks exactly like I would expect after lowering your field of view.
Now I'm confused... hasn't he just increased the FOV from 45 to 90?

Posted: Tue Jul 13, 2004 11:17 am
by bal
thesmileman wrote:bal, I could be wrong but the second image looks exactly like I would expect after lowering your field of view.
It looks good, but just test it yourself. If you move the mouse you'll feel that it is like you zoomed in.

Posted: Tue Jul 13, 2004 5:51 pm
by thesmileman
I tested it in a couple of my applications and while it does feel somewhat as though it is zoomed in I would expect that to be the case when you cange the field of view a considerable amount. have you tried a number for FOV in the middle of the two?

Posted: Tue Jul 13, 2004 5:53 pm
by thesmileman
I tested it in a couple of my applications and while it does feel somewhat as though it is zoomed in I would expect that to be the case when you cange the field of view a considerable amount. have you tried a number for FOV in the middle of the two?

Posted: Tue Jul 13, 2004 6:10 pm
by bal
Yes. 60 and 80 made the view completely f*cked up.

But how do the engines of real FPS-games handle this?

Posted: Wed Jul 14, 2004 10:20 am
by Captain_Kill
I'm suprised people haven't noticed this Irrlicht 'difference'... Specifying degrees like 90 or 80 is wrong :shock: If you check the docs for setFOV you'll see that you actually use fractions, eg. 1.4 is around normal for an FPS view. Yes it is weird and it did take me a while to figure out but I'm positive that's how Irrlicht handles FOV

Posted: Wed Jul 14, 2004 11:00 am
by bal
Omg, thx a lot Captain_Kill :D