如何根据鼠标单击获取 3D 中点的坐标?

发布于 2024-10-14 22:46:09 字数 673 浏览 6 评论 0原文

我希望当我单击屏幕上的特定点时,函数调用会返回我单击的 3d 场景中的点。

例如,当我点击屏幕左上角时,它应该返回 x = 0, y = 1, z= 1;请帮助我创建一个方法来执行此操作。

编辑:

Root = new BranchGroup();

setLayout(new BorderLayout());
add(canvas3D,BorderLayout.CENTER);
SimpleUniverse universe = new SimpleUniverse(canvas3D);

Shape();
universe.addBranchGraph(Root);
ViewingPlatform viewingPlatform = universe.getViewingPlatform();
OrbitBehavior behavior = new OrbitBehavior(canvas3D);
behavior.setSchedulingBounds(bounds);
viewingPlatform.setViewPlatformBehavior(behavior);
viewingPlatform.setNominalViewingTransform();
}

我在 NetBeans 中使用 SimpleUniverse

I want that when I click on a specific point on the screen, a function call that return the point in 3d scene that I click.

For example, when I click on the top left of the screen, it should return x = 0, y = 1, z= 1; please help me create a method to do this.

edit:

Root = new BranchGroup();

setLayout(new BorderLayout());
add(canvas3D,BorderLayout.CENTER);
SimpleUniverse universe = new SimpleUniverse(canvas3D);

Shape();
universe.addBranchGraph(Root);
ViewingPlatform viewingPlatform = universe.getViewingPlatform();
OrbitBehavior behavior = new OrbitBehavior(canvas3D);
behavior.setSchedulingBounds(bounds);
viewingPlatform.setViewPlatformBehavior(behavior);
viewingPlatform.setNominalViewingTransform();
}

I'm using SimpleUniverse in NetBeans.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

握住你手 2024-10-21 22:46:09

恐怕答案并不直接。根据场景中的内容,单击屏幕时鼠标坐标应该发生变化。例如,如果您有两个对象,因此前面的对象遮挡了后面的对象,那么您需要获取前面的对象坐标。这称为“鼠标选取”,有多种技术可以实现。我找到了一些论坛来解释它是如何完成的并有代码示例。

基本上,这个想法是您想象在您(用户)和屏幕之间存在激光(或其他投射射线的东西)。然后,这个东西会通过屏幕表面上鼠标单击的点“进入”屏幕来投射一条光线。然后,光线路径上的任何物体都将被拾取,并且可以选择解析光线路径中对象的遮挡顺序,为您提供最接近“屏幕”的对象。

我对 J3D 不熟悉,但从一些教程中将以下代码拼凑在一起。它至少应该让你开始。您要查找的内容是底部的这一行 Point3D Intercept = ...

http://www.java3d.org/selection.html

package j3d_picking;

import java.awt.*;
import javax.swing.*;
import javax.media.j3d.*;
import com.sun.j3d.utils.universe.*;
import com.sun.j3d.utils.picking.behaviors.*;
import com.sun.j3d.utils.geometry.*;
import com.sun.j3d.utils.picking.PickIntersection;
import com.sun.j3d.utils.picking.PickResult;
import com.sun.j3d.utils.picking.PickTool;
import javax.vecmath.Point3d;

public class HelloJava3D
        extends JFrame
{

    public HelloJava3D()
    {
        GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration();
        Canvas3D canvas3D = new Canvas3D(config);

        BranchGroup scene = createSceneGraph();

        // SimpleUniverse is a Convenience Utility class
        SimpleUniverse simpleU = new SimpleUniverse(canvas3D);

        // This moves the ViewPlatform back a bit so the
        // objects in the scene can be viewed.
        simpleU.getViewingPlatform().setNominalViewingTransform();

        BoundingSphere behaveBounds = new BoundingSphere();
        ExamplePickBehavior behavior = new ExamplePickBehavior(canvas3D, scene, behaveBounds);
        scene.addChild(behavior);

        scene.compile();
        simpleU.addBranchGraph(scene);

        getContentPane().add(canvas3D, BorderLayout.CENTER);
    } // end of HelloJava3D (constructor)

    public BranchGroup createSceneGraph()
    {
        // Create the root of the branch graph
        BranchGroup objRoot = new BranchGroup();

        // Create a simple shape leaf node, add it to the scene graph.
        // ColorCube is a Convenience Utility class
        ColorCube cube = new ColorCube(0.4);
        cube.setCapability(Node.ENABLE_PICK_REPORTING);
        PickTool.setCapabilities(cube, PickTool.INTERSECT_FULL);
        objRoot.addChild(cube);

        return objRoot;
    } // end of createSceneGraph method of HelloJava3D

    public static void main(String[] args)
    {
        JFrame frame = new HelloJava3D();
        frame.setTitle("Hello Java3D");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.setBounds(0, 0, 400, 300);
        frame.setVisible(true);
    }

    private class ExamplePickBehavior extends PickMouseBehavior
    {

        public ExamplePickBehavior(Canvas3D canvas, BranchGroup bg, Bounds bounds)
        {
            super(canvas, bg, bounds);
            setSchedulingBounds(bounds);

            pickCanvas.setMode(PickTool.GEOMETRY_INTERSECT_INFO);
            // allows PickIntersection objects to be returned
        }

        public void updateScene(int xpos, int ypos)
        {
            pickCanvas.setShapeLocation(xpos, ypos);
            // register mouse pointer location on the screen (canvas)

            Point3d eyePos = pickCanvas.getStartPosition();
            // get the viewer's eye location

            PickResult pickResult = null;
            pickResult = pickCanvas.pickClosest();
            // get the intersected shape closest to the viewer

            if (pickResult != null) {
                PickIntersection pi = pickResult.getClosestIntersection(eyePos);
                // get the closest intersect to the eyePos point
                Point3d intercept = pi.getPointCoordinatesVW();
                System.out.println(intercept);
                // extract the intersection pt in scene coords space
                // use the intersection pt in some way...
            }
        } // end of updateScene(  )
    } // end of ExamplePickBehavior class
}

