简介
今年早些时候,我发行了一张生成式氛围音乐专辑《Púrpura》。在本文中,我将探讨自己如何使用 Wwise 制作了这张专辑 – 从使用 Actor-Mixer Hierarchy 构建生成式音乐系统到使用 Unity 演奏音乐。
可能有些读者对相关概念并不熟悉,所以有必要在此简单介绍一下。所谓生成式音乐,就是通过让系统根据作曲家定义的一系列规则即兴创作并做不同的随机化处理来实时生成音乐。最主要的是,系统的规则可以规定哪些音符或样本能播放以及音符之间要间隔多长时间。如想了解更多相关信息,建议阅读布莱恩•埃诺 (Brian Eno) 的演讲文稿。
《Púrpura》的生成式系统
《Púrpura》中的所有乐曲都使用类似的系统生成。每首乐曲由四到五种乐器构成,每种乐器都包含随机播放的乐句库。对此,我在 Actor-Mixer Hierarchy 中做了相应设置:为每首乐曲创建一个 Actor-Mixer 父对象,并为父对象内的每种乐器创建一个 Random Container。
在下图中,我们可以看到乐曲《Rito》包含五种乐器:Bass、Cello、Flute、Granular Pad 和 Granular Organ。另外,还可看到 Granular Pad 总共包含七段随机播放的乐句。
图 1 -《Rito》的 Actor-Mixer Hierarchy
每个 Random Container 都设为连续播放和无限循环,过渡类型则设为 Delay。这样在播放 Random Container 时会随机选择并播放某一乐句。在该乐句结束后等待一定时间,然后随机选择并播放另一乐句 – 重复这一过程,直到要求停止。
图 2 - Random Container 设置
为了增添随机性,延迟时长也做了随机化处理。
图 3 - 对延迟时长做随机化处理
不知各位可曾使用 Wwise 在游戏中实现断续的环境声。这里的设置基本上是一样的。
在制作这张专辑的时候,我最关心的一点是让每首曲子的声音密度随着时间有机地变化,以便给音乐以足够的回转空间,同时又不至于陷入长久的沉默。要做到这一点,既要对 Wwise 中的数值做微调,也要对音乐素材本身反复推敲,确保乐曲编排全都与系统相配。
在 Wwise 中演奏这些乐曲时,只需同时播放各个 Random Container 并按照设定的时长运行即可。至于演奏的录制,则可在 DAW 中创建一条音轨,并将输入设为音频接口的输出 – 当然,要关闭监听以免产生反馈回路。我对每一首曲子都做了好几遍录音,最后将满意的曲子编入最终的专辑。以下是开场曲目,各位不妨听听组合起来的效果:
《Alva》:"Intensity" RTPC
专辑的前四首乐曲使用了与上述大体相同的系统,最后一首乐曲《Alva》则进一步使用了 RTPC 来控制力度随时间的变化。《Alva》完全由专辑前几首乐曲的样本制作而成。我对这些样本进行了修改和处理,并最终打造成了一个和谐的整体。另外,还使用了 Wwise 效果器来在整首乐曲当中动态地营造别样的质感。下面有个链接,各位可以听听:
跟其他乐曲相比,这首乐曲的设置稍有不同。首先,它使用 Interactive Music Hierarchy 循环播放 Cello 乐句,并以此为基础来通过 Actor-Mixer Hierarchy 演奏乐器。对此,Playlist Container 会先播放一次 Intro 乐句再转到 Loop 乐句。
图 4 - Music Playlist 设置
另外,Actor-Mixer Hierarchy 设置也有一些调整。这里有四种乐器:Sub-bass、Cello、Flute 和 Oboe;还有一个 Actor-Mixer 对象作为后三种乐器的父对象,方便跟 Sub-bass 分开处理。
图 5 -《Alva》的 Actor-Mixer Hierarchy
这首乐曲以 Interactive Music Hierarchy 中的 Cello 开始,然后使用 "Intensity" RTPC 逐一淡入 Actor-Mixer 乐器。以下是 Sub-bass 乐器的设置:
图 6 - "Intensity" RTPC:Voice Volume
Actor-Mixer Hierarchy 中的 Cello、Flute 和 Oboe 通过 Wwise Harmonizer 和 Wwise Guitar Distortion 效果器进行实时处理。"Intensity" RTPC 控制 Harmonizer 的 Dry Level 和 Wet Level 以及 Guitar Distortion 效果器的 Distortion Drive。以下是 Harmonizer 的 RTPC 曲线:
图 7 - "Intensity" RTPC:Harmonizer 效果器
Interactive Music Hierarchy 中的 Cello 也应用了这两种效果器并使用了大致相同的 RTPC 曲线。Sub-bass 也应用有自己的 Harmonizer 和 Guitar Distortion 效果器,其由 "Intensity" RTPC 控制并设为不同的值。此外,它还在所有使用 "Intensity" RTPC 的素材的最上层添加了 Wwise Tremolo 效果器来增加 LFO Frequency:
图 8 - "Intensity" RTPC:Tremolo 效果器
整张专辑将 Wwise Delay 和 Wwise RoomVerb 效果器作为 Master-Mixer Hierarchy 中的两条 Aux Bus,来确保所有声音具有连贯的空间感。在其他乐曲的 Aux Send Level 保持不变时,由《Alva》的 "Intensity" RTPC 控制 Actor-Mixer 乐器的 User-Defined Auxiliary Send Volume 并随着乐曲的行进逐渐增大。
最后是 Random Container 对象的设置。对此,我将 Flute、Oboe 和 Cello 设为了 Sequence Container 而非 Random Container,并将过渡类型设为了 Trigger Rate 而非 Delay。
图 9 - Sequence Container 设置
然后,使用 "Intensity" RTPC 控制 Trigger Rate,来让 Sequence Container 在乐曲行进时更快地触发各种乐器。
图 10 - "Intensity" RTPC:触发时长
在乐曲结束时,通过设置 Trigger Rate 来让 Sequence Container 每秒播放一段乐句,从而使各种乐器本身连续地叠合在一起。再加上所有效果器都由同一个 RTPC 控制,最终将原本独立的乐器变成协和的乐曲。
使用 Unity 动画曲线驱动 "Intensity" RTPC
在 Wwise 中设置《Alva》之后,还要设法随着音乐增大 "Intensity" RTPC 的值。事实证明,在录音时手动设置数值既麻烦又不可靠。在 Wwise 中将 RTPC 插值设为 Slew Rate 并不能带来我想要的微妙变化。为此,我将 Wwise 集成到了一个空白的 Unity 工程中并使用动画曲线来驱动 RTPC。
说是动画曲线,其实只是个定义特定时段(X 轴)内的值(Y 轴)的曲线图。以下是我为《Alva》设定用于驱动 "Intensity" RTPC 的曲线:
图 11 - 动画曲线图
为了把所有东西连接在一起,我编写了一小段 C# 脚本来将动画曲线的值传给 Wwise 中的 RTPC。在脚本中,我首先为 RTPC 动画曲线本身声明了变量,然后声明了另一变量来定义从 RTPC 的最小值到最大值需要多少秒。
图 12 - C# 脚本:公共变量
之所以将这些变量声明为公共变量,为的是方便在 Inspector 中进行设置。之后,可通过单击这里的图形符号来手动编辑动画曲线。
图 13 - C# 脚本:Inspector
如图 11 所示,曲线的 X 轴和 Y 轴的取值范围均被归一化为了 0 ~ 1。然后再将 X 轴缩放为所需的时长(270 秒),并将 Y 轴缩放为 Wwise 中定义的 RTPC 取值范围 (0 ~ 100)。对此,可通过下图所示的三行代码来实现。这三行代码在 Update 函数内运行,所以每一帧都会进行计算:
图 14 - C# 脚本:Update 函数
首先创建一个 timer 变量,在每帧通过 Time.deltaTime 递增,来计算从乐曲开始经过了多少秒。
然后,使用 timer 变量来随着时间的推移从曲线获取 Y 值。同时,使用 Evaluate 函数来在赋予 X 坐标作为参数时输出曲线图的 Y 值。接着,将 timer 变量作为参数传入,来在每帧递增 X 坐标的值。然后将其除以 duration 变量,使其从 0 到 1 需要 270 秒。
接着,缩放 Y 轴值以使其与 RTPC 的取值范围匹配。为此,我使用了 Mathf.Lerp 函数来基于 Y 轴值(通过 Evaluate 函数获取)在 0 ~ 100 之间做插值。之后,将计算结果写入到 rtpcValue 变量。
最后,使用 SetGlobalValue 函数将 rtpcValue 变量传给 Wwise。
结语
之所以制作《Púrpura》专辑,是为了将 Wwise 融入到作曲本身当中,并借助其创作音乐而不只是播放音乐。通常情况下,整合被认为是音乐创作完成之后才要做的事情。不过,我觉得将音频中间件纳入到创作中有助打造更加独特的互动体验。
有兴趣的话,可在 Bandcamp 和音乐流媒体上试听整张《Púrpura》专辑。
评论