声音与氛围
Assets/
Scenes/
Arena.unity
Scripts/
Prefabs/
Animations/
Audio/
你已经有的这一课新增
除了你在 tab 01 里加的音乐和按键音,你做到现在的所有东西都是静音的。Knight 走路没有脚步声,放技能没有声音,森林里也没有风声。
随便挑一个游戏把声音关掉,它立刻就显得很廉价。氛围感有一半来自声音,而新手往往把这一整半完全跳过。
三个层级、一个 mixer,凡是世界里占一个位置的音都用 3D 衰减。
三个音频层
Music —— 一条循环音轨,2D,音量不随距离变化。Spatial Blend 设为 0。
Ambience —— 风声、鸟叫、河流。铺满全局的底用 2D,某处具体的瀑布用 3D。
SFX —— 脚步声、打击、放技能。一律 3D,一律很短,一律做成池复用。
导入设置决定你的内存预算
- 1
音乐和很长的环境音 → Load Type = Streaming,Compression = Vorbis,Quality 60–70%。
- 2
短 SFX → Load Type = Decompress On Load,Compression = PCM 或 ADPCM。它们必须一调用就立刻出声。
- 3
凡是场景第一秒用不到的,都把 Preload Audio Data 的勾去掉。
- 4
所有 3D 声音都勾上 Force To Mono —— 反正 Unity 要自己算方位,立体声没意义,而且体积能省一半。
Audio Mixer —— 每个层一根音量滑块
- 1
→ 新建一个名为 MainMixer 的 mixer。
- 2
在 Master 下面加三个 group:Music、Ambience、SFX。
- 3
右键每个 group 的 Volume → Expose to script,再把参数名改成 MusicVol、AmbienceVol、SfxVol。
- 4
把每个 AudioSource 的 Output 指到对应的 group。这样一根滑块就能控制一整类声音。
using UnityEngine;
using UnityEngine.Audio;
public class GameAudioSettings : MonoBehaviour
{
[SerializeField] private AudioMixer mixer;
/// slider gives 0..1, the mixer wants decibels
public void SetMusic(float value01) => SetVolume("MusicVol", value01);
public void SetAmbience(float value01) => SetVolume("AmbienceVol", value01);
public void SetSfx(float value01) => SetVolume("SfxVol", value01);
void SetVolume(string param, float value01)
{
// -80 dB is silence. Log10 makes the slider feel linear to the ear.
float db = value01 <= 0.0001f ? -80f : Mathf.Log10(value01) * 20f;
mixer.SetFloat(param, db);
PlayerPrefs.SetFloat(param, value01);
}
void Start()
{
SetMusic(PlayerPrefs.GetFloat("MusicVol", 0.6f));
SetAmbience(PlayerPrefs.GetFloat("AmbienceVol", 0.8f));
SetSfx(PlayerPrefs.GetFloat("SfxVol", 1f));
}
}听起来真的像 3D 的声音
Spatial Blend = 1 把音源变成完全的 3D;为 0 时站在哪儿听着都一样响。
Volume Rolloff 用 Linear 比 Logarithmic 好调,小关卡尤其如此。
Min Distance 是还能保持满音量的半径,Max Distance 是完全听不到的距离。常用值:2 m 和 20 m。
场景里必须恰好只有一个 AudioListener,而且它应该挂在相机上。
听起来不像机关枪的脚步声
using UnityEngine;
public class FootstepPlayer : MonoBehaviour
{
[SerializeField] private AudioSource source;
[SerializeField] private AudioClip[] clips; // 4–6 variations
private int last = -1;
/// called from an Animation Event on the walk / run clips
public void Step()
{
if (clips.Length == 0) return;
// never play the same clip twice in a row
int i = Random.Range(0, clips.Length);
if (clips.Length > 1 && i == last) i = (i + 1) % clips.Length;
last = i;
source.pitch = Random.Range(0.92f, 1.08f); // tiny pitch jitter
source.PlayOneShot(clips[i], Random.Range(0.8f, 1f));
}
}四个采样再加随机音高,就是“一个游戏”和“一个半成品”之间的差别。这只花十分钟。
PlayOneShot 能让声音叠着放;source.Play() 会把上一个直接掐断。
用 Animation Event 才能把脚步声正好落在脚落地那一帧 —— 拿计时器去触发永远对不上。
去哪里找音效
freesound.org —— 量大、免费,但每个文件都要看它的许可证(CC0 最保险)。
Unity Asset Store 里有免费的音效包;按价格 0 过滤就行。
用手机自己录也行。碎石路上的脚步声、门、键盘 —— 效果比你想的好得多。
绝对不要把从 YouTube 上找来的音乐发出去。在应用商店吃版权投诉,整个应用都会被下架。