一直没时间学习手机,以前写过一篇 OpenGL ES 的学习笔记,结果数据丢失。。。还好发现网上有朋友替我做了备份(排版丢失,花了点时间才所代码行分清楚)。这两天重新翻出了 eclipse 和 Android SDK,复习下基础先
Android 上开发三维图形程序主要使用 OpenGL ES 接口了, 这个OpenGL ES (OpenGL for Embedded Systems) 是 OpenGL 的子集,主要针对移动设备。该API目前由 Khronos 维护,Khronos是一个图形软硬件行业协会,该协会主要关注图形和多媒体方面的开放标准。
这个 OpenGL ES 的接口和OpenGL一样,C风格的定义,说起来比 DirectX 的 C++ 风格要简洁明了, 但弄到面向对像的 Java 里来 — 说实话 — 就有点不伦不类的样子了, 尤其Java 一没指针二不支持引用传参, 所以看到用数组参数返回值的情况也不奇怪了。
首先建立一个Android OpenGL 程序的框架,主要用 GLSurfaceView 类及 Renderer 接口的实现类。 在 Eclipse 中新建一个Android Project, Project Name => HelloWorld, Package name => com.leftcode.android.HelloWorld, 并勾选 Create Activity => Main。
在新建好的Project中, 打开 src/com.leftcode.android.HelloWorld 下的 Main.java,添加一个成员变量
修改 onCreate 方法,把 setContentView(…) 一行删除,替换为以下内容:
接下来要定义 HelloWorldRenderer 类了, 这个类将 GLSurfaceView.Renderer 接口
现在我们已经定义好了一个OpenGL应用程序的基本部分, 这个程序在启动时创建GLSurfaceView作为主Activity的内容, 设置HelloWorldRenderer为绘图器对象,在表面创建时禁用颜色抖动,并设置颜色缓冲清除颜色为黑色。在表面尺寸变化时, 设置视口和投影矩阵。在绘制图形时仅仅清除颜色缓冲区。 现在运行程序,显示漆黑一片!
先来加点形状。OpenGL以三角形为基本绘图单位,数据表示上,三角形由三个顶点组成。先定义些顶点
这是一个立方体的8个顶点的数据,顶点可以是二、三、四维的,这里用的三维形式。数据类型为float,也可以是integer的。 定义完顶点后,还要把这些顶点连成三形才能绘制,这里用顶点索引模式,所以接下来定义索引数据
这里定义了构成立方体的12个三角形(6个表面,每个表面2个三角形)。 在有了顶点数据和索引数据后, 还要把数据装入缓冲对像中才能被OGL使用,所以定义缓冲成员变量
和一个createBuffers方法
然后在 Renderer 的构造方法中调用 createBuffers 方法创建数据缓冲对象。
现在要绘制这个立方体了
其中用了一个成员变量angle 控制每次绘制的角度
运行一下, 显示了一个旋转的立方体 — 实际上确切的说是一个绿乎乎平平的变化的多边形。这是因为 glColor 模式简单的将颜色填充在多边形中,没有层次,所以看起来一点也不立体, 来简单怎么改进下吧。glColor 设置所有的顶点使用一个颜色值,所以一切都是平的,来为顶点单独设置下颜色看看
以上是8个顶点的8个颜色值,也要用 ByteBuffer 传递给GL,添加 名为colors 的ByteBuffer 成员变量
并修改createBuffers 添加以下内容
修改绘制代码
将表示角度的成员变量angle 一分为三以让旋转看上去更有魅力:)
并修改旋转模型的代码为
运行发现在旋转过程中方块有的面出现缺失,这是因为绘制三角形的顺序问题,如果先绘制了前边的,后边的三角形在绘制时会把前边的覆盖。 这个问题可以使用深度测试来解决。 修改 onSurfaceCreated 添加以下代码启用深度测试
再次运行,效果好多了(虚拟机截图):