GL 项目无法正常工作

发布于 2024-10-05 01:33:36 字数 1449 浏览 1 评论 0原文

我正在使用尝试像 Glu.Project() 一样工作的代码,因为 OpenTK 不支持 Glu。

        Vector4 pos = new Vector4(s.Position.X, 0.0f, s.Position.Y, 1.0f);
        Matrix4 mov = new Matrix4();
        Matrix4 prj = new Matrix4();
        Matrix4 mpj = new Matrix4();
        float[] vp = new float[4];

        GL.GetFloat(GetPName.ModelviewMatrix, out mov);
        GL.GetFloat(GetPName.ProjectionMatrix, out prj);
        GL.GetFloat(GetPName.Viewport, vp);

        Matrix4.Mult(ref prj, ref mov, out mpj);
        Vector4.Transform(ref pos, ref mpj, out pos);

        // Final mathematics as described in OpenGL 2.1 Glu specs
        s.set2DPos(new Vector2f( (vp[0] + (vp[2] * (pos.X + 1) / 2.0f)),
                                (vp[1] + (vp[3] * (pos.Y + 1) / 2.0f)) ));

        // Final mathematics as described in OpenGL 3 Vector specs
        s.set2DPos(new Vector2f( (view[2] / 2 * pos.X + view[0]),
                                (view[3] / 2 * pos.X + view[1]) ));

        // Neither of them work, but in relation OpenGL 3 vector specs work better.

s 是一个类,主要作为 3D 空间中的模型存在于 s.Position 处。 但我从中得到的值远远超出了窗口边界。

来自断点的 ModelView 矩阵:

{(1, 0, 0, 0)
(0, 0.7071068, 0.7071068, 0)
(0, -0.7071068, 0.7071068, 0)
(0, -141.4214, -141.4214, 1)}

来自断点的投影矩阵:

{(1.931371, 0, 0, 0)
(0, 2.414213, 0, 0)
(0, 0, -1.0002, -1)
(0, 0, -2.0002, 0)}

我做错了什么还是我做错了什么?我错过了什么吗?

I'm using code which tries to work like Glu.Project() since OpenTK doesn't support Glu.

        Vector4 pos = new Vector4(s.Position.X, 0.0f, s.Position.Y, 1.0f);
        Matrix4 mov = new Matrix4();
        Matrix4 prj = new Matrix4();
        Matrix4 mpj = new Matrix4();
        float[] vp = new float[4];

        GL.GetFloat(GetPName.ModelviewMatrix, out mov);
        GL.GetFloat(GetPName.ProjectionMatrix, out prj);
        GL.GetFloat(GetPName.Viewport, vp);

        Matrix4.Mult(ref prj, ref mov, out mpj);
        Vector4.Transform(ref pos, ref mpj, out pos);

        // Final mathematics as described in OpenGL 2.1 Glu specs
        s.set2DPos(new Vector2f( (vp[0] + (vp[2] * (pos.X + 1) / 2.0f)),
                                (vp[1] + (vp[3] * (pos.Y + 1) / 2.0f)) ));

        // Final mathematics as described in OpenGL 3 Vector specs
        s.set2DPos(new Vector2f( (view[2] / 2 * pos.X + view[0]),
                                (view[3] / 2 * pos.X + view[1]) ));

        // Neither of them work, but in relation OpenGL 3 vector specs work better.

s is a class which primary exists as a model in 3D space at s.Position.
But the values I'm getting from this are astronomically far beyond the window boundaries.

The ModelView matrix from a breakpoint:

{(1, 0, 0, 0)
(0, 0.7071068, 0.7071068, 0)
(0, -0.7071068, 0.7071068, 0)
(0, -141.4214, -141.4214, 1)}

The Projection matrix from a breakpoint:

{(1.931371, 0, 0, 0)
(0, 2.414213, 0, 0)
(0, 0, -1.0002, -1)
(0, 0, -2.0002, 0)}

Am I doing something wrong or did I get something wrong? Am I missing something?

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

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

发布评论

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

