Sign in to follow this  
Kram

frames per sec. and the render speed

Recommended Posts

Hi everyone, I was just wondering about the rendering of a game that I am trying to slowly make. I have just learnt how to rotate a mesh that I created in Blender. when I rotate it, I just use a float variable that effects the rotation matrix on the Y axis, My problem comes from when I rotate it in small increments (float of something like 0.007f), i need to hit the right and left keys A LOT to fully rotate it (obviously), and if i increase the float to something like 0.05f. then the roation doesnt look smooth. The rotation "jerks" around the Y axis. I was wondering if anyone could help me out with making the rotation, smooth, but still not needing to press the right or left keys as much. (i.e. more sensitive to the key presses of the user). Hope this makes sense. Cheers, Mark

Share this post


Link to post
Share on other sites
You key presses need to indicate how fast it should rotate, not how much it should rotate per press. For this you need to work out how much the cube should rotate given the time the last frame was rendered.

Basically you want time-based animation and there will be quite a few articles on google about it.

Good luck.

Share this post


Link to post
Share on other sites
1. If you are rotating an object by 0.05 radian per frame, the rotation should be quite smooth.

2. Sounds like you are rotating your model by a specific amount in response to a single keypress event. What you need to do is start rotating when the key is pressed and stop rotating when released.

Share this post


Link to post
Share on other sites
I think a bit of a mixture of both your suggestions is what I need here, to rotate using time-based animation, while the key is pressed down.

I have been looking into it and have come across many questions which touch on more of the fundamentals behind the process.

I don't really know where to start, but here it goes.

I have read a few articles about the process behind time-based animation, and I need to understand the call to the Render() method which will render my mesh on the screen.

my main game loop so far looks like this:


while(msg.message != WM_QUIT)
{
if(::PeekMessage(&msg, 0, 0, 0, PM_REMOVE))
{
::TranslateMessage(&msg);
::DispatchMessage(&msg);
}
else
{
static DWORD StartTime = timeGetTime();
DWORD Elapsed = timeGetTime() - StartTime;

ptr_display(Elapsed);
}
}



ptr_display is a function pointer to the Display method which is like this:


bool Display(float timeDelta)
{
//only render if the device has been setup and is not null
if( p_d3dDevice == NULL )
return false;

//clear the back buffer and the
//clear the z-buffer to white
p_d3dDevice->Clear( 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER , D3DCOLOR_XRGB(255, 255, 255), 1.0f, 0 );

HRESULT beginHr = p_d3dDevice->BeginScene();

if( SUCCEEDED( beginHr ) )
{
if (g_pMaze)
{
g_pMaze->Render(timeDelta);
}
// End the scene
p_d3dDevice->EndScene();
}

p_d3dDevice->Present( NULL, NULL, NULL, NULL );

return true;
}



as you can see I give the render method of my maze the "timeDelta"...

but im not too sure what to do with it :)

When the user hits the "right" arrow key, this happens:


...
case VK_RIGHT:
//rotate maze along X axis
if (g_pMaze)
g_pMaze->DecreaseXTilt();

break;
...



...
void Maze::DecreaseXTilt()
{
m_xTilt -= 0.08f;
}

...



Then in the render method i do this:


...
D3DXMATRIX yRot;
D3DXMatrixRotationY(&yRot, m_xTilt);
D3DXMATRIX World = yRot;
mp_d3dDevice->SetTransform(D3DTS_WORLD, &World);
...



so you see I think im on the right track, but its still not what I think i need to do to make it really smooth. I believe that I need to calculate the rotation increments, based on time, but Im not sure exactly how to implement that...

Thanks if you can help! I really appreciate it

Share this post


Link to post
Share on other sites
Quote:

2. Sounds like you are rotating your model by a specific amount in response to a single keypress event. What you need to do is start rotating when the key is pressed and stop rotating when released.


Yep. You can simply have a global "flag" variable indicating whether there should be any movement at the time (1 for one direction, 0 for no movement, -1 for reverse), this variable will be set in a reaction on key down and key up events.
Then, in the render procedure, you'll need to count time between frames (dt) and then simply increment the absolute rotation of the mesh by chosen velocity * dt * direction flag (-1 or 0 or +1).

Rotation will be as smooth as your current FPS and the rotation speed can make ;)

Share this post


Link to post
Share on other sites
Quote:
Original post by Tom KQT
Yep. You can simply have a global "flag" variable indicating whether there should be any movement at the time (1 for one direction, 0 for no movement, -1 for reverse), this variable will be set in a reaction on key down and key up events.
Then, in the render procedure, you'll need to count time between frames (dt) and then simply increment the absolute rotation of the mesh by chosen velocity * dt * direction flag (-1 or 0 or +1).

Rotation will be as smooth as your current FPS and the rotation speed can make ;)


Ok, so I think I get ya

I have this setup now:


float yRotation = this->m_yRotationVelocity * timeDelta * this->m_yDir;
D3DXMatrixRotationY(&yRot, yRotation);
D3DXMATRIX World = yRot;
mp_d3dDevice->SetTransform(D3DTS_WORLD, &World);



where:
m_yRotationVelocity = 0.001f
timeDelta = timeGetTime() - g_startTime
and
m_yDir = -1, 0, or 1 based on key presses

so when I press the left or right buttons, it does actually rotate smoothly!

But, when I press the other key (going from left to right keys), it suddenly "jumps" from one spot in the rotation to another, and it looks wrong...

but im not sure why???

Share this post


Link to post
Share on other sites
You forgot about the INCREMENT part ;)

this->m_yRotationVelocity * timeDelta * this->m_yDir;

must be ADDED to the rotation, not assigned.

That means you'll have to change yRotation to global variable and modify it somehow like so:


m_yRotation += this->m_yRotationVelocity * timeDelta * this->m_yDir;
D3DXMatrixRotationY(&yRot, m_yRotation);
D3DXMATRIX World = yRot;
mp_d3dDevice->SetTransform(D3DTS_WORLD, &World);


Please notice that there is += and not =.

Share this post


Link to post
Share on other sites
Quote:
Original post by Tom KQT
You forgot about the INCREMENT part ;)

this->m_yRotationVelocity * timeDelta * this->m_yDir;

must be ADDED to the rotation, not assigned.

That means you'll have to change yRotation to global variable and modify it somehow like so:


m_yRotation += this->m_yRotationVelocity * timeDelta * this->m_yDir;
D3DXMatrixRotationY(&yRot, m_yRotation);
D3DXMATRIX World = yRot;
mp_d3dDevice->SetTransform(D3DTS_WORLD, &World);


Please notice that there is += and not =.


Oh ok, thanks.

But wont that just make the m_yRotation var forever increase? essentially rotating at a constantly faster rate?

Should I be setting it back to zero somewhere?

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this