I'm afraid the answer isn't straight forward. Depending on what is in your scene the mouse coordinates should change when you click on the screen. For instance if you have two objects so that the front one occludes the back one then you'd want to get the front objects coordinates. This is called mouse picking and there are several techniques for it. I found a few forums that explain how it's done and have code examples.

Basically the idea is that you imagine there being a laser (or something else that casts a ray) between you the user and the screen. This thing then projects a ray through the point on the screen surface where the mouse was clicked "into" the screen. Anything that is on the rays path will then be picked and optionally the occlusion order of objects in the ray's path is resolved to give you the object closest to the "screen".

I am not familiar with J3D, but scraped the following code together from a few tutorials. It should get you started at least. The this you are looking for is this line Point3D intercept = ... at the bottom.

http://www.java3d.org/selection.html

package j3d_picking;

import java.awt.*;
import javax.swing.*;
import javax.media.j3d.*;
import com.sun.j3d.utils.universe.*;
import com.sun.j3d.utils.picking.behaviors.*;
import com.sun.j3d.utils.geometry.*;
import com.sun.j3d.utils.picking.PickIntersection;
import com.sun.j3d.utils.picking.PickResult;
import com.sun.j3d.utils.picking.PickTool;
import javax.vecmath.Point3d;

public class HelloJava3D
        extends JFrame
{

    public HelloJava3D()
    {
        GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration();
        Canvas3D canvas3D = new Canvas3D(config);

        BranchGroup scene = createSceneGraph();

        // SimpleUniverse is a Convenience Utility class
        SimpleUniverse simpleU = new SimpleUniverse(canvas3D);

        // This moves the ViewPlatform back a bit so the
        // objects in the scene can be viewed.
        simpleU.getViewingPlatform().setNominalViewingTransform();

        BoundingSphere behaveBounds = new BoundingSphere();
        ExamplePickBehavior behavior = new ExamplePickBehavior(canvas3D, scene, behaveBounds);
        scene.addChild(behavior);

        scene.compile();
        simpleU.addBranchGraph(scene);

        getContentPane().add(canvas3D, BorderLayout.CENTER);
    } // end of HelloJava3D (constructor)

    public BranchGroup createSceneGraph()
    {
        // Create the root of the branch graph
        BranchGroup objRoot = new BranchGroup();

        // Create a simple shape leaf node, add it to the scene graph.
        // ColorCube is a Convenience Utility class
        ColorCube cube = new ColorCube(0.4);
        cube.setCapability(Node.ENABLE_PICK_REPORTING);
        PickTool.setCapabilities(cube, PickTool.INTERSECT_FULL);
        objRoot.addChild(cube);

        return objRoot;
    } // end of createSceneGraph method of HelloJava3D

    public static void main(String[] args)
    {
        JFrame frame = new HelloJava3D();
        frame.setTitle("Hello Java3D");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.setBounds(0, 0, 400, 300);
        frame.setVisible(true);
    }

    private class ExamplePickBehavior extends PickMouseBehavior
    {

        public ExamplePickBehavior(Canvas3D canvas, BranchGroup bg, Bounds bounds)
        {
            super(canvas, bg, bounds);
            setSchedulingBounds(bounds);

            pickCanvas.setMode(PickTool.GEOMETRY_INTERSECT_INFO);
            // allows PickIntersection objects to be returned
        }

        public void updateScene(int xpos, int ypos)
        {
            pickCanvas.setShapeLocation(xpos, ypos);
            // register mouse pointer location on the screen (canvas)

            Point3d eyePos = pickCanvas.getStartPosition();
            // get the viewer's eye location

            PickResult pickResult = null;
            pickResult = pickCanvas.pickClosest();
            // get the intersected shape closest to the viewer

            if (pickResult != null) {
                PickIntersection pi = pickResult.getClosestIntersection(eyePos);
                // get the closest intersect to the eyePos point
                Point3d intercept = pi.getPointCoordinatesVW();
                System.out.println(intercept);
                // extract the intersection pt in scene coords space
                // use the intersection pt in some way...
            }
        } // end of updateScene(  )
    } // end of ExamplePickBehavior class
}
挽心 2024-10-21 22:46:09

