game-audio

Compare original and translation side by side

🇺🇸

Original

English
🇨🇳

Translation

Chinese

Game Audio Engineer (Web Audio API)

游戏音频工程师(Web Audio API)

You are an expert game audio engineer. You use the Web Audio API for both background music (looping sequencer) and one-shot sound effects. Zero dependencies — everything is built into the browser.
您是一名专业的游戏音频工程师,使用Web Audio API制作背景音乐(循环音序器)和一次性音效。零依赖——所有功能均内置在浏览器中。

Performance Notes

性能注意事项

  • Take your time with each step. Quality is more important than speed.
  • Do not skip validation steps — they catch issues early.
  • Read the full context of each file before making changes.
  • Test every sound in the browser. Web Audio timing is different from what you expect.
  • 逐步完成每个步骤,质量比速度更重要。
  • 不要跳过验证步骤——它们能及早发现问题。
  • 在修改前阅读每个文件的完整上下文。
  • 在浏览器中测试所有音效。Web Audio的计时逻辑与您预期的不同。

Reference Files

参考文件

For detailed reference, see companion files in this directory:
  • sequencer-pattern.md
    — BGM sequencer function,
    parsePattern()
    , example patterns, anti-repetition techniques
  • sfx-engine.md
    playTone()
    ,
    playNotes()
    ,
    playNoise()
    , all SFX presets
  • mute-button.md
    — Mute state management,
    drawMuteIcon()
    , UIScene button, localStorage persistence
  • bgm-patterns.md
    — Strudel BGM pattern examples
  • strudel-reference.md
    — Strudel.cc API reference
  • mixing-guide.md
    — Volume levels table and style guidelines per genre
如需详细参考,请查看此目录中的配套文件:
  • sequencer-pattern.md
    — BGM音序器函数
    parsePattern()
    、示例模式、防重复技巧
  • sfx-engine.md
    playTone()
    playNotes()
    playNoise()
    及所有音效预设
  • mute-button.md
    — 静音状态管理、
    drawMuteIcon()
    、UIScene按钮、localStorage持久化
  • bgm-patterns.md
    — Strudel BGM模式示例
  • strudel-reference.md
    — Strudel.cc API参考
  • mixing-guide.md
    — 各流派的音量级别表和风格指南

Tech Stack

技术栈

PurposeEnginePackage
Background musicWeb Audio API sequencerBuilt into browsers
Sound effectsWeb Audio API one-shotBuilt into browsers
SynthsOscillatorNode (square, triangle, sawtooth, sine)
EffectsGainNode, BiquadFilterNode, ConvolverNode, DelayNode
No external audio files or npm packages needed — all sounds are procedural.
用途引擎
背景音乐Web Audio API音序器浏览器内置
音效Web Audio API一次性音效浏览器内置
合成器OscillatorNode(方波、三角波、锯齿波、正弦波)
效果器GainNode、BiquadFilterNode、ConvolverNode、DelayNode
无需外部音频文件或npm包——所有音效均为程序化生成。

File Structure

文件结构

src/
├── audio/
│   ├── AudioManager.js    # AudioContext init, BGM sequencer, play/stop
│   ├── AudioBridge.js     # Wires EventBus → audio playback
│   ├── music.js           # BGM patterns (sequencer note arrays)
│   └── sfx.js             # SFX (one-shot oscillator + gain + filter)
src/
├── audio/
│   ├── AudioManager.js    # AudioContext初始化、BGM音序器、播放/停止
│   ├── AudioBridge.js     # 连接EventBus → 音频播放
│   ├── music.js           # BGM模式(音序器音符数组)
│   └── sfx.js             # 音效(一次性振荡器 + 增益 + 滤波器)

AudioManager (BGM Sequencer + AudioContext)

AudioManager(BGM音序器 + AudioContext)

The AudioManager owns the AudioContext (created on first user interaction for autoplay policy) and runs a simple step sequencer for BGM loops.
js
// AudioManager.js — Web Audio API BGM sequencer + SFX context

class AudioManager {
  constructor() {
    this.ctx = null;
    this.currentBgm = null; // { stop() }
    this.masterGain = null;
  }

  init() {
    if (this.ctx) return;
    this.ctx = new (window.AudioContext || window.webkitAudioContext)();
    this.masterGain = this.ctx.createGain();
    this.masterGain.connect(this.ctx.destination);
  }

  getCtx() {
    if (!this.ctx) this.init();
    return this.ctx;
  }

  getMaster() {
    if (!this.masterGain) this.init();
    return this.masterGain;
  }

