在OpenGL中任何事物都在3D空间中,可是屏幕和窗口是一个2D像素阵列,因此OpenGL的大部分工做都是关于如何把3D坐标转变为适应你屏幕的2D像素。3D坐标转为2D坐标的处理过程是由OpenGL的图形渲染管线完成的。图像渲染管线能够被划分为两个主要部分:第一个部分把你的3D坐标转换为2D坐标,第二部分是把2D坐标转变为实际的有颜色的像素。小程序
渲染管线接收一组3D坐标,而后把它们转变为你屏幕上的有色2D像素。渲染管线能够被划分为几个阶段,每一个阶段须要把前一阶段的输出做为输入。全部这些阶段都是高度专门化的,它们能简单地并行执行。因为它们的并行执行的特征,当今大多数显卡都有成千上万的小处理核心GPU,在GPU上为每个阶段运行各自的小程序,从而在图形输送管道中快速处理你的数据。这些小程序叫作着色器。有些着色器容许开发者本身配置,用咱们本身写的着色器替换默认存在的。这样咱们就能够更细致地控制渲染管线的特定部分,由于它们运行在GPU上,因此它们也会节约宝贵的CPU时间。着色器是用OpenGL着色器语言(OpenGL Shading Language)GLSL写成的。数组
下图显示了渲染管线中各个阶段主要完成的工做,蓝色部分表明的是咱们能够定义本身的着色器。测试

在上图中,咱们以数组的形式传递3个3D坐标做为渲染管线的输入,用它来表示一个三角形,这个数组叫作顶点数据(Vertex Data);这里顶点数据是几个顶点的集合。每一个顶点是用顶点属性(vertex attributes)表示的,它能够包含任何咱们但愿用的数据,下面咱们来看看渲染管线中各个阶段主要完成的工做:blog
- 渲染管线的第一个部分是顶点着色器(vertex shader),它把一个单独的顶点做为输入。顶点着色器主要的目的是把3D坐标转为另外一种3D坐标(投影坐标),同时顶点着色器容许咱们对顶点属性进行一些基本处理。
- 图元组装(primitive assembly)阶段把顶点着色器的表示为基本图形的全部顶点做为输入,把全部点组装为特定的基本图形的形状;上图中是一个三角形。
- 图元组装阶段的输出会传递给几何着色器(geometry shader)。几何着色器把基本图形造成的一系列顶点的集合做为输入,它能够经过产生新顶点构造出新的(或是其余的)基本图形来生成其余形状。
- 细分着色器(tessellation shaders)拥有把给定基本图形细分为更多小基本图形的能力。这样咱们就能在物体更接近玩家的时候经过建立更多的三角形的方式建立出更加平滑的视觉效果。
- 细分着色器的输出会进入光栅化(rasterization)阶段,这里它会把基本图形映射为屏幕上相应的像素,生成供像素着色器(fragment shader)使用的fragment(OpenGL中的一个fragment是OpenGL渲染一个独立像素所需的全部数据。)。在像素着色器运行以前,会执行裁切(clipping)。裁切会丢弃超出你的视图之外的那些像素,来提高执行效率。
- 像素着色器的主要目的是计算一个像素的最终颜色,这也是OpenGL高级效果产生的地方。一般,像素着色器包含用来计算像素最终颜色的3D场景的一些数据(好比光照、阴影、光的颜色等等)。
- 在全部相应颜色值肯定之后,最终它会传到另外一个阶段,咱们叫作alpha测试和混合(blending)阶段。这个阶段检测像素的相应的深度(和stencil)值,使用这些来检查这个像素是否在另外一个物体的前面或后面,如此作到相应取舍。这个阶段也会查看alpha值(alpha值是一个物体的透明度值)和物体之间的混合(blend)。因此即便在像素着色器中计算出来了一个像素所输出的颜色,最后的像素颜色在渲染多个三角形的时候也可能彻底不一样。
虽然渲染管线有多个阶段,每一个阶段都须要对应的着色器,但其实对于大多数场合,咱们必须作的只是顶点和像素着色器,几何着色器和细分着色器是可选的,一般使用默认的着色器就好了。如今的OpenGL中,咱们必须定义至少一个顶点着色器和一个像素着色器(由于GPU中没有默认的顶点/像素着色器)。ip