# 画面設計書 25-WebAudioサンプル

## 概要

本ドキュメントは、three.js Examples における WebAudio API を使用した 3D オーディオ連携サンプル群（4件）の画面設計書である。Web Audio API と three.js の 3D シーンを連携させた空間オーディオやオーディオビジュアライザーのデモンストレーションを提供する。

### 本画面の処理概要

WebAudioサンプル画面は、three.js の Audio クラス群（Audio, PositionalAudio, AudioListener, AudioAnalyser）を使用した 3D オーディオの実装例を提供する。空間オーディオ（3D 空間内のオブジェクトからの音源）、オーディオビジュアライザー（音声の周波数データをシェーダーで可視化）、タイミング同期（オーディオタイムラインとアニメーションの同期）などを実装している。

**業務上の目的・背景**：ゲーム、VR/AR コンテンツ、音楽ビジュアライゼーションなど、オーディオと 3D グラフィックスを連携させたアプリケーション開発者に対して、実装例を提供する。Web Audio API のネイティブな機能と three.js の統合方法を学習できる。没入感のある体験を作成するための基礎技術を提供する。

**画面へのアクセス方法**：
1. examples/index.html にアクセス
2. 左側パネルの「webaudio」カテゴリを選択
3. 検索フィルタで「webaudio」を入力して絞り込み
4. 目的のサンプルを選択

**主要な操作・処理内容**：
1. AudioListener（リスナー）の設定とカメラへの追加
2. Audio または PositionalAudio（音源）の作成と配置
3. AudioLoader によるオーディオファイルの読み込み
4. AudioAnalyser による周波数データの取得
5. シェーダーによるオーディオビジュアライゼーション
6. ユーザー操作による再生開始（autoplay policy 対応）

**画面遷移**：
- 遷移元：Examples一覧画面（examples/index.html）
- 遷移先：なし（各サンプルは独立して動作）
- GitHub ソースコードページへの外部リンクあり

**権限による表示制御**：なし（パブリックアクセス）

## 関連機能

| 機能No | 機能名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| 118 | Audio | 主機能 | 3Dオーディオの再生 |
| 119 | AudioListener | 主機能 | リスナー位置の管理 |
| 120 | PositionalAudio | 補助機能 | 空間オーディオの配置 |
| 121 | AudioAnalyser | 補助機能 | オーディオ周波数解析 |
| 13 | WebGLRenderer | 補助機能 | レンダリング処理 |

## 画面種別

サンプル / デモンストレーション

## URL/ルーティング

- カテゴリ: `examples/index.html` (webaudio)
- 個別サンプル:
  - `examples/webaudio_orientation.html` - 空間オーディオ（オリエンテーション）
  - `examples/webaudio_sandbox.html` - オーディオサンドボックス
  - `examples/webaudio_timing.html` - タイミング同期
  - `examples/webaudio_visualizer.html` - オーディオビジュアライザー

## 入出力項目

| 項目名 | 入出力 | データ型 | 説明 |
|--------|--------|----------|------|
| オーディオファイル | 入力 | File (MP3/WAV等) | 再生するオーディオファイル |
| ユーザー操作 | 入力 | Event (click等) | 再生開始のトリガー |
| リスナー位置 | 入力 | Vector3 | カメラ位置に連動 |
| 音源位置 | 入力 | Vector3 | PositionalAudio の 3D 位置 |
| 周波数データ | 出力 | Uint8Array | AudioAnalyser から取得 |
| ビジュアライゼーション | 出力 | Canvas | 音声の可視化結果 |

## 表示項目

| 項目名 | 表示形式 | 説明 |
|--------|----------|------|
| 3Dシーン | Canvas | オーディオと連携した3Dレンダリング |
| 再生ボタン | HTML button | オーディオ再生開始用のUI |
| ビジュアライザー | Canvas/Shader | 周波数データの可視化 |
| 情報パネル | HTML div | サンプル説明、操作ガイド |

## イベント仕様

