【问题标题】:OpenGL - setting visible areaOpenGL - 设置可见区域
【发布时间】:2013-06-05 02:10:38
【问题描述】:

编辑看来 glOrtho 做了我想做的事情(设置您要查看的区域),错误在我的代码中。然而,这可能是一个常见的初学者错误,所以有人可能仍然觉得这很有用

我正在使用 glOrtho(我认为设置正交投影应该比设置透视更容易)。无论如何,我在 500x500x500 的区域(我所有的可见区域)中绘制小立方体(1x1x1)。如何告诉 OpenGL(使用 openGL 2)在屏幕上绘制区域(500,500,500)中的所有内容?

这是我的代码 - 它是用 Java 编写的,但它应该可以正常工作......

public void reshape(GLAutoDrawable gLDrawable, int x, int y, int width, int height) 
{
    final GL2 gl = gLDrawable.getGL().getGL2();

    if (height <= 0) // avoid a divide by zero error!
    {
        height = 1;
    }

    final float h = (float) width / (float) height;

    gl.glViewport(0, 0, width, height);
    gl.glMatrixMode(GL2.GL_PROJECTION);
    gl.glLoadIdentity();
    gl.glOrtho(0, 512, 0, 512, 0, 512);
    gl.glMatrixMode(GL2.GL_MODELVIEW);
    gl.glLoadIdentity();
}

这似乎不起作用,我只能看到几个正方形而不是数百个......

这是我的立方体绘制代码(所有立方体的所有坐标都在0到500之间):

public void display(GLAutoDrawable gLDrawable) 
{
    final GL2 gl = gLDrawable.getGL().getGL2();
    gl.glClear(GL2.GL_COLOR_BUFFER_BIT | GL2.GL_DEPTH_BUFFER_BIT);
    gl.glLoadIdentity();

    for(InterestingVoxel iv: visibleList) {
        gl.glTranslatef(iv.getI(), iv.getJ(), iv.getK());
        System.out.println("x:"+iv.getI() + ", y:" + iv.getJ() + ", z:" + iv.getK());
        drawCube(gl);
    }


}

void drawCube(GL2 gl)
{
    gl.glBegin(GL2.GL_QUADS);

    // front
    gl.glVertex3f(0.5f, 0.5f, 0.5f);
    gl.glVertex3f(1.5f, 0.5f, 0.5f);
    gl.glVertex3f(1.5f, 1.5f, 0.5f);
    gl.glVertex3f(0.5f, 1.5f, 0.5f);
    // back
    gl.glVertex3f(0.5f, 0.5f, -0.5f);
    gl.glVertex3f(1.5f, 0.5f, -0.5f);
    gl.glVertex3f(1.5f, 1.5f, -0.5f);
    gl.glVertex3f(0.5f, 1.5f, -0.5f);
    // right
    gl.glVertex3f(1.5f, 0.5f, 0.5f);
    gl.glVertex3f(1.5f, 0.5f, -0.5f);
    gl.glVertex3f(1.5f, 1.5f, -0.5f);
    gl.glVertex3f(1.5f, 1.5f, 0.5f);
    // left
    gl.glVertex3f(0.5f, 0.5f, 0.5f);
    gl.glVertex3f(0.5f, 0.5f, -0.5f);
    gl.glVertex3f(0.5f, 1.5f, -0.5f);
    gl.glVertex3f(0.5f, 1.5f, 0.5f);
    // top
    gl.glVertex3f(0.5f, 1.5f, 0.5f);
    gl.glVertex3f(1.5f, 1.5f, 0.5f);
    gl.glVertex3f(1.5f, 1.5f, -0.5f);
    gl.glVertex3f(0.5f, 1.5f, -0.5f);
    // bottom
    gl.glVertex3f(0.5f, 0.5f, 0.5f);
    gl.glVertex3f(1.5f, 0.5f, 0.5f);
    gl.glVertex3f(1.5f, 0.5f, -0.5f);
    gl.glVertex3f(0.5f, 0.5f, -0.5f);

    gl.glEnd();
    gl.glFlush();
}

【问题讨论】:

  • 我看不出有什么问题。我们也可以看看你的立方体绘制代码吗?
  • 当然...刚刚添加了代码。

标签: opengl


【解决方案1】:

您的 glTranslate 调用正在累积,这使您的大多数立方体远远超出 512。也许您想使用矩阵堆栈,或者在循环内使用 glLoadIdentity

【讨论】:

  • 你是对的 - 我不得不在循环中使用 glLoadIdentity。谢谢!
【解决方案2】:

我假设您问的是如何将绘图限制在特定区域。如果不是,这是一个更通用的“我的代码不起作用”的问题,您可以忽略这个答案。

由于您使用的是 GL 2.x,因此您可能希望研究使用 ClipPlane 将绘图剪辑到特定区域。所以,在你的情况下,(取决于你传递给 GL 的数据是什么)你可能想要传递 3 到 6 个剪辑平面并启用它们(Enable(CLIP_PLANEi) where i 是剪辑平面索引/编号)。

例如(伪代码,因为我现在没有可用的 GL2 测试平台):

plane planes[] = {
    plane::from_triangle(
        500, 500, 500,
        500, 500, 0,
        500, 0, 500,
    ),
    plane::from_triangle(
        500, 500, 500,
        0, 500, 500,
        500, 0, 500,
    ),
    ...
}
// Assume the above is just a lot of GLdoubles somehow [e.g., POD types]

ClipPlane(6, planes)
for (unsigned plane_index = 0 to 5) {
    Enable(CLIP_PLANE0 + plane_index)
}

这样做,您可以合理地将渲染限制在指定平面的一侧。请记住,尽管这已被弃用(就像很多 GL 2.x 一样),所以如果您打算超越它,您可能需要在着色器中重新实现剪辑平面。

或者,只需检查您正在绘制的内容,并且仅在您想要绘制的区域内绘制它。

【讨论】:

    猜你喜欢
    • 2010-11-19
    • 1970-01-01
    • 2012-11-15
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-02-12
    • 1970-01-01
    相关资源
    最近更新 更多