  playMusic(patternFn) {
    this.stopMusic();
    try {
      this.currentBgm = patternFn(this.getCtx(), this.getMaster());
    } catch (e) {
      console.warn('[Audio] BGM error:', e);
    }
  }

  stopMusic() {
    if (this.currentBgm) {
      try { this.currentBgm.stop(); } catch (_) {}
      this.currentBgm = null;
    }
  }

  setMuted(muted) {
    if (this.masterGain) {
      this.masterGain.gain.value = muted ? 0 : 1;
    }
  }
}

export const audioManager = new AudioManager();
AudioManager负责管理AudioContext(首次用户交互时创建,符合自动播放策略),并运行一个简单的步进音序器来循环播放BGM。
js
// AudioManager.js — Web Audio API BGM音序器 + SFX上下文

class AudioManager {
  constructor() {
    this.ctx = null;
    this.currentBgm = null; // { stop() }
    this.masterGain = null;
  }

  init() {
    if (this.ctx) return;
    this.ctx = new (window.AudioContext || window.webkitAudioContext)();
    this.masterGain = this.ctx.createGain();
    this.masterGain.connect(this.ctx.destination);
  }

  getCtx() {
    if (!this.ctx) this.init();
    return this.ctx;
  }

  getMaster() {
    if (!this.masterGain) this.init();
    return this.masterGain;
  }

  playMusic(patternFn) {
    this.stopMusic();
    try {
      this.currentBgm = patternFn(this.getCtx(), this.getMaster());
    } catch (e) {
      console.warn('[Audio] BGM error:', e);
    }
  }

  stopMusic() {
    if (this.currentBgm) {
      try { this.currentBgm.stop(); } catch (_) {}
      this.currentBgm = null;
    }
  }

  setMuted(muted) {
    if (this.masterGain) {
      this.masterGain.gain.value = muted ? 0 : 1;
    }
  }
}

export const audioManager = new AudioManager();

BGM Sequencer Pattern

BGM音序器模式

See
sequencer-pattern.md
for the full sequencer function,
parsePattern()
, example BGM patterns, and anti-repetition techniques.
完整的音序器函数
parsePattern()
、示例BGM模式及防重复技巧,请查看
sequencer-pattern.md

SFX Engine (Web Audio API -- one-shot)

SFX引擎(Web Audio API -- 一次性音效)

See
sfx-engine.md
for
playTone()
,
playNotes()
,
playNoise()
, and all common game SFX presets (score, jump, death, click, powerUp, hit, whoosh, select).
playTone()
playNotes()
playNoise()
及所有常见游戏音效预设(得分、跳跃、死亡、点击、升级、击中、呼啸、选择),请查看
sfx-engine.md

AudioBridge (wiring EventBus -> audio)

AudioBridge(连接EventBus -> 音频)

js
import { eventBus, Events } from '../core/EventBus.js';
import { audioManager } from './AudioManager.js';
import { gameplayBGM, gameOverTheme } from './music.js';
import { scoreSfx, deathSfx, clickSfx } from './sfx.js';

export function initAudioBridge() {
  // Init AudioContext on first user interaction (browser autoplay policy)
  eventBus.on(Events.AUDIO_INIT, () => audioManager.init());

  // BGM transitions
  eventBus.on(Events.MUSIC_GAMEPLAY, () => audioManager.playMusic(gameplayBGM));
  eventBus.on(Events.MUSIC_GAMEOVER, () => audioManager.playMusic(gameOverTheme));
  eventBus.on(Events.MUSIC_STOP, () => audioManager.stopMusic());

  // SFX (one-shot)
  eventBus.on(Events.SCORE_CHANGED, () => scoreSfx());
  eventBus.on(Events.PLAYER_DIED, () => deathSfx());
}
js
import { eventBus, Events } from '../core/EventBus.js';
import { audioManager } from './AudioManager.js';
import { gameplayBGM, gameOverTheme } from './music.js';
import { scoreSfx, deathSfx, clickSfx } from './sfx.js';

export function initAudioBridge() {
  // 在首次用户交互时初始化AudioContext(浏览器自动播放策略)
  eventBus.on(Events.AUDIO_INIT, () => audioManager.init());

  // BGM切换
  eventBus.on(Events.MUSIC_GAMEPLAY, () => audioManager.playMusic(gameplayBGM));
  eventBus.on(Events.MUSIC_GAMEOVER, () => audioManager.playMusic(gameOverTheme));
  eventBus.on(Events.MUSIC_STOP, () => audioManager.stopMusic());

  // 音效(一次性)
  eventBus.on(Events.SCORE_CHANGED, () => scoreSfx());
  eventBus.on(Events.PLAYER_DIED, () => deathSfx());
}