### 1-オーディオ初期化

ユーザー操作（クリック等）後にオーディオを初期化：
1. AudioListener を作成してカメラに追加
2. Audio または PositionalAudio を作成
3. AudioLoader でオーディオファイルを読み込み
4. setBuffer() でオーディオバッファを設定
5. play() で再生開始

### 2-空間オーディオ更新

毎フレームの処理：
1. カメラ位置の更新（AudioListener の位置も自動更新）
2. PositionalAudio のオブジェクトの位置更新
3. Web Audio API が自動的にパンニングと減衰を計算

### 3-ビジュアライザー更新

毎フレームの処理：
1. AudioAnalyser.getFrequencyData() で周波数データを取得
2. DataTexture を更新（needsUpdate = true）
3. シェーダーが周波数データをサンプリングして描画

### 4-iOS 対応

iOS デバイスでの再生対応：
1. HTMLMediaElement を使用（AudioLoader の代わり）
2. setMediaElementSource() で Audio に接続
3. ユーザー操作後に mediaElement.play() を呼び出し

## データベース更新仕様

### 操作別データベース影響一覧

本画面はフロントエンドのみで動作するサンプルであり、データベースへのアクセスは行わない。

| 操作（イベント） | 対象テーブル | 操作種別 | 概要 |
|----------------|-------------|---------|------|
| - | - | - | データベース操作なし |

## メッセージ仕様

| 種別 | メッセージ | 発生条件 |
|------|-----------|----------|
| 情報 | "Play" ボタン表示 | 初期状態、オーディオ再生待ち |
| エラー | コンソールエラー | オーディオファイル読み込み失敗 |
| 警告 | Autoplay blocked | ユーザー操作なしで再生試行時 |

## 例外処理

| 例外状況 | 処理内容 |
|----------|----------|
| Autoplay policy による再生ブロック | Play ボタンを表示、ユーザー操作を待機 |
| オーディオファイル読み込み失敗 | エラーログ出力、代替音源の検討 |
| Web Audio API 非対応 | エラーメッセージ表示 |

## 備考

- ブラウザの Autoplay policy により、ユーザー操作後にのみ再生可能
- iOS では HTMLMediaElement を使用する必要がある場合がある
- PositionalAudio は refDistance, rolloffFactor で減衰を制御
- AudioAnalyser の fftSize でビジュアライゼーションの解像度を設定

---

## コードリーディングガイド

本画面を理解するために参照すべきファイルと、推奨する読み解き順序を以下に示す。

### 推奨読解順序

#### Step 1: データ構造を理解する

three.js の Audio 関連クラスの構造を理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | AudioListener.js | `src/audio/AudioListener.js` | リスナーの位置・向きの管理 |
| 1-2 | Audio.js | `src/audio/Audio.js` | 基本的なオーディオ再生 |
| 1-3 | PositionalAudio.js | `src/audio/PositionalAudio.js` | 空間オーディオ |
| 1-4 | AudioAnalyser.js | `src/audio/AudioAnalyser.js` | 周波数解析 |

**読解のコツ**: AudioListener をカメラに追加し、Audio/PositionalAudio を Scene または Object3D に追加する。Web Audio API の AudioContext は内部で管理される。

#### Step 2: エントリーポイントを理解する

ビジュアライザーサンプルの構造を理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | webaudio_visualizer.html | `examples/webaudio_visualizer.html` | ビジュアライザーの実装 |

**主要処理フロー**:
1. **Line 9-41**: カスタムシェーダー（vertex/fragment）の定義
2. **Line 69-70**: Play ボタンのイベントハンドラ設定
3. **Line 72-150**: init() 関数
4. **Line 91-93**: AudioListener の作成
5. **Line 94-113**: Audio の作成と読み込み（iOS 対応を含む）
6. **Line 115**: AudioAnalyser の作成（fftSize: 128）
7. **Line 119-121**: DataTexture の作成（周波数データ用）
8. **Line 125-131**: ShaderMaterial の作成（周波数データをサンプリング）
9. **Line 158-165**: animate() 関数（周波数データの更新）