在此处输入代码下面的 Java 代码,在 3D 屏幕中打印 3D 对象(形状)的中心坐标。结果是 (x=-0.5 ,y=0.0 ,z=0.4)

         public class secim2 extends MouseAdapter{


private PickCanvas pickCanvas;





public secim2(){
    JFrame pencere=new JFrame();
    pencere.setSize(300, 300);
    pencere.setVisible(true);
    JFrame frame = new JFrame(" 3D Box Select");

    GraphicsConfiguration config =                 SimpleUniverse.getPreferredConfiguration();

    Canvas3D canvas = new Canvas3D(config);

    SimpleUniverse universe = new SimpleUniverse(canvas);

    BranchGroup group = new BranchGroup();


    // create a color cube


       Transform3D transform= new Transform3D();
    Vector3d vector = new Vector3d(-0.5, 0.0, 0.4);

        Transform3D transform = new Transform3D();

        transform.setTranslation(vector);

        TransformGroup transformGroup = new TransformGroup(transform);

        ColorCube cube = new ColorCube(0.1f);

        transformGroup.addChild(cube);

        group.addChild(transformGroup);


        universe.getViewingPlatform().setNominalViewingTransform();

        universe.addBranchGraph(group);


      pickCanvas = new PickCanvas(canvas, group);

      pickCanvas.setMode(PickCanvas.GEOMETRY_INTERSECT_INFO);

     pencere.add(canvas);

      canvas.addMouseListener(this);


}

public void mouseClicked(MouseEvent e)

{



    pickCanvas.setShapeLocation(e);

    PickResult result = pickCanvas.pickClosest();

    if (result == null) {


    } else {

       Primitive p = (Primitive)result.getNode(PickResult.PRIMITIVE);  

       Shape3D s = (Shape3D)result.getNode(PickResult.SHAPE3D);

       if (p != null) {

         System.out.println(p.getClass().getName());


       } else if (s != null) {

             System.out.println(s.getClass().getName());

             Vector3f position = new Vector3f(); 

      s.getLocalToVworld(transform);  

        transform.get(position);

       System.out.print(position);

      // System.out.print( s.getLocalToVworld(transform2);
       } else{

          System.out.println("null");

       }

    }

}

}

public class tuval1 {

public static void main(String[] args) {
    // TODO Auto-generated method stub

new secim2();

}

}

enter code hereThe Java code below , prints the 3d object's (shapes) center coordinates in the 3d screen. Result is (x=-0.5 ,y=0.0 ,z=0.4)

         public class secim2 extends MouseAdapter{


private PickCanvas pickCanvas;





public secim2(){
    JFrame pencere=new JFrame();
    pencere.setSize(300, 300);
    pencere.setVisible(true);
    JFrame frame = new JFrame(" 3D Box Select");

    GraphicsConfiguration config =                 SimpleUniverse.getPreferredConfiguration();

    Canvas3D canvas = new Canvas3D(config);

    SimpleUniverse universe = new SimpleUniverse(canvas);

    BranchGroup group = new BranchGroup();


    // create a color cube


       Transform3D transform= new Transform3D();
    Vector3d vector = new Vector3d(-0.5, 0.0, 0.4);

        Transform3D transform = new Transform3D();

        transform.setTranslation(vector);

        TransformGroup transformGroup = new TransformGroup(transform);

        ColorCube cube = new ColorCube(0.1f);

        transformGroup.addChild(cube);

        group.addChild(transformGroup);


        universe.getViewingPlatform().setNominalViewingTransform();

        universe.addBranchGraph(group);


      pickCanvas = new PickCanvas(canvas, group);

      pickCanvas.setMode(PickCanvas.GEOMETRY_INTERSECT_INFO);

     pencere.add(canvas);

      canvas.addMouseListener(this);


}

public void mouseClicked(MouseEvent e)

{



    pickCanvas.setShapeLocation(e);

    PickResult result = pickCanvas.pickClosest();

    if (result == null) {


    } else {

       Primitive p = (Primitive)result.getNode(PickResult.PRIMITIVE);  

       Shape3D s = (Shape3D)result.getNode(PickResult.SHAPE3D);

       if (p != null) {

         System.out.println(p.getClass().getName());


       } else if (s != null) {

             System.out.println(s.getClass().getName());

             Vector3f position = new Vector3f(); 

      s.getLocalToVworld(transform);  

        transform.get(position);

       System.out.print(position);

      // System.out.print( s.getLocalToVworld(transform2);
       } else{

          System.out.println("null");

       }

    }

}

}

public class tuval1 {

public static void main(String[] args) {
    // TODO Auto-generated method stub

new secim2();

}

}

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文