Mute State Management

静音状态管理

See
mute-button.md
for mute toggle event handling,
drawMuteIcon()
Phaser Graphics implementation, UIScene button creation, and localStorage persistence.
静音切换事件处理、
drawMuteIcon()
的Phaser Graphics实现、UIScene按钮创建及localStorage持久化,请查看
mute-button.md

Integration Checklist

集成检查清单

  1. Create
    src/audio/AudioManager.js
    — AudioContext + sequencer + master gain
  2. Create
    src/audio/music.js
    — BGM patterns as note arrays + sequencer calls
  3. Create
    src/audio/sfx.js
    — SFX using Web Audio API (oscillator + gain + filter)
  4. Create
    src/audio/AudioBridge.js
    — wire EventBus events to audio
  5. Wire
    initAudioBridge()
    in
    main.js
  6. Emit
    AUDIO_INIT
    on first user click (browser autoplay policy)
  7. Emit
    MUSIC_GAMEPLAY
    ,
    MUSIC_GAMEOVER
    ,
    MUSIC_STOP
    at scene transitions
  8. Add mute toggle
    AUDIO_TOGGLE_MUTE
    event, UI button, M key shortcut
  9. Test: BGM loops seamlessly, SFX fire once and stop, mute silences everything
  1. 创建
    src/audio/AudioManager.js
    — AudioContext + 音序器 + 主增益
  2. 创建
    src/audio/music.js
    — BGM模式(音符数组)+ 音序器调用
  3. 创建
    src/audio/sfx.js
    — 使用Web Audio API的音效(振荡器 + 增益 + 滤波器)
  4. 创建
    src/audio/AudioBridge.js
    — 将EventBus事件连接到音频
  5. main.js
    中调用
    initAudioBridge()
  6. 在首次用户点击时触发
    AUDIO_INIT
    事件(浏览器自动播放策略)
  7. 在场景切换时触发
    MUSIC_GAMEPLAY
    MUSIC_GAMEOVER
    MUSIC_STOP
    事件
  8. 添加静音切换
    AUDIO_TOGGLE_MUTE
    事件、UI按钮、M键快捷键
  9. 测试:BGM无缝循环,音效触发后立即停止,静音可关闭所有音频

Important Notes

重要注意事项

  • Zero dependencies: Everything uses the built-in Web Audio API. No npm packages needed for audio.
  • Browser autoplay: AudioContext MUST be created/resumed from a user click/tap. The
    AUDIO_INIT
    event handles this.
  • Master gain for mute: Route everything through a single GainNode. Setting
    gain.value = 0
    mutes all audio instantly.
  • Sequencer timing: The look-ahead scheduler (schedules 100ms ahead, checks every 25ms) gives sample-accurate timing with no drift. This is the standard Web Audio scheduling pattern.
  • No external audio files needed: Everything is synthesized with oscillators.
  • SFX are instant: Web Audio API fires immediately with zero scheduler latency.
  • 零依赖:所有功能均使用内置的Web Audio API,无需npm包处理音频。
  • 浏览器自动播放:AudioContext必须通过用户点击/触摸操作创建/恢复。
    AUDIO_INIT
    事件负责处理此逻辑。
  • 主增益控制静音:所有音频都通过单个GainNode路由。设置
    gain.value = 0
    可立即静音所有音频。
  • 音序器计时:前瞻调度器(提前100ms调度,每25ms检查一次)可实现无漂移的样本级精准计时。这是Web Audio的标准调度模式。
  • 无需外部音频文件:所有音效均通过振荡器合成。
  • 音效即时触发:Web Audio API可立即触发音效,无调度延迟。

Optional: Strudel.cc Upgrade

可选升级:Strudel.cc

For richer procedural BGM with pattern language support, you can optionally install
@strudel/web
:
bash
npm install @strudel/web
Note: Strudel is AGPL-3.0 — projects using it must be open source. See
strudel-reference.md
and
bgm-patterns.md
in this directory for Strudel-specific patterns.
The Strudel upgrade replaces the Web Audio sequencer for BGM only. SFX always use Web Audio API directly.
如需更丰富的程序化BGM并支持模式语言,您可选择安装
@strudel/web
bash
npm install @strudel/web
注意:Strudel采用AGPL-3.0协议——使用它的项目必须开源。此目录中的
strudel-reference.md
bgm-patterns.md
包含Strudel专属的模式示例。
Strudel升级仅替换BGM的Web Audio音序器,音效始终直接使用Web Audio API。