Control Of Bone

Started by
37 comments, last by VitaliBR 13 years, 3 months ago

Good job. It appears that the bone's local Y axis is pointing out of the screen - the rotation is clockwise with increasing angle.

For the model, what do you set for the world transform when you render it? The equations you're using assume the model is rendered with an identity world matrix. You need to use the same world matrix for D3DXVec3Project as you do when you render it, to ensure that the projected bone location is in screen space with the mouse location.

I.e., if you render the model something like:

dev->SetTransform(D3DTS_WORLD, &modelWorld);
// draw the model

then you need to use the same modelWorld in the D3DXVec3Project call:

D3DXVec3Project(&boneLocation,&boneLocation,&m_vp,&m_pm,&m_vm,&modelWorld);



[font="arial, sans-serif"]But not sure how I'm doing using the identity matrix?
[font="arial, sans-serif"]D3DXMATRIX ident;
D3DXMatrixIdentity(&ident);
D3DXMATRIX final = bone->TransformationMatrix*(*parentMatrix);
D3DXVECTOR3 boneLocation(final._41,final._42,final._43);
D3DXVec3Project(&boneLocation,&boneLocation,&m_vp,&m_pm,&m_vm,&ident); // use YOUR viewport, projection and view matrices in this call
D3DXVECTOR3 dir = mouseLocation - boneLocation;

http://mateusvitali.wordpress.com/
Advertisement
The last parameter in the D3DXVec3Project call should be the world matrix for the vector you want projected. If you render the mesh with a world matrix other than the identity matrix, substitute the mesh's world matrix as shown in my post.

Please don't PM me with questions. Post them in the forums for everyone's benefit, and I can embarrass myself publicly.

You don't forget how to play when you grow old; you grow old when you forget how to play.

[font="arial, sans-serif"]Ok, I did as you said, the arm responds to the mouse, but moves very little, not totally in sync with the cursor
D3DXMATRIX ident;
D3DXMATRIX modelWorld;
D3DXMatrixIdentity(&ident);
m_pDevice->SetTransform(D3DTS_WORLD, &modelWorld);
D3DXMATRIX final = bone->TransformationMatrix*(*parentMatrix);
D3DXVECTOR3 boneLocation(final._41,final._42,final._43);
D3DXVec3Project(&boneLocation,&boneLocation,&m_vp,&m_pm,&m_vm,&modelWorld); // use YOUR viewport, projection and view matrices in this call
D3DXVECTOR3 dir = mouseLocation - boneLocation;

float offset = D3DX_PI/2.0f;
float angle = offset - atan2(dir.y,dir.x); // change this when you rotate the model
D3DXMATRIX rot;
D3DXMatrixRotationY(&rot,angle);
bone->CombinedTransformationMatrix = rot*final;
http://mateusvitali.wordpress.com/
You need to really try to get a better understanding of what you're trying to do. In your code, you don't set the modelWorld matrix to a valid value. You should be using the same world transform that you use when you render the mesh.

Answer for yourself: what world transform is set when the mesh is rendered? For instance, if you're using a shader, what world transform is used by the shader when the mesh is rendered. Use that same transform in the D3DXVec3Project call.

Please don't PM me with questions. Post them in the forums for everyone's benefit, and I can embarrass myself publicly.

You don't forget how to play when you grow old; you grow old when you forget how to play.

[font=arial, sans-serif]I do not know if these data shall go help on something, but I did as follows: D3DXMATRIX ident;
D3DXMATRIX modelWorld;
D3DXMatrixIdentity(&ident);
m_pDevice->SetTransform(D3DTS_WORLD, &modelWorld);
D3DXMATRIX final = bone->TransformationMatrix*(*parentMatrix);
D3DXVECTOR3 boneLocation(final._41,final._42,final._43);
D3DXVec3Project(&boneLocation,&boneLocation,&m_vp,&m_pm,&m_vm,&modelWorld); // use YOUR viewport, projection and view matrices in this call
Logging->LogMessage(MSG_INFO,"boneLocation.x ",boneLocation.x);
Logging->LogMessage(MSG_INFO,"boneLocation.y ",boneLocation.y);
Logging->LogMessage(MSG_INFO,"boneLocation.z ",boneLocation.z);
D3DXVECTOR3 dir = mouseLocation - boneLocation;

Logging->LogMessage(MSG_INFO,"mouseLocation.x ",mouseLocation.x);
Logging->LogMessage(MSG_INFO,"mouseLocation.y ",mouseLocation.y);
Logging->LogMessage(MSG_INFO,"mouseLocation.z ",mouseLocation.z);
Logging->LogMessage(MSG_INFO,"dir.x ",dir.x);
Logging->LogMessage(MSG_INFO,"dir.y ",dir.y);
Logging->LogMessage(MSG_INFO,"dir.z ",dir.z);

