大家好! 整整四年我都没有写过《哈伯》。 我最近的
系列文章是关于我们在上一款游戏中使用的各种工具和技巧(在Unity上开发)。 从那时起,我们成功发布了这款游戏,并且还发布了一款新游戏。 因此,现在您可以喘口气,写一些对某人可能有用的新文章。
今天,我想谈谈图形技巧和我们用来创建在上面的GIF中看到的图片的技巧。
我们对游戏的视觉效果非常敏感,因此在各种效果和其他包子上投入了大量时间和精力,这将使我们的像素艺术尽可能地吸引人。 也许有人会发现一些对自己有用的东西。
首先,我将简要列出游戏中的图片:
- 可变的环境光-取决于一天中的时间,照明的平常变化。
- LUT颜色校正-负责根据一天中的时间(或区域类型)更改图像的色调。
- 动态光源-火炬,火炉,灯具。
- 法线贴图-负责赋予对象体积,尤其是在移动光源时。
- 3D配光的数学-负责确保屏幕中央的光源正确照亮较高的物体,但不照亮较低的物体(即朝着相机的不发光侧)。
- 阴影-由子图形产生的阴影,会旋转并响应光源的位置。
- 模拟物体的高度-正确显示雾气。
- 其他装饰器:雨,风,动画(包括树叶和草的着色器动画)等。
现在更详细。
可变的环境光
原则上,这里没有什么特别的。 在晚上-较黑,白天-较浅。 光的颜色由时间梯度设置。 到了晚上,光源不仅变得更暗,而且获得了蓝色。
看起来像这样:
LUT色彩校正
LUT(查找表)-颜色交换表。 粗略地说,这是一个三维RGB阵列,其中每个节点上都有一个颜色值,应将其替换为相应的颜色值。 也就是说,如果在坐标(1、1、1、1)处有一个红点,则表示图片中的所有白色将被红色替换。 如果坐标(1,1,1)是白色(R = 1,G = 1,B = 1),则没有变化。 因此,对于与这些相同坐标相对应的每个坐标,不变的LUT具有颜色。 即 点(0.4、0.5、0.8)是颜色(R = 0.4,G = 0.5,B = 0.8)。
好吧,值得注意的是,为方便起见,他们将3D纹理呈现为二维。 例如,这是“默认” LUT的外观(不更改颜色渲染):

它是基本实现的,它可以快速,方便地工作。
设置起来也非常容易-您可以向艺术家提供游戏中的任何图片,并说“色调让您感觉像是晚上。” 之后,将所有色彩校正层应用于默认的LUT,并获得夜间LUT。
在我们的案例中,艺术家有些困惑,并在一天中的不同时间(夜晚,黄昏,晚上等)创建了多达10个不同的LUT。 这是他们的设置的外观:
结果,根据一天中的时间,相同的位置看起来会有所不同:

在这里,来自窗户的光精灵的透明度也会根据一天中的时间而变化。
动态光源和法线贴图
光源绝对来自Unity。 此外,还为每个子图绘制了法线贴图,这使您获得了体积感。
这样的法线很简单地绘制。 艺术家从四个方面用刷子大致绘制了一个灯光:
然后此脚本转到法线贴图:
如果您正在寻找可以做到这一点的着色器(和软件),则可以朝精灵灯的方向看。
3D灯光模拟
这有点复杂。 您不仅可以拾起并突出显示精灵。 我们需要考虑精灵是在光源“后面”还是“前面”。
注意这张照片:
这两棵树与光源的距离相同,但是,远处的树会被照亮,而最近的树则不会被照亮(因为其未照亮的部分朝向摄像机)。
我很简单地解决了这个问题。 着色器计算光源和精灵之间沿垂直y轴的距离。 如果它是正的(光源在子图形之前),则照常照亮子图形,但是如果它是负的(子图形会阻挡光源),但是光强度会以很大的系数从远处衰减。 精确地确定了系数,而不仅仅是“不发光”,因此当光源移动并突然出现在精灵后面时,精灵不会立即变黑而是逐渐变黑。 但是仍然很快。
暗影
精灵是围绕点旋转的精灵所产生的阴影。 我试图给它们增加更多的压缩(偏斜),但是事实证明这是不必要的。
总共,每个对象最多可以有4个阴影。 一种来自太阳,三种来自动态光源。 下图显示了原理:

“查找接下来的3个光源并计算阴影与它们之间的距离/角度”这一任务由Update中涉及的脚本解决。 是的,它的运行速度不是很快,因为 你必须做很多数学。 如果我现在写,我将在Unity中使用新的并行作业系统。 但这还没有,所以我尽可能地优化了普通脚本。
唯一重要的是我使子画面旋转不是变换而是在顶点着色器中进行变换。 即 旋转不动。 只是在sprite中设置了参数(我为此使用了颜色,因为所有相同,所有阴影均为黑色),并且着色器已经负责sprite的旋转。 这更快,因为 不必在Unity中拖动几何。
这种方法的另一个缺点是必须为每个对象分别设置(有时绘制)阴影。 没错,我们大概用了十几种不同的通用精灵(薄,厚,椭圆等)。
第二个缺点是有时很难为与地球的接触点非常长的物体制作阴影。 例如,看一下栅栏上的阴影:
不完美。 如果使篱笆本身的精灵是半透明的,则外观如下所示:
但是,在此值得注意的是,子画面在垂直方向上仍然非常变形(原始的阴影子画面看起来几乎像一个圆形)。 这就是为什么他的转弯看起来不像是转弯,而是扭曲。
雾和高度模拟
游戏中有雾。 看起来像这样(上面是普通版本,下面是一个极端的100%雾以演示效果)。

如您所见,房屋和树木的顶部从雾中伸出来。 实际上,达到这种效果非常简单。 雾由分布在舞台整个深度的许多水平云组成。 结果是,所有精灵的上部被更少的雾精灵所阻塞:

风
像素艺术风是另一个故事。 没有太多选择。 要么用双手进行动画处理(这对于我们的美术作品来说几乎是不可能的),或者编写变形的着色器,但是有时您不得不忍受难看的变形。 您当然可以根本不设置动画,但是随后图片看起来没有动画。
我们使用着色器选择了失真选项。 看起来像这样:
如果将此着色器应用于方格纹理,将清楚会发生什么:
还值得注意的是,我们没有为整个树冠设置动画,而只是为单个叶子设置了动画:
我们也随风摇动小麦,但是一切都很简单-顶点着色器考虑到y分量使x坐标变形。 点越高,交错越强。 这样做是为了使仅顶部交错,而根不交错。 另外-摆动相位从x / y坐标变化,因此屏幕上的不同精灵会随机摆动。
当玩家穿过小麦和草时,该着色器也可用于创建摇摆麦子和草的效果。
现在可能就这些了。 我故意没有解决构建场景及其几何的问题,因为 这是另一篇文章的材料。 对于其余的内容,他谈到了开发中使用的主要解决方案。
PS:如果有人对某些技术方面感兴趣,请在评论中写。 也许我会在另一篇文章中讲述。 当然,除非有必要。
PPS:我借此机会说,现在我们想在团队中找到几个有能力的人(程序员,PM,KM,艺术家)。 详细信息在工作室网站上。 我希望这句话不违反规则。