jnsmalm / pixi3d

The 3D renderer for PixiJS. Seamless integration with 2D applications.
https://pixi3d.org
MIT License
759 stars 44 forks source link

Raycasting world mouse position on a ground plane in orthographic (isometric) mode #50

Closed Unwarped closed 3 years ago

Unwarped commented 3 years ago

Hey again.

I have been having fun experimenting with Pixi3D.

I succeeded in getting the world mouse position of a 3d ground plane with this code:

        var normal = new PIXI3D.Vec3.fromValues(0, 1, 0)
        var plane = new PIXI3D.Plane(normal, 0.01)
        var ray = PIXI3D.Camera.main.screenToRay(MouseX, MouseY)
        var raycast = plane.rayCast(ray);
        var point = ray.getPoint(raycast)

But it doesn't seem to work in orthographic mode. Only in perspective.

Is there anything I have to change for it to work in orthographic mode?

Please let me know if you need a working example or more code.

Thanks!

jnsmalm commented 3 years ago

I have to check and see why this wouldn't work with orthographic camera.

Unwarped commented 3 years ago

Thank you jnsmalm! I made a playground example in case it helps: https://www.pixiplayground.com/#/edit/j0rijRVXRBPItApj_DyqI Click anywhere to see the blue cube move to the raycasted click position. Uncomment line 23 and it breaks

I did some research and it seems like this might be a common problem raycasting an orthographic camera.

https://stackoverflow.com/questions/18553209/orthographic-camera-and-selecting-objects-with-raycast

Any idea how I might adapt that solution to my code?

jnsmalm commented 3 years ago

Think I found a solution for it, seems like has to be done just a tiny bit different for orthographic camera. Use this function instead, I will also fix this in the lib.

function screenToRay(x, y) {
  let screen = PIXI3D.Camera.main.screenToWorld(x, y, 1);
  if (screen) {
    return new PIXI3D.Ray(screen.array, PIXI3D.Camera.main.worldTransform.forward);
  }
}
Unwarped commented 3 years ago

Brilliant. Thank you again jnsmalm! It works very nicely now. var ray = PIXI3D.Camera.main.orthographic ? screenToRay(MouseX, MouseY) : PIXI3D.Camera.main.screenToRay(MouseX, Mouse) Using this hack for the moment :)