У меня есть эта функция выбора, но она не работает.функция должна возвращать true, если она сталкивается с объектом, но возвращает 0;и это никогда не изменится.
вот моя функция выбора
BOOL D3dDevice::Picking(HWND hWnd, LPDIRECT3DDEVICE9 d3ddev, CXFileEntity *entity)
{
D3DXVECTOR3 v;
D3DXMATRIX matProj;
POINT pt;
D3DVIEWPORT9 vp;
GetCursorPos(&pt);
ScreenToClient(hWnd, &pt);
d3ddev->GetTransform(D3DTS_PROJECTION, &matProj);
d3ddev->GetViewport(&vp);
v.x = ( ( ( 2.0f * pt.x ) / vp.Height ) - 1 ) / matProj._11;
v.y = -( ( ( 2.0f * pt.x ) / vp.Width ) - 1 ) / matProj._22;
v.z = 1.0f;
D3DXMATRIX m;
D3DXVECTOR3 rayOrigin,rayDir;
D3DXMATRIX matView;
d3ddev->GetTransform(D3DTS_VIEW, &matView);
D3DXMatrixInverse( &m, NULL, &matView );
// Transform the screen space pick ray into 3D space
rayDir.x = v.x*m._11 + v.y*m._21 + v.z*m._31;
rayDir.y = v.x*m._12 + v.y*m._22 + v.z*m._32;
rayDir.z = v.x*m._13 + v.y*m._23 + v.z*m._33;
rayOrigin.x = m._41;
rayOrigin.y = m._42;
rayOrigin.z = m._43;
// Use inverse of matrix
D3DXMATRIX matInverse, matWorld;
d3ddev->GetTransform(D3DTS_WORLD, &matWorld);
// Use inverse of matrix
D3DXMatrixInverse(&matInverse,NULL,&matWorld);
// Transform ray origin and direction by inv matrix
D3DXVECTOR3 rayObjOrigin,rayObjDirection, rayDirection;
D3DXVec3TransformCoord(&rayObjOrigin,&rayOrigin,&matInverse);
D3DXVec3TransformNormal(&rayObjDirection,&rayDirection,&matInverse);
D3DXVec3Normalize(&rayObjDirection,&rayObjDirection);
BOOL hasHit;
float distanceToCollision;
D3DXIntersect(entity->pDrawMesh, &rayObjOrigin, &rayObjDirection, &hasHit, NULL, NULL, NULL, &distanceToCollision, NULL, NULL);
return hasHit;
}
примечание: мой pDrawMesh является изменяемым LPD3DXMESH, а не LPD3DXBASEMESH. ОБНОВЛЕНИЕ
BOOL D3dDevice::Picking(HWND hWnd, LPDIRECT3DDEVICE9 d3ddev, CXFileEntity *entity)
{
D3DXVECTOR3 v;
D3DXMATRIX matProj;
POINT pt;
D3DVIEWPORT9 vp;
D3DXMATRIX matInverse, matWorld;
D3DXMATRIX m;
D3DXVECTOR3 rayOrigin,rayDir;
D3DXMATRIX matView;
D3DXVECTOR3 rayObjSpace;
D3DXVECTOR3 rayObjOrigin,rayObjDirection, rayDirection;
GetCursorPos(&pt);
ScreenToClient(hWnd, &pt);
d3ddev->GetTransform(D3DTS_PROJECTION, &matProj);
d3ddev->GetViewport(&vp);
d3ddev->GetTransform(D3DTS_VIEW, &matView);
// Use inverse of matrix
d3ddev->GetTransform(D3DTS_WORLD, &matWorld);
D3DXVECTOR3 vec3( pt.x, pt.y, 1.0f );
D3DXVec3Unproject( &rayObjSpace, &vec3, &vp, &matProj, &matView, &matWorld );
// Transform ray origin and direction by inv matrix
D3DXMATRIX invWorld;
D3DXMatrixInverse( &invWorld, NULL, &matWorld );
D3DXVECTOR3 camObjSpace;
D3DXVECTOR3 camPos(0.0, 0.0, -14.0f);
D3DXVec3TransformCoord( &camObjSpace, &camPos, &invWorld );
rayDir = rayObjSpace - camObjSpace;
BOOL hasHit;
float distanceToCollision;
if(FAILED(D3DXIntersect(entity->pDrawMesh, &rayObjSpace, &rayDir, &hasHit, NULL, NULL, NULL, &distanceToCollision, NULL, NULL)))
{
PostQuitMessage(0);
};
if(hasHit==1)
{
PostQuitMessage(0);
}
return hasHit;
}
ОБНОВЛЕНИЕ 2: Теперь оно не пересекается; /.BOOL D3dDevice :: Picking (HWND hWnd, LPDIRECT3DDEVICE9 d3ddev, CXFileEntity * entity, int z) {D3DXVECTOR3 v;POINT pt;D3DVIEWPORT9 vp;D3DXMATRIX matInverse, matWorld, m, matView, matProj;
GetCursorPos(&pt);
ScreenToClient(hWnd, &pt);
d3ddev->GetTransform(D3DTS_PROJECTION, &matProj);
d3ddev->GetViewport(&vp);
d3ddev->GetTransform(D3DTS_WORLD, &matWorld);
d3ddev->GetTransform(D3DTS_VIEW, &matView);
// Use inverse of matrix
D3DXVECTOR3 rayPos(pt.x, pt.y,0); // near-plane position
D3DXVECTOR3 rayDir(pt.x, pt.x,1); // far-plane position
D3DXVec3Unproject(&rayPos,&rayPos,&vp,&matProj,&matView,&matWorld);
D3DXVec3Unproject(&rayDir,&rayDir,&vp,&matProj,&matView,&matWorld);
rayDir -= rayPos; // make a direction from the 2 positions
D3DXVec3Normalize(&rayDir,&rayDir); // don't know if this is necessary.
// Transform ray origin and direction by inv matrix
BOOL hasHit;
float distanceToCollision;
if(FAILED(D3DXIntersect(entity->pDrawMesh, &rayPos, &rayDir, &hasHit, NULL, NULL, NULL, &distanceToCollision, NULL, NULL)))
{
PostQuitMessage(0);
};
if(hasHit!=0)
PostQuitMessage(0);
return hasHit;
}
ОБНОВЛЕНИЕ 3: Хорошо, теперь оно всегда пересекается; / после изменения значений в этой функции
D3DXMatrixPerspectiveFovLH(&matProjection,
D3DXToRadian(45), // the horizontal field of view
(FLOAT)Width / (FLOAT)Height, // aspect ratio
0.0f, // the near view-plane
1.0f); // the far view-plane