|
一位名为 Agustinus Nalwan 的奶爸曾经从事游戏开发、计算机视觉、3D 动画等方面的工作,疫情期间,他为两岁半的儿子 Dexie 制作了一款名为 Griffin 的视觉互动游戏。
图丨 Dexie 的游戏体验
Griffin 本意为狮身鹰脸的神兽,在《哈利波特》中,格兰芬多学院(Gryffindor)即指金色的 Griffin。Nalwan 的儿子 Dexie 非常喜欢老鹰,所以 Nalwan 便以 Griffin 为原型制作了这样一款游戏。在 Medium 上,他发布了制作过程的细节并公布了游戏的开源代码。本文着重介绍其制作过程。
图丨传说中的 griffin
所需模块:3D 游戏引擎;身体姿势估计;动作映射和手势识别;通信系统。
所需硬件:NVIDIA Jetson AGX Xavier;显示器;Sony IMX327 摄像头;万能胶带。
图丨 NVIDIA Jetson AGX Xavier、Sony IMX327 摄像头和万能胶带
制作过程
一、构建 3D 游戏引擎
Griffin 系统用第三视角渲染 3D 世界,既可以看到雄鹰的翅膀随着玩家同步摆动,又可以更加逼真地模拟真实飞行。专业的 3D 游戏引擎有 Unity 和 Unreal,但都不能在 Ubuntu OS 或 ARM 上运行,因此 Nalwan 找到了一个可以在 OpenGL 上运行的 C++ 开源飞行模拟器,并对其作出了一些修改。
首先,他将基于按键的飞行控制系统改成了基于手势识别的飞控。
其次,他重构了静态 3D 模型,来符合鹰的身体结构。原始的飞行器模型与鹰不同的是,飞行器是一个保持不变的形体,以机身为轴线转动,而鹰则有一对不断运动的翅膀。因此,他使用 3D 作图工具 Blender,改变了原始机身的骨骼动画系统,把机翼作为两个单独的 3D 模型加到机身上,作为鹰的两翼。
图丨 Blender 中编辑的鹰的 3D 模型
接着,他设置了不同的游戏状态,使得可以通过玩家的动作直接重新开始游戏。游戏中的鹰有两种状态,或站立在树枝上,或飞翔在蓝天里。
最后,他使用 libSFML 添加了音效,当鹰一起飞,就会伴随着鹰的啸声和急促的风声。
二、构建身体姿势识别
这一模块是通过对身体各个部位的确认,来识别不同的身体姿势,以代表不同的游戏指令。通过检测手臂的姿态、脸部的位置等,系统就能确定玩家的特定姿势,触发动画中鹰的动作效果。
其中涉及到一个名为 OpenPose 的开源库,其包含各种手势识别、姿势识别、面部识别的 AI 模型,而 Nalwan 使用了名为 COCO 的身体姿势模型。该模型含有 18 个骨骼节点捕捉器,能实时识别人体的 18 个关节,Griffin 用到了其中 6 个关节。
图丨 COCO 关节点图
OpenPose 建立在 PyTorch 框架之上,该框架在 NVIDIA AGX Xavier 中运行帧率很低,只有 4FPS。Nalwan 则使用 torch2trt 工具,将 PyTorch 模型移植到 TensorRT 中,大大加快了帧率,达到 100FPS。
图丨人体姿态识别
不过,该模型的关节识别有时候会出错,偶尔会识别到一些其他物件,而不是玩家本人。为此,Nalman 添加了辅助 AI 模型来解决这个问题,他使用 Amazon SageMaker JumpStart,这是 AWS 近日发布的一款工具,可以轻易在 TensorFlowHub 和 PyTorchHub 部署 AI 模型,一共有 150 多种型号可选。
图丨错误情况
这种 AI 辅助模型具有对象检测功能,可以确定玩家主体的边界框,这样系统就不会把一些杂物识别成人物关节了。
图丨人体边框以外的关节点被排除在外
三、构建动作映射和手势识别
该模块将通过玩家的 6 个关节识别出游戏的各种指令:
第一,身体倾斜。玩家通过倾斜身体控制鹰在飞行途中的转向。系统根据手臂与水平面的角度来计算倾斜程度,从而控制转向幅度。在这里 Nalwan 选择了肘关节作为参考点,而非腕关节,是因为腕关节常常出画或被遮挡。
第二,手臂旋转。在站立时旋转手臂,鹰也会跟着拨动翅膀,这单纯是一个趣味性互动画面。系统根据手肘与水平面的夹角计算鹰翼的倾角,同时再增加 15 度,使得画面更加生动。
图丨身体倾斜和手臂旋转的动作映射
第三,下蹲。这也是一个没有具体功能的动作,代表雄鹰起飞前的起势动作。系统计算颈部到鼻子的长度与肩膀长度的比例,作为蹲伏偏移量。蹲的幅度越大,颈部到鼻子的距离就越小,而肩膀长度不变。之所以不直接计算颈部到鼻子的长度,是因为玩家到相机的距离不同,这个长度也不同,会影响到就算结果,从而不能触发雄鹰的下蹲动作。
图丨下蹲动作映射
第四,起飞姿势。该姿势识别通过两肩的中心点的探测,如果在一秒内该点上下移动的幅度大于阈值,则判定为起飞姿势。触发起飞姿势后,雄鹰就会跳出树枝,腾空而起。
第五,重新启动姿势。当玩家转身背对相机,左右肩交换位置,系统判定为重新启动。重新启动后,雄鹰将再次站在树枝上,等待起飞。
图丨起飞和复位姿势识别
四、整合系统
在完成了上述三个模块的基础上,下一步就是把三者整合起来。连接关节识别模块和手势识别模块不难,因为两者都是由 Python 编写。但把这两者和 3D 引擎结合就出现了难题,因为 3D 引擎是由 C++ 编写的,而用 Python 访问 OpenGL 基本是不可能的。
为此,Nalwan 选择通过 socket 来整合该系统,这是 TCP 协议使用的一种低级通信机制。由于两个模块在同一电脑中运行,延迟将被控制在 5 毫秒以内。通信层由一个在 Python 应用中的客户端模块、和一个在 C++ 应用中的服务器模块组成。
图丨 Griffin 的整体架构图
校准与测试
一切准备好后,Nalwan 对 Griffin 系统进行了测试,在执行以上的节点捕捉、姿势识别和 3D 渲染的同时,整体的帧率达到 60FPS。
Nalwan 向儿子 Dexie 演示了如何玩这个游戏,儿子看着电视里的雄鹰和爸爸是一样的姿势,感到十分兴奋。Dexie 上手玩的时候,一下子就玩了半个小时,扮演着雄鹰的身份,在蓝天下翱翔、在峡谷里躲避。
图丨 Dexie 的飞行体验
对于 Nalwan 来说,这也是好事,一方面儿子玩的开心了,另一方面,儿子玩累了睡得很早,晚上 Nalwan 就不会被熊孩子打扰了。
总结
在 Nalwan 看来,这次制作游戏的实践也让他受益匪浅,他总结了如下的一些收获。
1.Torch2trt 能自动将 PyTorch 模型移植到 TensorRT 中去,大大加快 AI 模型的运行速率。
2.NVIDIA Jetson AGX Xavier 性能非常强劲,可以连贯地运行包含 30 个实时 1080p 视频的视觉模型。
3.Amazon SageMaker JumpStart 提供了海量的流行 AI 模型供开发者使用。
4.构建 3D 游戏引擎让他回忆起了之前作为游戏和电影 SFX 开发者的身份,刷新了对自己 OpenGL、C++ 和计算机图形学能力的认知。
5. 他本可以通过 Unity Engine 和 Kinect sensor 在 Xbox 中构建 Griffin,但是自己动手 DIY 一个游戏远比这有趣得多。
6. 在游戏里扮演一只老鹰是很累人的,要一直举着自己的手臂。然而,真正的老鹰会借助气流,保持它们滑翔的姿态。 |
|