OpenGL剪辑

时间:2011-09-24 09:55:29

标签: opengl-es clipping bounding-box

我现在已经阅读了有关剪辑的文章数小时了,但我似乎找不到解决问题的方法。

这是我的情景:

在OpenGL ES环境(IOS,Android)中,我有一个由可绘制对象组成的2D场景图,形成一棵树。

每个树节点都有自己的空间,它有自己的变换矩阵,每个节点都会将其坐标空间继承给它的子节点。每个节点都有一个矩形边界框,但这些边界框不是轴对齐的。

此设置非常适合渲染2D场景图,遍历树,渲染每个对象,然后渲染它的子对象。

现在出现了我的问题:我正在寻找一种在节点上启用剪切的方法。启用剪辑后,应在离开父边界框的区域时剪切节点的子节点。

例如,我想让一个节点包含一组文本节点作为子节点,可以使用它的父节点边框向上和向下滚动,并且在离开父节点边界框​​的区域时应该被剪裁。

由于边界框不是轴对齐的,我不能使用glScissor,这是最简单的方法。

我正在考虑使用模板缓冲区并将填充的边界矩形绘制到其中,当启用剪切时,然后启用模板缓冲区。这可能会起作用但会导致另一个问题:如果剪切节点内的子节点再次出现剪辑会发生什么? - 必须为孩子设置模板掩模,擦除父母的模板掩模。

我想到的另一个解决方案是在软件中进行裁剪。这是可能的,因为在每个节点内,剪切可以相对容易地在它自己的局部坐标空间中完成。这个解决方案的反向提取是必须为每个实现的新节点类型实现剪切。

这里有人能指出我正确的方向吗? 我正在寻找的是像glscissor的功能,用于剪切非轴对齐的矩形区域。

1 个答案:

答案 0 :(得分:5)

剪刀盒是一种简单的工具,可满足简单需求。如果您的需求不那么简单,那么您将不得不使用不那么简单的OpenGL机制进行裁剪:模板缓冲区。

假设您目前没有将模板缓冲区用于其他任何目的,您可以访问8个模板位。通过为场景图中的每个级别提供比最后一个级别更高的数字,您可以为每个级别分配自己的模板蒙版。当然,如果同一深度级别的两个兄弟姐妹重叠,或者只是太靠近,那么你就会遇到问题。

另一种方法是为每个节点分配一个从1到255的数字。使用GL_EQUAL的模板测试,您将能够防止上面的重叠问题。但是,这意味着整个场景图中的节点数不能超过255个。根据您的特定需求,这可能是一个太大的限制。

当你通过任何一种方法用完比特时,你当然可以清除模板(和深度。不要试图只清除其中一个)。但这可能有些昂贵,而且需要你清除深度,这可能是你不想做的。

另一种方法是对非轴对齐节点使用递增数和GL_EQUAL测试。对大多数节点使用剪刀框,但如果有一些旋转(无论是在该节点上还是继承),则使用模板掩码代替,在处理图形时碰撞掩码计数器。同样,您只能使用256个节点,但至少这些节点仅适用于旋转节点。根据您的需求和旋转节点的数量,这可能就足够了。