#### Step 3: シェーダーを理解する

ビジュアライザーのシェーダー処理を理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | webaudio_visualizer.html (shader) | `examples/webaudio_visualizer.html` (Line 23-39) | フラグメントシェーダー |

**主要処理フロー**:
- **texture2D(tAudioData, vec2(vUv.x, 0.0)).r**: X座標に対応する周波数の振幅を取得
- **step(vUv.y, f)**: 振幅以下の領域を描画
- **step(f - 0.0125, vUv.y)**: ライン表示のための処理

#### Step 4: 空間オーディオを理解する

空間オーディオの実装を理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 4-1 | webaudio_orientation.html | `examples/webaudio_orientation.html` | 空間オーディオサンプル |

**主要処理フロー**:
- PositionalAudio を 3D オブジェクトに追加
- カメラの移動に伴いパンニングと減衰が変化
- setRefDistance(), setRolloffFactor() で減衰特性を設定

### プログラム呼び出し階層図

```
webaudio_visualizer.html (エントリーポイント)
    |
    +-- startButton.click()
    |      +-- overlay.remove()
    |      +-- init()
    |
    +-- init()
    |      |
    |      +-- THREE.AudioListener()
    |      |      +-- camera.add(listener)
    |      |
    |      +-- THREE.Audio(listener)
    |      |      +-- AudioLoader.load() または
    |      |      +-- setMediaElementSource() [iOS]
    |      |      +-- play()
    |      |
    |      +-- THREE.AudioAnalyser(audio, fftSize)
    |      |      +-- getFrequencyData() [毎フレーム]
    |      |
    |      +-- THREE.DataTexture(analyser.data, ...)
    |      |      +-- needsUpdate = true [毎フレーム]
    |      |
    |      +-- THREE.ShaderMaterial({ uniforms: { tAudioData } })
    |      |
    |      +-- THREE.Mesh(PlaneGeometry, ShaderMaterial)
    |             +-- scene.add()
    |
    +-- animate()
           +-- analyser.getFrequencyData()
           +-- uniforms.tAudioData.value.needsUpdate = true
           +-- renderer.render(scene, camera)
```

### データフロー図

```
[オーディオビジュアライザーのデータフロー]

Audio File ────────> AudioLoader ────────> Audio Buffer
                          |
                          v
              Audio.setBuffer() + play()
                          |
                          v
              AudioAnalyser.getFrequencyData()
                          |
                          v
              Uint8Array (周波数データ)
                          |
                          v
              DataTexture (needsUpdate = true)
                          |
                          v
              ShaderMaterial (uniform: tAudioData)
                          |
                          v
              Fragment Shader (texture2D でサンプリング)
                          |
                          v
              Canvas (ビジュアライゼーション)
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| AudioListener.js | `src/audio/AudioListener.js` | ソース | リスナー管理 |
| Audio.js | `src/audio/Audio.js` | ソース | オーディオ再生 |
| PositionalAudio.js | `src/audio/PositionalAudio.js` | ソース | 空間オーディオ |
| AudioAnalyser.js | `src/audio/AudioAnalyser.js` | ソース | 周波数解析 |
| AudioLoader.js | `src/loaders/AudioLoader.js` | ソース | オーディオ読み込み |
| webaudio_orientation.html | `examples/webaudio_orientation.html` | テンプレート | 空間オーディオサンプル |
| webaudio_sandbox.html | `examples/webaudio_sandbox.html` | テンプレート | オーディオサンドボックス |
| webaudio_timing.html | `examples/webaudio_timing.html` | テンプレート | タイミング同期 |
| webaudio_visualizer.html | `examples/webaudio_visualizer.html` | テンプレート | ビジュアライザー |
| 376737_Skullbeatz___Bad_Cat_Maste.mp3 | `examples/sounds/` | リソース | サンプルオーディオ |
