Clipping-planes in OpenGL ES 2.0
2016-07-19 10:06
639 查看
I need to clip a few hundred objects under a clipping plane in OpenGL ES 2.0 and would appreciate ideas from people more experienced with this subset of OpenGL.
In OpenGL ES 1.x there is glClipPlane. On the desktop you have glClipPlane, or gl_ClipDistance in your shader. Neither of these two are available in OpenGL ES 2.0. It seems that this kind of functionality disappeared completely with 2.0.
It seems the only way to do this is either A) run the plane equation in the fragment shader, or B) write a very complex vertex shader that positions vertices on the plane if they are behind it.
(A) would be slow compared to glClipPlane, since "regular" clipping is done after the vertex shader and before the fragment shader, each fragment would still have to be partially processed and discarded.
(B) would be very hard to make compatible between shaders, since we can't discard vertices we have to align them with the plane and adjust attributes for those that are "cut". It's not possible to interpolate between vertices in the shader without sending all
vertices in a texture and sample it, which would be extremely expensive. Often it would probably be impossible to interpolate the data correcly anyway.
I've also thought of aligning the near plane with the clipping plane which would be an efficient solution.
And drawing a plane after rendering the whole scene and checking for depth-fail will not work either (unless you are looking close to perpendicular to the plane).
What works for a single object is to draw the plane to the depth buffer and then render the object with glDepthFunc(GL_GREATER), but as expected it does not work when one of the objects is behind another. I tried to build on to this concept but eventually ended
up with something very similar to shadow volumes and just as expensive.
So what am I missing? How would you do plane clipping in OpenGL ES 2.0?
Here is two solutions I've found on Vuforia
SDK forums.
Using shaders by Harri Smatt:
Using quad in depth buffer by Alessandro Boccalatte:
disable color writing (i.e. set the
render a quad which matches the marker shape (i.e. just a quad with the same size and position/orientation of the marker); this will only be rendered into the depth buffer (because
we disabled color buffer writing in the previous step)
enable back the color mask (
render your 3D models
In OpenGL ES 1.x there is glClipPlane. On the desktop you have glClipPlane, or gl_ClipDistance in your shader. Neither of these two are available in OpenGL ES 2.0. It seems that this kind of functionality disappeared completely with 2.0.
It seems the only way to do this is either A) run the plane equation in the fragment shader, or B) write a very complex vertex shader that positions vertices on the plane if they are behind it.
(A) would be slow compared to glClipPlane, since "regular" clipping is done after the vertex shader and before the fragment shader, each fragment would still have to be partially processed and discarded.
(B) would be very hard to make compatible between shaders, since we can't discard vertices we have to align them with the plane and adjust attributes for those that are "cut". It's not possible to interpolate between vertices in the shader without sending all
vertices in a texture and sample it, which would be extremely expensive. Often it would probably be impossible to interpolate the data correcly anyway.
I've also thought of aligning the near plane with the clipping plane which would be an efficient solution.
And drawing a plane after rendering the whole scene and checking for depth-fail will not work either (unless you are looking close to perpendicular to the plane).
What works for a single object is to draw the plane to the depth buffer and then render the object with glDepthFunc(GL_GREATER), but as expected it does not work when one of the objects is behind another. I tried to build on to this concept but eventually ended
up with something very similar to shadow volumes and just as expensive.
So what am I missing? How would you do plane clipping in OpenGL ES 2.0?
5down vote | Apparently I was on to something when I attempted to do clipping using the projection matrix. Exactly how to do this is described in this paper I found: http://www.terathon.com/lengyel/Lengyel-Oblique.pdf |
5down vote | Apparently I was on to something when I attempted to do clipping using the projection matrix. Exactly how to do this is described in this paper I found: http://www.terathon.com/lengyel/Lengyel-Oblique.pdf |
SDK forums.
Using shaders by Harri Smatt:
uniform mat4 uModelM; uniform mat4 uViewProjectionM; attribute vec3 aPosition; varying vec3 vPosition; void main() { vec4 pos = uModelM * vec4(aPosition, 1.0); gl_Position = uViewProjectionM * pos; vPosition = pos.xyz / pos.w; }
precision mediump float; varying vec3 vPosition; void main() { if (vPosition.z < 0.0) { discard; } else { // Choose actual color for rendering.. } }
Using quad in depth buffer by Alessandro Boccalatte:
disable color writing (i.e. set the
glColorMask(false, false, false, false);)
render a quad which matches the marker shape (i.e. just a quad with the same size and position/orientation of the marker); this will only be rendered into the depth buffer (because
we disabled color buffer writing in the previous step)
enable back the color mask (
glColorMask(true, true, true, true);)
render your 3D models
5down vote | Apparently I was on to something when I attempted to do clipping using the projection matrix. Exactly how to do this is described in this paper I found: http://www.terathon.com/lengyel/Lengyel-Oblique.pdf |
1down vote | I don't know if this applies to OpenGL ES, but OpenGL has the gl_ClipDistance varying output enabled by glEnable(GL_CLIP_DISTANCE0). Once enabled, the primitive is clipped such that gl_ClipDistance[0] >= 0 after the vertex and geometry shaders. The clip distance can be specified as just a dot product with a world-space plane equation: http://github.prideout.net/clip-planes/ |
5down vote | Apparently I was on to something when I attempted to do clipping using the projection matrix. Exactly how to do this is described in this paper I found: http://www.terathon.com/lengyel/Lengyel-Oblique.pdf |
1down vote | I don't know if this applies to OpenGL ES, but OpenGL has the gl_ClipDistance varying output enabled by glEnable(GL_CLIP_DISTANCE0). Once enabled, the primitive is clipped such that gl_ClipDistance[0] >= 0 after the vertex and geometry shaders. The clip distance can be specified as just a dot product with a world-space plane equation: http://github.prideout.net/clip-planes/ |
相关文章推荐
- CentOS下编译安装MySQL 5.6.21
- 码神Linux01
- security information and event management 学习初探(三)
- Nginx配置IP白名单和黑名单
- ubuntu系统知识汇总(2016-7-18)
- Unix操作系统查看系统性能监控工具
- Centos7 下 Hadoop 2.6.4 分布式集群环境搭建
- 修改linux下默认的python版本
- Linux命令之dos2unix - 将DOS格式文本文件转换成UNIX格式
- window open opener
- Linux和windows双系统启动问题之一(win7 + ubuntu14.04 + legacy bios + mbr)
- linux修改系统时间
- Linux(CentOS)查看操作系统版本命令
- LINUX ESXI5.5系统安装手册
- opencv-cvCopy和cvCloneImage
- linux 内核参数VM调优 之 参数调节和场景分析
- opencv-线性滤波
- Linux(Ubuntu)下第一个C程序(0)
- Linux VM子系统参数调整
- linux操作系统-在文件夹复制一份Linux导入VMware后eth0网卡无法启动问题(或克隆linux虚拟机)