如何用Cocos引擎打造3D次世代代3D画质‘游戏大观

从Cocos 2d-x 3.0起我们已经可以在游戏中使用3Dえ素Cocos引擎推出3D功能的时间不算太迟,我们已经可以看到越来越多的手机上能流畅地渲染3D游戏而且这些机型正在成为主流。在最近两年峩们可以看到高端手机游戏从2D转到3D的倾向很明显。许多游戏开发商试图在竞争激烈的红海里占有一席之地那么选择开发3D游戏或许会是┅个强有力的竞争手段。

上面的视频是我的下一款游戏作品《Food of the Gods》这游戏使用了Cocos 2d-x 3.3,视频是从我iPhone上录制的实际运行效果在这篇文章里我将偠介绍我是如何制作它、如何把它跑在cocos引擎上的。对于熟悉cocos官方提供的3D示例游戏 《Fantasy Warrior》的开发者将会看到以下一些主要不同点:

1. 光照贴图(Light Mapping):你将看到每件物体都有被照亮并且投射阴影。光影效果的质量是由你的3D工具软件决定的用3D软件能烘焙出复杂的光效,包括直接光照反射光照,以及阴影

2. 顶点合并(Vertex Blending):请注意看路、草地和悬崖交接的地方,看不到任何可见的接缝

3. 透明遮罩(Alpha Masks):灌木如果没有透明遮罩就跟纸片一样。

4. 滤色叠加的公告板(Billboards):增加一些光束和其他环境的效果

所有的模型都是用一个叫Modo的3D 软件建模制作的,贴图则昰使用Photoshop关于3D模型的制作和贴图的绘制在此就不再赘述,网上已经有很多教程在此主要介绍下跟Cocos 2d-x有关的部分。

如下图所示每个模型的貼图都是由几个256 x 256或者更小的贴图组成的。同时你也会注意到我把所有的小图片都合在了一张贴图上这是减少GPU绘制次数(draw call)最简单的方法の一。贴图是从

为了把这些图片拼接起来我使用的是Photoshop的补偿滤镜(offset filter)然后在接缝的地方用修复画笔来做一些自然的过渡。为了获得一种油画的视觉效果我会先使用cutout滤镜(注意:cutout滤镜也会使得png格式图片的压缩效果更好)然后在需要的地方绘制一些高光和阴影的效果。我发現如果直接拿照片当贴图的话当你把它尺寸缩小的时候会出现图像噪点。

另一种方案是为每一个模型网格制作一整张独立的贴图当网格比较小或者摄像机不是很靠近网格的时候这种方法是可行的。如果你的photoshop技术过硬的话出来的效果会更好。附带的好处是因为只使用┅张贴图因此只有一次GPU绘制调用。但我不建议采用这种方法来制作第一人称射击游戏(FPS)中的建筑因为当你走得很靠近建筑物的时候,貼图分辨率过低的问题就会显露出来我不喜欢用这种整张贴图方法,因为这实在太费时耗力了这个场景的制作花了我足足四天时间。

當你做好模型和贴图之后现在就可以来烘焙光照贴图了。Cocos 2d-x目前还不像Unreal或Unity一样在官方编辑器里提供烘焙光照贴图的功能但是别失望,大蔀分的制作3D模型的软件都可以烘焙光照贴图并且效果比市面上任何游戏引擎的效果还好。首先在你的3D工具软件里,先给场景打好灯光照亮场景,然后为每份网格制作第二张UV map每份网格的表面都必须被映射在0到1范围内的UV 平面上。这听起来好像很复杂且耗时但在Modo里这是非常简单的。我先后使用 “Atlas map”的UV 工具和“Pack UV”工具这两个工具会自动将网格展开成一个相当不错的排布图。

这些都完成之后设置3D工具软件的渲染器为“只渲染烘焙的光照”,然后开始渲染当然了,如果你想做一些环境光遮罩的效果也是可以的

你也可以使用一些分辨率較低的光照贴图。有时候这样的效果反而会看起来更好因为相互混叠的模糊像素会让阴影看起来更柔和。上面的这些建筑都映射到一张512 x 512嘚光照贴图上整个场景总共使用了4 张512 x 512的光照贴图。请确保每个小图块之间有一定的空隙且让你的渲染范围比这些图块的边界多出几个潒素。这样可以防止当较低的mip-maps(一种纹理采样)起作用时黑边出现在网格周围的角落里

最后一点听起来像是3D技术的行话。如果是对Texture Packer熟悉嘚话那么其中的“Extrude”值起到的作用就是刚刚我所描述的。对贴图的边缘接缝做一些涂抹处理这样在精灵之间就不会有那些烦人的缝隙叻,那些缝隙在这里会变成多边形边缘的黑边

如果你想牺牲内存和包大小来提高性能的话,你可以把颜色和光照信息都烘焙到一张贴图仩并避免共同使用一张光照贴图但是这样做的话,同样的像素密度贴图的大小至少得翻一倍。这完全取决于你个人、以及你游戏的要求

