决定要制作怎样的节奏 FPS
《BPM: Bullets Per Minute》是一款节奏动作 FPS 游戏,当中的射击、换弹、跳跃和躲闪动作全都与节拍同步。
(国内观赏视频通道)
在准备开始制作的时候,我们考虑了以下声音设计方式:
1. 音符表(如《Guitar Hero》、《Rock Band》、《Frets on Fire》)。每条音轨都有用来定义攻击、躲闪和换弹节奏的元数据。这些元数据可告知敌人行为。音符表会告诉 AI 要做什么。
优点:心潮澎湃的音乐编排体验、可以由用户生成优质内容。
缺点:每分钟游戏的制作成本很高。耐玩性低。
2. 程序化音乐(如《PaRappa the Rapper》或《Wii Music》)。音乐由音轨段落组成。音轨段落是动态变换的,由算法选择下一个要播放的音轨段落。AI 会在各个音轨段落的特定标记点发起攻击。
设想一下当敌人在十六分音符处快速攻击时播放鼓声段落,随后当敌人在小鼓声处发起攻击时播放反拍。
优点:动感、耐玩。
缺点:音乐品质较低。音乐由玩家定义,而不是歌曲结构,音乐体验比较差。
3. 紧跟节拍(如《Crypt of the NecroDancer》)。AI 始终与歌曲的节拍保持一致,但动作并不依赖于音轨的状态。
优点:动感、耐玩。音乐可以有自己的多彩变换,便于轻松制作更多音乐内容,游戏设计不依赖于现成音乐。
缺点:音乐不是为体验量身打造的。
作为一个小型团队,我们想做一款规模相对较大、能玩好几个小时的游戏。为此,我们决定选用“紧跟节拍”这一声音设计方式。与此同时,我们想在开发游戏时乐在其中,所以选择了 Roguelike 结构。Roguelike 游戏的随机关卡生成意味着每次试玩都会有不一样的体验。鉴于 Roguelike 游戏需要很高的耐玩性,我们知道“音符表”方式无法满足《BPM》高达 30 小时的游戏时长要求。
为此,我们决定在《BPM》中加入一些程序化音乐,大多在快要战胜 BOSS 时以插播乐句的形式呈现。在打败 BOSS 之后,其会随着玩家操作逐渐增强。
协调玩法
《BPM》的玩法机制本质上是个每分钟 88 拍的 4/4 拍步进音序器。敌人可以请求在几拍的时间内发动攻击。他们通过查询步进音序器确认在某一拍发起攻击是否会导致环境过于嘈杂。
敌人告知步进音序器“我想在两个节拍内攻击玩家,迫使他们躲闪”。步进音序器回应“是”或“否”。步进音序器的响应基于这一拍上是否发起了太多攻击或者有没有别的敌人完全占用这一拍。通过这种方式,《BPM》的整个玩法机制都可以由步进音序器来控制。
玩家的玩法机制中也引入了这种音序器。事实上,玩家只能在每个半拍执行操作。比如,玩家可以每隔半拍射击、跳跃或施法。不过,每次只能做一个动作:换弹、躲闪、射击或施法(跳跃动作不受限制;试过跟节拍同步,但效果很不理想)。
从技术角度来说,主要难点在于确保知道音轨中的“节拍”何时发生。为此,我们在 Unreal Engine 内做了各种尝试,但是都没有办法让音频时钟和游戏时钟同步。除此之外,我们还希望在音轨之间过渡,确保不会因为采样缺失而产生噼啪噪声。
为此,我们选择了使用 Wwise 来解决了以下三个问题:
1. 保证音轨之间的流畅过渡。
2. 确保音乐合拍、音效可闻。
3. 让游戏的时钟与节拍同步。
过渡和效果
乔什•沙利文 (Josh Sullivan):我负责《BPM》的所有声音设计。我的声音制作/混制过程比较特别。我在视频制作方面有十多年的经验,所以在使用程序来处理要应用到《BPM》中的声音时,我选用了 Sony Vegas(视频剪辑软件)而非专门的音频剪辑套件。除了有个视频预览窗口,Vegas 其实跟 Sound Forge(Sony 的音频剪辑套件)差不了多少。
幸运的是,《BPM》的配乐为每分钟 88 拍。由于整个游戏中始终采用这一曲速,我可以轻松地将所有要合拍的音频序列剪辑成 88 bpm 的节拍音轨。比如,《BPM》中武器的换弹都是紧跟节拍的(给人一种类似《Baby Driver》的感觉)。为此,我将一条节拍音轨放到了 Vegas 时间线中,通过剪辑确保各个声音跟此节拍音轨步调一致。每个声音都会被调到这一曲速。不过,如果设置不同的曲速,这种方法便无法奏效。
在声音做好之后,只需把它们导入到 Wwise 中并在必要时为其提供定位数据便可。在必要的情况下,我可以对声音实例数加以限制。比如,急射小机枪就需要这样做,其每个四分音符都会射击。由于射击速度很快,混音有时会很嘈杂。为此,最好限制为同一时间最多只有一个急射小机枪射击声。随后,我调节了一下 General Settings(声部、音高等)。最后,我将声音设置到了与之对应的 Output Bus 上。对于像射击这样的操作,每种枪支都设有至少四个不同的声音。然后,我把它们全部放在了 Random Container 中。这样就可避免因为反复播放同一枪声而让玩家感到单调乏味。
之后,只需在 Wwise 中为对应的音频创建 Event 即可。不过,我并没有把 Event 搞得太复杂。其中一个用法是先停掉之前的声音再播放后面的声音。比如,在敌人发出呱噪声时(跟着节拍咕哝、吼叫)。在触发代表敌人痛苦的 Wwise Event 时,不仅会播放 "ouch" Random Container,还会把敌人的呱噪声切掉。
在 Wwise 中,我可以使用 Music Switch Container 和 Music Playlist Container 轻松实现乐曲之间的过渡,并借助时间设置来确保所有音乐都与节拍同步。
在游戏中,有些音乐不应与节拍同步,好比在跟 BOSS 决战的时候。在跟 BOSS 战斗时,不用时刻踩着节奏做动作;只要在音符上就可以射击,但每个音符都要无限循环,直到下一次扣动扳机射击。它们在技术上来说是音乐,但我在 Wwise 中将其当成了声音来处理,因为以 Wwise Event 的形式实现更容易。
为节奏动作游戏混音
山姆•霍顿 (Sam Houghton):在为《BPM》混音时,我的主要目标是让玩家感觉好像自己在指挥一个摇滚乐团。武器是混音中的主要乐器,为的是当玩家沉浸在游戏中节节获胜时为其提供巨大的成就感。相反,倘若没能把握好射击或换弹的节奏,便不会有声音响起,听起来让人感到挫败和沮丧。
与此同时,我还在跟乔•柯林森 (Joe Collinson) 一起创作音乐,所以为这些声音的编排留了一些空间。网上有很多人都说 OST 听起来很棒,在游戏中混入枪声后效果甚至更好。能得到玩家的认可,让我感到非常欣慰。毕竟,游戏配乐正是为了支撑玩法机制。只是跟很多其他类型的游戏相比,《BPM》在这一点上做得更鲜明。
早前,我确实尝试了在玩家做“合拍互动”时闪避音乐声道。然而,这种细微效果并不能增强成就感,甚至还有可能会让游戏失去生气。因此,我只在 Wwise 中稍微做了一些电平调节,来确保在音乐方面一切都很鲜明而有力。乔什•沙利文把所有声音都做得很好,所以可以非常轻松地对游戏进行混音。
让游戏的时钟与节拍同步
大卫•琼斯 (David Jones):说到让游戏的时钟与节拍同步,我觉得最好的做法是《Borderlands》的解决方案,即修改 Wwise 来强制 MIDI 调用中断游戏逻辑。在每一拍的结尾,我们可以请求获取其时的输入状态。
最好是每次在 Wwise 中调用节拍 Event 时马上轮询控制器输入。这种方式类似于传统采样器。在实现中将输入和音频紧密绑定在一起,判断玩家的输入是早是晚以及相差多久,确保输入和音频之间的同步尽可能精准。然后,拒绝那些跟音乐过于不合拍的输入。不过,这一解决方案对我们这样规模的团队来说并不可行。这种工作要有全职音频程序员协助,因为它会干扰 Unreal Engine 的整个输入系统,并且需要对 Wwise 进行修改。最终,我们决定采取不同的做法。
简便之法
我们的解决方案非常简单和便捷。具体来说就是针对音乐 Event 注册回调,并查找 EAkCallbackType::MusicSyncBeat。每次有来自 Music Switch Container 的音乐 Event,我们就会发现游戏时钟和音轨行进之间的偏差。如果该偏差大于 10 ms,则重新校准游戏时钟,并为所有相关角色调用 Event。
我们选用这种简单的校准方法是因为游戏玩法不需要很花哨。这样可确保敌人行为大致合拍。最多只有 10 ms 的偏差,比节奏测试窗口小得多。
不过对于玩家的输入,还有其他错误要考虑。玩家错误窗口为:
源自时钟校准的 10 ms + 源自帧时间的 [frametime] ms + 源自延迟渲染器的 [frametime] ms + 源自输入设备的 ? ms + 源自主机处理的 ? ms + 源自TV/音频输出处理的 ? ms。
这在有些系统上最终可能会产生巨大的偏差。这一偏差对每个用户来说都是非常不一样的。不过,还有更糟糕的问题:节奏 FPS 有个无解的难题 (Cursed Problem)。
在 2019 年的 GDC 演讲中,来自 Riot Games 的亚历克斯•杰斐 (Alex Jaffe) 将“无解的难题”定义为“根植于核心玩家承诺之间的冲突而无法解决的设计问题”。在《BPM》中,我们的玩家承诺是“玩家跟着节拍同步射击”和“子弹在扣动扳机时射出”。然而,两者是冲突的。要想解决这一问题,只能“以退为进”。
在像《Guitar Hero》这样的对拍游戏中,会依据通过校准控制器设定的延迟来对玩家输入施加偏置。因为音符没有任何因果效应,所以可以在测试时计入延迟。游戏会通过测试玩家之前是否做到了跟着节拍输入来对视频延迟加以补偿。游戏知道应当在何时压在音符上、实际在何时压在了音符上以及 TV 延迟有多长时间。所以,游戏会检查并确认是否在“当前时间 - 延迟时间”的窗口内。这可能不太好理解。在《Guitar Hero》中,可以看到音符在线以下会消失,过了线好像也能成功弹到音符。TV 有延迟,而且可以实时看到这一延迟。然而,这在 FPS 中是不可行的。所有动作都要压在点上。
在《BPM》中,我们假定用户的延迟小于 80 ms。倘若用户的延迟超过这个时间,在开机校准序列当中会检测到,并依据情况启用自动节奏功能。自动节奏功能会在玩家输入时一直将射击动作保持到下一拍。对于延迟小于 80 ms 的用户,如果射击的时机早了,我们会应用一定延迟,确保其发生在下一拍;倘若射击的时机晚了,会让该动作立即发生。
为了给玩家提供更好的游戏体验,《BPM》会容许某些不合拍的操作。有很多逻辑来定义什么是容许的、什么是不容许的。主要是为了使所有的输入配置都能顺利地发挥作用。我们希望能为玩家提供酣畅的射击体验,而不是制作一款严格意义上的节奏游戏。
最终,《BPM》因为将音乐和玩法紧密融合在一起而大获成功。在这当中,Wwise 帮助我们高效而精准地实现了自己的设想。
![]() David Jones | 程序 |
![]() Josh Sullivan | 声音 |
![]() Sam Houghton | 音乐 |
评论