float offset = D3DX_PI/2.0f;
float angle = offset - atan2(dir.y,dir.x); // change this when you rotate the model
D3DXMATRIX rot;
D3DXMatrixRotationY(&rot,angle);
bone->CombinedTransformationMatrix = rot*final;


Look the data:
INFO: boneLocation.x -60.4733
INFO: boneLocation.y 853.739
INFO: boneLocation.z 0.947493
INFO: mouseLocation.x -56
INFO: mouseLocation.y 74
INFO: mouseLocation.z 0
INFO: dir.x 4.47333
INFO: dir.y -779.739
INFO: dir.z -0.947493
INFO: boneLocation.x -60.4733
INFO: boneLocation.y 853.739
INFO: boneLocation.z 0.947493
INFO: mouseLocation.x -105
INFO: mouseLocation.y 174
INFO: mouseLocation.z 0
INFO: dir.x -44.5267
INFO: dir.y -679.739
INFO: dir.z -0.947493
INFO: boneLocation.x -60.4733
INFO: boneLocation.y 853.739
INFO: boneLocation.z 0.947493
INFO: mouseLocation.x -115
INFO: mouseLocation.y 225
INFO: mouseLocation.z 0
INFO: dir.x -54.5267
INFO: dir.y -628.739
INFO: dir.z -0.947493
INFO: boneLocation.x -60.4733
INFO: boneLocation.y 853.739
INFO: boneLocation.z 0.947493
INFO: mouseLocation.x -99
INFO: mouseLocation.y 225
INFO: mouseLocation.z 0
INFO: dir.x -38.5267
INFO: dir.y -628.739
INFO: dir.z -0.947493
INFO: boneLocation.x -60.4733
INFO: boneLocation.y 853.739
INFO: boneLocation.z 0.947493
INFO: mouseLocation.x 159
INFO: mouseLocation.y 79
INFO: mouseLocation.z 0
INFO: dir.x 219.473
INFO: dir.y -774.739
INFO: dir.z -0.947493
INFO: boneLocation.x -60.4734
INFO: boneLocation.y 853.739
INFO: boneLocation.z 0.947493
INFO: mouseLocation.x 427
INFO: mouseLocation.y 65
INFO: mouseLocation.z 0
INFO: dir.x 487.473
INFO: dir.y -788.739
INFO: dir.z -0.947493
INFO: boneLocation.x -60.4734
INFO: boneLocation.y 853.739
INFO: boneLocation.z 0.947493
INFO: mouseLocation.x 586
INFO: mouseLocation.y 106
INFO: mouseLocation.z 0
INFO: dir.x 646.473
INFO: dir.y -747.739
INFO: dir.z -0.947493
http://mateusvitali.wordpress.com/
As I mentioned before:
In your code, you don't set the modelWorld matrix to a valid value. You should be using the same world transform that you use when you render the mesh.

Please don't PM me with questions. Post them in the forums for everyone's benefit, and I can embarrass myself publicly.

You don't forget how to play when you grow old; you grow old when you forget how to play.


As I mentioned before:
In your code, you don't set the modelWorld matrix to a valid value. You should be using the same world transform that you use when you render the mesh.




[font="arial, sans-serif"]Sorry by my ignorance, but if I'm not doing correctly, how about it?
http://mateusvitali.wordpress.com/
When you render the mesh, how do you set the world transform, the dev->SetRenderState(D3DTS_WORLD,...) call? Post the code you use to render the mesh.

In your code, you have

D3DXMATRIX modelWorld;

You don't set the value of that variable before you call D3DXVec3Project(..., &modelWorld).

Please don't PM me with questions. Post them in the forums for everyone's benefit, and I can embarrass myself publicly.

You don't forget how to play when you grow old; you grow old when you forget how to play.

