Jump to content
  • Advertisement
Sign in to follow this  
iop

3d camera rotation

This topic is 3614 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Hello, First of all I'm working with DirectX9 and have implemented buffered input. In fact my problem is only a programming one ( I think so :-) )but the whole thing has to do with graphics, so I post my question here. I want to rotate my camera around my "lookAt" point while I'm holding down the middle mouse button. So I use the "D3DXMatrixLookAtLH(...)" funcion. After that I rotate around the y-axis (by using the new mouse coordinates as the angle) and set then the viewMatrix. Until this point everything works correct, but I have a fault somewhere because of this phenomenon: I release the mouse button after moving my camera and move the mouse afterwards to another position. When I push and hold the mouse button again, the camera jumps to another position (probably rotated around the new mouse position as a new angle). From here on I can move the camera around normaly. How can I fix the "jump" of the camera? I thought about it very long but I don't get it to run as I want to... your my last hope :-)

Share this post


Link to post
Share on other sites
Advertisement
Do you have a code snippet we could look at that you think might be causing the problem?

To me it sounds like you have a variable or something that gets reset and when it does the camera pops to this default position.

Share this post


Link to post
Share on other sites
Hmm can't you set the mouse cursor to the center of the viewport when the middle mouse is pressed for the first time?Then when the mouse moves you will get the distance to the center and use those differences to rotate the camera.
And set the cursor to the center again.
I do it this way and I don't get any popping.

if(middleMouseDown && middleMouseFirstPress){
setCursorToCenter();
middleMouseFirstPress = false;
}

if(middleMouseDown){
POINT difference = getCursorPos() - center;
rotateCamera(difference.x,difference.y);
setCursorToCenter();
}

//somewhere in the input code
if(middleMouseUp)
middleMouseFirstPress = true;

Share this post


Link to post
Share on other sites
Ok, so here is my code:


//input.cpp
void Cinput::detect_mousepos(HWND hWnd)
{

//...
case DIMOFS_BUTTON2:
if(od.dwData & 0x80)
{
mbmiddledown = true;
}
else
{
mbmiddledown = false;
}
break;
//...
if(mbmiddledown)
rangeX = CMainApp.getMouseCoordsInputX();
else
//nothing
//...
}



//mainApp.cpp
void MainApplication::mainAppRender(HWND hWnd)
{
//begin scene, drawing my world...

//setting up the camera
D3DXMatrixLookAtLH(&ViewMatrix,
&D3DXVECTOR3 (vCamPos.x, vCamPos.y, vCamPos.z),// the camera position
&D3DXVECTOR3 (vLookAt.x, vLookAt.y, vLookAt.z),// the look-at position
&D3DXVECTOR3 (0.0f, 1.0f,0.0f));// the up direction

D3DXMatrixRotationY(&matRotateY, D3DXToRadian(input.rangeX));
D3DXMatrixMultiply(&ViewMatrix, &matRotateY, &ViewMatrix);
pd3ddev->SetTransform(D3DTS_VIEW, &ViewMatrix);

//... end scene
}


..hope, this helps to get a better overview.

Thank you!

Share this post


Link to post
Share on other sites
Black Knights method should work I think. His method might be better than the following because his doesn't have the cursor all over the screen in the background.

@Black Knight: I think you need to add together the difference to the previous movement otherwise it will keep getting reset and re-rotating.

You also could store the position of the mouse when the button is released and then the next time it's pressed reset the mouse position to that spot.

if (middleMouseDown)
{
if (storedCoordinates != EMPTY) //Not real code :p
{
mouseCoordinates = storedCoordinates;
storedCoordinates = EMPTY;
}

//do normal actions
}
else if (middleMouseUp && storedCoordinates == EMPTY)
{
storedCoordinates = mouseCoordinates;
}

Share this post


Link to post
Share on other sites
Quote:
Original post by Black Knight
Hmm can't you set the mouse cursor to the center of the viewport when the middle mouse is pressed for the first time?Then when the mouse moves you will get the distance to the center and use those differences to rotate the camera.
And set the cursor to the center again.
I do it this way and I don't get any popping.


Yes, its right but insead of the camera the mouse cursor jumps, or am I wrong with that? For example, you have clicked and released the mouse button and moved the cursor afterwards to the right side of your screen, then your method would let jump the curosr back to the middle, right?

I would like to rotate from that point on where the mouse is without any jumps.

Share this post


Link to post
Share on other sites
First of all I want to thank you for supporting me!

But my problem still exists. I tried what you said but my code doesn't do what I want.

Could you please look again over it? Here is an actualized version:


//input.cpp

//somewhere in the detect_mouse() function

case DIMOFS_BUTTON2:
if(od.dwData & 0x80)
mbmiddledown = true;
else
mbmiddledown = false;
break;

//....

if(mbmiddledown && middleMouseFirstPress)
{
CMainApp.setMouseCoordX(CMainApp.getViewport().Width / 2);
middleMouseFirstPress = false;
}
if(mbmiddledown)
{
rangeX = CMainApp.getMouseCoordsInputX() - CMainApp.getViewport().Width/2;
CMainApp.setViewMat();
CMainApp.setMouseCoordX(CMainApp.getViewport().Width / 2);
}
else
middleMouseFirstPress = true;
//...


//rotate function
void MainApplication::setViewMat()
{
D3DXMATRIX matView, matRotateY;

pd3ddev->GetTransform(D3DTS_VIEW, &matView);
D3DXMatrixRotationY(&matRotateY, D3DXToRadian(input.rangeX));
D3DXMatrixMultiply(&matView, &matRotateY, &matView);
pd3ddev->SetTransform(D3DTS_VIEW, &matView);
}



So thats it. Have you possibly another hint for me?

Thanks in advance!

Share this post


Link to post
Share on other sites
Yeah, I got it!

Here's the code, perhaps someone else need it too...


case DIMOFS_BUTTON2:
if(od.dwData & 0x80)
{
mbmiddledown = true;
middleMouseFirstPress = true;
}
else
mbmiddledown = false;
break;

//...

if(mbmiddledown && middleMouseFirstPress)
{
help = CMainApp.getMouseCoordsInputX();
middleMouseFirstPress = false;
}
if(mbmiddledown)
{
if(CMainApp.getMouseCoordsInputX() - help != 0)
rangeX+= ((CMainApp.getMouseCoordsInputX()) - help) * ROTATEMOUSESPEED;
}




Thank you again for helping me! I think the "middleMouseFirstPress" was the right food for thought what guided me to the right direction... thanks very much! :-)

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

Participate in the game development conversation and more when you create an account on GameDev.net!

Sign me up!