本文是此系列两部分中的第 1 部分,介绍了 Mobile 3D Graphics API (JSR 184) 的有关内容。作者将带领您进入 Java 移动设备的 3D 编程世界,并展示了处理光线、摄像机和材质的方法。
init() 中的第一个步骤就是使用户获取图形上下文(GC),以便绘制 3D 图形。Graphics3D 是一个单元素,_graphics3d 中保存了一个引用,以备将来使用。接下来,创建一个 VertexBuffer 以保存顶点数据。在后文中可以看到,可以为一个顶点指派多种类型的信息,所有顶点都包含于 VertexBuffer 之中,在设置使用 _cubeVertexData.setPositions() 的 VertexArray 中,您惟一需要获取的信息就是顶点位置。VertexArray 构造函数中保存了顶点数量(8 个)、各顶点的组件数(x, y, z)以及各组件的大小(1 字节)。由于这个立方体非常小,1 个字节足以容纳一个坐标。如果需要创建大型的对象,那么还可以创建使用 Short 值(2 个字节)的 VertexArray。但不能使用实数,只能使用整数。接下来,使用 TRIANGLE_INDICES 中的索引对 TriangleStripArray 进行初始化操作。
初始化代码的最后一部分就是摄像机设置。在 setPersective() 中,可设置观察角度、纵横比和剪贴板。注意纵横比和剪贴板的值应为浮点值。M3G 需要 Java 虚拟机(Java Virtual Machine,JVM)提供浮点值支持,这是在 CLDC 1.1 以后的版本中增加的功能。经过观察后,将摄像机从立方体处移开,以查看对象的全视图。可通过平移实现这一操作,转换 部分将就这一主题进行详细讨论。现在,您只要相信,带有第三个正数参数的 postTranslate() 可使摄像机沿 z 轴移动。
初始化后,您就可以将场景渲染到屏幕上。清单 3 实现了此功能。
清单 3. 显示立方体的示例,第 3 部分:绘图
/**
* Renders the sample on the screen.
*
* @param graphics the graphics object to draw on.
*/
protected void paint(Graphics graphics)
{
_graphics3d.bindTarget(graphics);
_graphics3d.clear(null);
_graphics3d.render(_cubeVertexData, _cubeTriangles,
new Appearance(), null);
_graphics3d.releaseTarget();
}
关于示例代码 如果想尝试建立并运行本文中的示例,可以在 “下载” 部分中下载完整的源代码。我使用了 Sun 的 Java Wireless Toolkit 2.2,并将我的项目配置为使用 MIDP 1.0、CLDC 1.1 —— 当然,还有 M3G。我将各部分的示例均作为单独类加以实现。另外还实现了一个简单的界面,您可以在这里选择及执行各个示例。wi-m3gsamples1.zip 压缩包中包含 readme.txt 文件,其中的信息更为详细。
在 paint() 中,bindTarget() 将 Canvas 的图形上下文指派给 Graphics3D。从而开始渲染 3D 对象,到调用 releaseTarget() 时终止渲染。调用 clear() 清除背景后,即可通过 init() 中创建的顶点数据和三角形绘制对象。许多 Graphics3D 的方法都会抛出不可控异常,但绝大多数错误都是不可恢复的,所以我决定不在代码中使用 try/catch 块。可在 VerticesSample.java 处找到本文的全部源代码。
我编写了一个简单的 MIDlet,用于显示示例。可从 下载 中获得 MIDlet 及本文全部源代码。示例运行结果如图 2 所示。
图 2. 示例立方体
很难看出这个屏幕上的矩形就是立方体,这是因为我将摄像机放置在其正对面,这就像站在一堵白墙前面一样。为什么是白色呢?我还没有指派任何颜色,而默认颜色就是白色。下一节将在颜色方面对程序进行完善。
顶点颜色 创建 VertexBuffer 时,我曾提到可以为一个顶点指派多种类型的信息 —— 颜色也是其中之一。图形硬件是以流水线形式处理顶点的,就像工厂以流水线组装汽车一样。它逐个地对各顶点进行一系列的处理,直至各顶点都显示在屏幕上。在这一架构中,来自所有顶点的所有数据都必须同时可用。可以设想,如果组装工人必须每次从不同的地方取螺丝,效率该有多么低。
图 3 以平面布局展示了立方体的前五个顶点,还包括(R,G,B)格式的颜色信息。角上的数字同样是在三角形带中使用的索引。
图 3. 带有索引、顶点颜色和方位的三角形带
为顶点指派颜色对三角形内的像素会有什么影响呢?可能性之一就是为整个三角形使用同样的顶点颜色。另外还有可能在两个顶点之间插入颜色,实现颜色梯度效果。M3G 允许用户在这两个选项之间任选其一。在平面着色渲染模式下,可用三角形的第三个顶点颜色为整个三角形着色。如果您将图 2 所示第 1 个三角形定义为(0,1,2),则其颜色为红色(255,0,0)。在光影渲染模式下,三角形中的各像素都通过插值而获得了自己的颜色。索引 0 和 2 之间的像素初始颜色为绿色(0,255,0),渐变为红色。有些三角形共享索引 2 和索引 3 处的顶点,由于一个顶点只能有一种颜色,所以这也就意味着这些三角形也使用了一种相同的颜色。