user1658740
user1658740

Reputation: 75

ask about D3DXIntersect function:(

        // get the current transform matrices
    D3DXMATRIX matProjection, matView, matWorld, matInverse;
    ENGINE.GetDevice()->GetDevice()->GetTransform(D3DTS_PROJECTION, &matProjection);
    ENGINE.GetDevice()->GetDevice()->GetTransform(D3DTS_VIEW, &matView);
    ENGINE.GetDevice()->GetDevice()->GetTransform(D3DTS_WORLD, &matWorld);

    // use the mouse coordinates to get the mouse angle
    float xAngle = (((2.0f * ENGINE.GetInputManager()->GetMousePos()->x) / WINDOW_WIDTH) - 1.0f) / matProjection(0, 0);
    float yAngle = (((-2.0f * ENGINE.GetInputManager()->GetMousePos()->y) / WINDOW_HEIGHT) + 1.0f) / matProjection(1, 1);

    D3DXVECTOR3 origin, direction;
    origin = D3DXVECTOR3(0.0f, 0.0f, 0.0f);
    direction = D3DXVECTOR3(xAngle, yAngle, 1.0f);

    // find the inverse matrix
    D3DXMatrixInverse(&matInverse, NULL, &(matWorld * matView));

    // convert origin and direction into model space
    D3DXVec3TransformCoord(&origin, &origin, &matInverse);
    D3DXVec3TransformNormal(&direction, &direction, &matInverse);
    D3DXVec3Normalize(&direction, &direction);

    // detect picking
    BOOL hit;
    std :: list<CEntity*> :: iterator iter = MAINMANAGER.GetLegoObjectManager()->GetObjList().begin();
    CResource* g_pResource = NULL;

    while(iter != MAINMANAGER.GetLegoObjectManager()->GetObjList().end())
    {
        g_pResource = static_cast<CEntity*>(*iter)->GetResource();

        D3DXIntersect( static_cast<PassiveMesh*>(g_pResource)->GetMesh(), &origin, &direction, &hit, NULL, NULL, NULL, NULL, NULL, NULL);

        if(hit)
        {
            ENGINE.GetDevice()->GetDevice()->SetRenderState(D3DRS_LIGHTING, FALSE);
            break;
        }
        else
        {
            ENGINE.GetDevice()->GetDevice()->SetRenderState(D3DRS_LIGHTING, TRUE);
        }

        ++iter;
    }

This is my picking sample source code. I have a problem.

if I create three 3D objects. so picking works third object. not working first, second object.

if I create only one Object. picking works well!

if I create two object. picking works second object not first.

only create last obejct works picking well.

I don't find why this problem is coming.

please give me some advice.

Upvotes: 0

Views: 542

Answers (2)

ENGINE.GetDevice()->GetDevice()->GetTransform(D3DTS_WORLD, &matWorld);

This is the last rendered mesh's transforms. (because all meshes use device->SetTransform(D3DTS_WORLD, &something);)

You need get transform matrix of your target mesh after draw and use that.

yourtargetmesh->DrawSubset(0);
device->GetTransform(D3DTS_WORLD, &yourtargetmeshmatWorld);

Upvotes: 0

Joseph Pla
Joseph Pla

Reputation: 1598

What I'm guessing is that your list is not ordered by distance to camera, which is normal but because of this, you simply check a mesh and if there is a hit, you break. Instead, because you don't know the order of the list, you should check all meshes in the list, and then take the shortest one. The way you are doing things now makes the picking dependent on the list and not at all where the camera is.

Upvotes: 1

Related Questions