评论(3

蹲在坟头点根烟 2024-10-12 01:33:36
    Vector2 GetScreenCoordinates(Vector3 ObjectCoordinate)
    {
        // ref: http://www.songho.ca/opengl/gl_transform.html
        Vector4 obj = new Vector4(ObjectCoordinate.X, ObjectCoordinate.Y, ObjectCoordinate.Z, 1.0f);
        Matrix4 projection = new Matrix4();
        Matrix4 modelView = new Matrix4();
        Vector4 viewPort = new Vector4();

        GL.GetFloat(GetPName.ModelviewMatrix, out modelView);
        GL.GetFloat(GetPName.ProjectionMatrix, out projection);
        GL.GetFloat(GetPName.Viewport, out viewPort);

        Vector4
            eye = Vector4.Transform(obj, modelView),
            clip = Vector4.Transform(eye, projection);
        Vector3
            ndc = new Vector3(clip.X / clip.W, clip.Y / clip.W, clip.Z / clip.W);
        Vector2
            w = new Vector2(viewPort.Z / 2 * ndc.X + viewPort.X + viewPort.Z / 2,
                            viewPort.W / 2 * ndc.Y + viewPort.Y + viewPort.W / 2);

        return w;
    }
    Vector2 GetScreenCoordinates(Vector3 ObjectCoordinate)
    {
        // ref: http://www.songho.ca/opengl/gl_transform.html
        Vector4 obj = new Vector4(ObjectCoordinate.X, ObjectCoordinate.Y, ObjectCoordinate.Z, 1.0f);
        Matrix4 projection = new Matrix4();
        Matrix4 modelView = new Matrix4();
        Vector4 viewPort = new Vector4();

        GL.GetFloat(GetPName.ModelviewMatrix, out modelView);
        GL.GetFloat(GetPName.ProjectionMatrix, out projection);
        GL.GetFloat(GetPName.Viewport, out viewPort);

        Vector4
            eye = Vector4.Transform(obj, modelView),
            clip = Vector4.Transform(eye, projection);
        Vector3
            ndc = new Vector3(clip.X / clip.W, clip.Y / clip.W, clip.Z / clip.W);
        Vector2
            w = new Vector2(viewPort.Z / 2 * ndc.X + viewPort.X + viewPort.Z / 2,
                            viewPort.W / 2 * ndc.Y + viewPort.Y + viewPort.W / 2);

        return w;
    }
假情假意假温柔 2024-10-12 01:33:36

在使用 s.Position 值之前您是否仔细检查过它?应用于向量的投影和变换矩阵怎么样,它们看起来正常吗?

我不熟悉 OpenTK,但 set2DPos() 之前的数学看起来足够合理。

Have you sanity checked the s.Position value before using it? What about the projection and transformation matrices you apply to the vector, are they sane looking?

I'm not familiar with OpenTK, but the mathematics prior to set2DPos() look sensible enough.

2024-10-12 01:33:36

它的工作原理如下:

GL.GetFloat(GetPName.ModelviewMatrix, out model);
GL.GetFloat(GetPName.ProjectionMatrix, out proj);
GL.GetFloat(GetPName.Viewport, view);

Matrix4.Transpose(ref model, out model);
Matrix4.Transpose(ref proj, out proj);

Vector4 posa = new Vector4(0.0f, s.Position.Y, 1.0f, s.Position.X);
Vector4 posb = new Vector4(s.Position.Y, 1.0f, s.Position.X, 0.0f);
Vector4 posc = new Vector4(1.0f, s.Position.X, 0.0f, s.Position.Y);

Vector4 one = new Vector4(1.0f, 1.0f, 1.0f, 1.0f);
Matrix4 posv = new Matrix4(pos, posa, posb, posc);

Matrix4 ProjPos = Matrix4.Mult(Matrix4.Mult(proj, model), posv);
Matrix4.Transpose(ref ProjPos, out ProjPos);

Vector2f posout = new Vector2f(
   (0 + (this.glc.Width * (ProjPos.Column0.X / ProjPos.Column0.W + 1.0f)) - (this.glc.Width / 2.0f)),
   (0 + (this.glc.Height * (ProjPos.Column0.Y / ProjPos.Column0.W + 1.0f)) - (this.glc.Height / 2.0f))
);

以防万一有人需要它:)

Here is how it works:

GL.GetFloat(GetPName.ModelviewMatrix, out model);
GL.GetFloat(GetPName.ProjectionMatrix, out proj);
GL.GetFloat(GetPName.Viewport, view);

Matrix4.Transpose(ref model, out model);
Matrix4.Transpose(ref proj, out proj);

Vector4 posa = new Vector4(0.0f, s.Position.Y, 1.0f, s.Position.X);
Vector4 posb = new Vector4(s.Position.Y, 1.0f, s.Position.X, 0.0f);
Vector4 posc = new Vector4(1.0f, s.Position.X, 0.0f, s.Position.Y);

Vector4 one = new Vector4(1.0f, 1.0f, 1.0f, 1.0f);
Matrix4 posv = new Matrix4(pos, posa, posb, posc);

Matrix4 ProjPos = Matrix4.Mult(Matrix4.Mult(proj, model), posv);
Matrix4.Transpose(ref ProjPos, out ProjPos);

Vector2f posout = new Vector2f(
   (0 + (this.glc.Width * (ProjPos.Column0.X / ProjPos.Column0.W + 1.0f)) - (this.glc.Width / 2.0f)),
   (0 + (this.glc.Height * (ProjPos.Column0.Y / ProjPos.Column0.W + 1.0f)) - (this.glc.Height / 2.0f))
);

In case anyone needs it :)

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