[font="arial, sans-serif"]No, I'm not calling [font=&quot;arial, verdana, tahoma, sans-serif&quot;]dev-&gt;SetRenderState(D3DTS_WORLD,…) when rendering the mesh <img src='http://public.gamedev.net/public/style_emoticons/default/huh.gif' alt='huh.gif'><br /> <br /> [font=&quot;arial, sans-serif&quot;]My code to render the mesh is:<br /> [font=&quot;arial, sans-serif&quot;]<code>void SKINNEDMESH::Render(BONE *bone, float scale)<br /> {<br /> if(bone == NULL)bone = (BONE*)m_pRootBone;<br /> <br /> // Setup world matrix<br /> D3DXMATRIXA16 matWorld,matWorld2;<br /> // set the rotation matrix<br /> D3DXMatrixRotationYawPitchRoll(&amp;matWorld2,rotation.x,rotation.y,rotation.z);<br /> <br /> D3DXMatrixScaling(&amp;matWorld,scale,scale,scale);<br /> D3DXMatrixMultiply(&amp;matWorld,&amp;matWorld,&amp;matWorld2);<br /> <br /> D3DXMatrixTranslation( &amp;matWorld2, vPos.x, vPos.y,vPos.z );<br /> <br /> D3DXMatrixMultiply(&amp;matWorld,&amp;matWorld,&amp;matWorld2);<br /> <br /> m_pDevice-&gt;SetTransform( D3DTS_WORLD, &amp;matWorld );<br /> <br /> //If there is a mesh to render..<br /> if(bone-&gt;pMeshContainer &#33;= NULL)<br /> {<br /> BONEMESH *boneMesh = (BONEMESH*)bone-&gt;pMeshContainer;<br /> <br /> if (boneMesh-&gt;pSkinInfo &#33;= NULL)<br /> { <br /> // set up bone transforms<br /> int numBones = boneMesh-&gt;pSkinInfo-&gt;GetNumBones();<br /> for(int i=0;i &lt; numBones;i++)<br /> D3DXMatrixMultiply(&amp;boneMesh-&gt;currentBoneMatrices<span style="font-weight:bold;">,<br /> &amp;boneMesh-&gt;boneOffsetMatrices<span style="font-weight:bold;">,<br /> boneMesh-&gt;boneMatrixPtrs<span style="font-weight:bold;">);<br /> <br /> //Update the skinned mesh<br /> BYTE *src = NULL, *dest = NULL;<br /> boneMesh-&gt;OriginalMesh-&gt;LockVertexBuffer(D3DLOCK_READONLY, (VOID**)&amp;src);<br /> boneMesh-&gt;MeshData.pMesh-&gt;LockVertexBuffer(0, (VOID**)&amp;dest);<br /> <br /> boneMesh-&gt;pSkinInfo-&gt;UpdateSkinnedMesh(boneMesh-&gt;currentBoneMatrices, NULL, src, dest);<br /> <br /> boneMesh-&gt;MeshData.pMesh-&gt;UnlockVertexBuffer();<br /> boneMesh-&gt;OriginalMesh-&gt;UnlockVertexBuffer();<br /> <br /> //Render the mesh<br /> for(int i=0;i &lt; boneMesh-&gt;NumAttributeGroups;i++)<br /> {<br /> int mtrlIndex = boneMesh-&gt;attributeTable<span style="font-weight:bold;">.AttribId;<br /> m_pDevice-&gt;SetMaterial(&amp;(boneMesh-&gt;materials[mtrlIndex]));<br /> m_pDevice-&gt;SetTexture(0, boneMesh-&gt;textures[mtrlIndex]);<br /> boneMesh-&gt;MeshData.pMesh-&gt;DrawSubset(mtrlIndex);<br /> }<br /> }<br /> }<br /> <br /> <br /> if(bone-&gt;pFrameSibling &#33;= NULL)Render((BONE*)bone-&gt;pFrameSibling, scale);<br /> if(bone-&gt;pFrameFirstChild &#33;= NULL)Render((BONE*)bone-&gt;pFrameFirstChild, scale);<br /> }</code><br /> <br /> [font=&quot;arial, sans-serif&quot;] [font=&quot;arial, sans-serif&quot;] [font=&quot;arial, sans-serif&quot;]<blockquote>[font=&quot;arial, verdana, tahoma, sans-serif&quot;]You don&#39;t set the value of that variable before you call D3DXVec3Project(…, &amp;modelWorld)[font=&quot;arial, sans-serif&quot;][font=&quot;arial, verdana, tahoma, sans-serif&quot;][font=&quot;arial, sans-serif&quot;]And what are the values that I set for example?[font=&quot;arial, sans-serif&quot;]
http://mateusvitali.wordpress.com/
I'm not calling dev->SetRenderState(D3DTS_WORLD,...) when rendering the mesh
Ouch! My mistake. I intended dev->SetTransform(D3DTS_WORLD,...).

In the code you just posted, you calculate matWorld and call m_pDevice->SetTransform(D3DTS_WORLD, &matWorld).

That matWorld matrix value, as you have calculated it, should be used in the D3DXVec3Project call.

Please don't PM me with questions. Post them in the forums for everyone's benefit, and I can embarrass myself publicly.

You don't forget how to play when you grow old; you grow old when you forget how to play.

This topic is closed to new replies.

Advertisement