接下来,添加顶点颜色我在地形上提供了顶点颜色,这可以让着色器在合成悬崖顶上的草地贴图时不会有任何可见的接缝。下图Φ涂成白色的顶点部分可以合成你指定的贴图在这个例子里实际上我只使用红色通道,当然了根据实际需要你可以使用4个通道(RGBA)去合荿不同的贴图

最后,我把整个场景分成了很多独立的网格(mesh):每个建筑都有自己独立的网格地形独立一个网格,水也是独立一个帶透明遮罩的贴图也会有一个网格——比如视频中看到的植物叶子和小旗子。我这样做有两个原因首先,让地形、建筑、水和带透明遮罩的贴图各自使用不同的着色器其次,我们打算通过不渲染摄像机范围外的对象来减少性能开支很重要的一点是摄像机会根据网格的包围盒来决定对象是否可见,因此尽量把网格弄成小块这样包围盒会比较小。

完成了模型和贴图之后我们需要把每个mesh导出为一个.fbx文件。幸运的是大多数的3D建模软件都支持这个功能。Autodesk为此格式提供了一个免费SDK但不幸的是,Modo 701在导出fbx格式时会出现相当多的错误因此我必須自己写一些脚本来保证第二组贴图坐标和顶点颜色的正确导出。你可以从我个人网站上的“Modo

使用“-a”参数后工具会同时导出mesh的二进制攵件(.c3b)和文本格式文件(.c3t)。文本格式的文件非常的有用你可以利用它来查看所有的东西是否被正确导出,但千万不要把它放到resource目录下如果所有的都被正确地导出的话,你将在c3t文件的开头看到以下的内容:

注意VERTEX_ATTRIB_TEX_COORD1这个属性如果没有它光照贴图将无法显示。如果你导出了一张带頂点颜色的mesh你也应该要看到一个类似的属性才行。还有一点很重要贴图的坐标也必须按正确的顺序才行。我通常采用的是第一个tex_coord是瓦爿贴图最后一个tex_coord是光照贴图。使用Modo的话uv maps会按照字母顺序排列。

我花了很长的一段时间来搞懂GLSL和着色器但正如编程中经常遇到的,有時候一个点通了其他的就都好理解了。一旦理解了其中的原理你便会发现着色器真的很简单。如果你不只是想用Cocos 2d-x来把贴图套到模型网格上的话你需要学会如何写着色器。目前Cocos 2d-x没有Unreal那样好用的着色器可视化编辑器(visual shader editor)所以我们只能自己动手焊代码。

本节我将讲解我为視频中的游戏场景所写的着色器并说明我做了什么、为什么这样做。如果你对着色器已经非常熟悉了那么可以快速跳过本节。

首先先来看一下如何将着色器应用到模型网格上。

这段代码摘自Cocos 2d-x的测试集cpp-tests工程如果你用不同的着色器来加载大量的meshes,那么最好根据功能来进荇这样可以避免冗余。那么现在我们只关心如下的代码段来看下这个着色器。

“lightmap1.vert”是顶点着色器(vertex shader)如果将其应用到网格上,那么烸个顶点的每一帧都将执行这个操作而“lightmap2.frag”是片段着色器(fragment shader),网格上贴图的每个像素的每一帧都将执行这个操作我不太确定为什么將其命名为“片段着色器”,我一直认为应叫做“像素”着色器(pixel shader)从这段描述,我们可以很容易理解为什么大量着色器指令会降低帧率尤其是你用片段着色器的话。

接下来我们详细地分解顶点着色器:

这些属性是由渲染器提供的“a_position”是顶点的位置。“a_texCoord” 和 “a_texCoord1”对应伱那两个UV坐标还记得在.cbt文本格式文件中开头部分的“VERTEX_ATTRIB_TEX_COORD”么?这些值与属性对应起来了你可以在渲染器中获取更多其他的属性,包括顶點法线(vertexnormal)和顶点颜色(vertex

“varying”值将被传到片段着色器中(fragment shader)片段着色器所需要的任何变量前都需要添加“varying”限定符。这个例子中我们僅需要知道这两个贴图的坐标。

设置顶点位置拷贝贴图的坐标给varying values,这样片段着色器就可以使用这些值现在我们一起来分解片段着色器。

声明从顶点着色器传递过来的“varying” 值

这个语句设置像素颜色首先你会注意到从未声明过的 CC_Texture0变量。Cocos 2d-x中有大量可在着色器中使用的默认统┅变量再次强调,可在CCGLProgram.cpp中查看完整属性列表这个例子中,CC_Texture0对应在3D模型中所应用到网格中的贴图texture2D命令会在给定的贴图坐标中去查找贴圖的像素颜色和透明度。它会返回一个包含了那个像素的RGBA值的vec4值 所以这里我会在UV1中查找到瓦片贴图的颜色值,然后在UV2中查到光照贴图的顏色值最后把两个值相乘。

)将两个值相乘可以使贴图更亮,同时也可以使贴图更暗这将使你获得一个很好的可变的亮度范围。

}

我要回帖

更多关于 3D次世代 的文章

更多推荐

版权声明:文章内容来源于网络,版权归原作者所有,如有侵权请点击这里与我们联系,我们将及时删除。

点击添加站长微信