@craf-te/canvas-buffer-viewer 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.ja.md ADDED
@@ -0,0 +1,261 @@
1
+ # Canvas Buffer Viewer
2
+
3
+ WebGLフレームバッファ、レンダーターゲット、Canvas2Dの内容をリアルタイムで可視化する軽量デバッグツールです。複雑なレンダリングパイプラインやポストプロセスエフェクトのデバッグに最適です。
4
+
5
+ ![License](https://img.shields.io/badge/license-MIT-blue.svg)
6
+
7
+ ## 特徴
8
+
9
+ - フレームバッファとレンダーターゲットをサムネイルオーバーレイとして**リアルタイム表示**
10
+ - パフォーマンスへの影響を最小限に抑える**FPSスロットリング**
11
+ - **マルチフレームワーク対応**: Three.js、生WebGL、Canvas2D
12
+ - WebGLの下から上へのピクセル順序を**自動フリップ処理**
13
+ - **カスタマイズ可能な配置位置**(左上、右上、左下、右下)
14
+ - **依存関係なし** - Three.jsはオプションでヘルパー使用時のみ必要
15
+ - **Web Components ベース** - Shadow DOMによるカプセル化されたUI
16
+
17
+ ## インストール
18
+
19
+ ```bash
20
+ npm install canvas-buffer-viewer
21
+ ```
22
+
23
+ ## クイックスタート
24
+
25
+ ### 基本的な使い方
26
+
27
+ ```typescript
28
+ import { BufferViewer } from 'canvas-buffer-viewer';
29
+
30
+ // シングルトンインスタンスを取得
31
+ const viewer = BufferViewer.getInstance({
32
+ fps: 10, // キャプチャレート(デフォルト: 10)
33
+ corner: 'top-right', // 表示位置(デフォルト: 'top-right')
34
+ active: true // 起動時にアクティブ(デフォルト: true)
35
+ });
36
+
37
+ // レンダーループ内でバッファをキャプチャ
38
+ viewer.capture('My Buffer', () => ({
39
+ data: pixelData, // RGBA ピクセルの Uint8Array
40
+ width: 512,
41
+ height: 512,
42
+ flipY: true // WebGLはtrue(デフォルト)、Canvas2Dはfalse
43
+ }));
44
+ ```
45
+
46
+ ### Three.js との連携
47
+
48
+ ```typescript
49
+ import { BufferViewer, readRenderTarget } from 'canvas-buffer-viewer';
50
+ import * as THREE from 'three';
51
+
52
+ const renderer = new THREE.WebGLRenderer();
53
+ const renderTarget = new THREE.WebGLRenderTarget(512, 512);
54
+ const viewer = BufferViewer.getInstance({ fps: 20 });
55
+
56
+ function animate() {
57
+ // ターゲットにレンダリング
58
+ renderer.setRenderTarget(renderTarget);
59
+ renderer.render(scene, camera);
60
+
61
+ // 可視化用にキャプチャ
62
+ viewer.capture('Scene RT', () => readRenderTarget(renderer, renderTarget));
63
+
64
+ // 画面にレンダリング
65
+ renderer.setRenderTarget(null);
66
+ renderer.render(scene, camera);
67
+
68
+ requestAnimationFrame(animate);
69
+ }
70
+ ```
71
+
72
+ ### 生 WebGL
73
+
74
+ ```typescript
75
+ import { BufferViewer, readPixels } from 'canvas-buffer-viewer';
76
+
77
+ const canvas = document.createElement('canvas');
78
+ const gl = canvas.getContext('webgl2');
79
+ const viewer = BufferViewer.getInstance();
80
+
81
+ function render() {
82
+ // ... WebGL レンダリングコード ...
83
+
84
+ // 現在のフレームバッファをキャプチャ
85
+ viewer.capture('Main FB', () => readPixels(gl));
86
+
87
+ // または特定のフレームバッファをキャプチャ
88
+ viewer.capture('Shadow Map', () => readPixels(gl, shadowFramebuffer));
89
+
90
+ requestAnimationFrame(render);
91
+ }
92
+ ```
93
+
94
+ ### Canvas2D
95
+
96
+ ```typescript
97
+ import { BufferViewer, readCanvas } from 'canvas-buffer-viewer';
98
+
99
+ const canvas = document.createElement('canvas');
100
+ const ctx = canvas.getContext('2d');
101
+ const viewer = BufferViewer.getInstance();
102
+
103
+ function render() {
104
+ // ... Canvas2D 描画コード ...
105
+
106
+ // キャンバスの内容をキャプチャ
107
+ viewer.capture('2D Canvas', () => readCanvas(canvas));
108
+ // またはコンテキストを直接渡す
109
+ viewer.capture('2D Canvas', () => readCanvas(ctx));
110
+
111
+ requestAnimationFrame(render);
112
+ }
113
+ ```
114
+
115
+ ## API リファレンス
116
+
117
+ ### `BufferViewer`
118
+
119
+ バッファ可視化を管理するメインクラス。シングルトンパターンを使用。
120
+
121
+ #### `BufferViewer.getInstance(options?)`
122
+
123
+ シングルトンインスタンスを返す。必要に応じて作成。
124
+
125
+ ```typescript
126
+ interface ViewerOptions {
127
+ active?: boolean; // 起動時にアクティブ(デフォルト: true)
128
+ fps?: number; // キャプチャレート制限(デフォルト: 10)
129
+ corner?: Corner; // 'top-left' | 'top-right' | 'bottom-left' | 'bottom-right'
130
+ }
131
+ ```
132
+
133
+ #### `viewer.capture(label, getData, note?)`
134
+
135
+ バッファデータをキャプチャして表示。
136
+
137
+ - `label`: このバッファスロットの一意の識別子
138
+ - `getData`: `CaptureData` を返すコールバック(FPSスロットルが許可した時のみ呼び出される)
139
+ - `note`: ラベルの下に表示されるオプションの説明テキスト
140
+
141
+ ```typescript
142
+ interface CaptureData {
143
+ data: Uint8Array; // RGBA ピクセルデータ
144
+ width?: number; // 初回キャプチャ時は必須
145
+ height?: number; // 初回キャプチャ時は必須
146
+ flipY?: boolean; // WebGLはtrue(デフォルト)、Canvas2Dはfalse
147
+ }
148
+ ```
149
+
150
+ #### `viewer.active`
151
+
152
+ アクティブ状態の取得・設定。非アクティブ時はキャプチャがスキップされ、オーバーレイが非表示になる。
153
+
154
+ ```typescript
155
+ viewer.active = false; // ビューアを非表示
156
+ viewer.active = true; // ビューアを表示
157
+ ```
158
+
159
+ #### `viewer.toggle()`
160
+
161
+ ビューアのオン/オフを切り替え。
162
+
163
+ #### `viewer.setFps(fps)`
164
+
165
+ キャプチャレート制限を変更。
166
+
167
+ #### `viewer.removeBuffer(label)`
168
+
169
+ 特定のバッファを表示から削除。
170
+
171
+ #### `viewer.dispose()`
172
+
173
+ 全リソースをクリーンアップしてオーバーレイを削除。
174
+
175
+ ### ヘルパー関数
176
+
177
+ #### `readRenderTarget(renderer, renderTarget)`
178
+
179
+ Three.js の `WebGLRenderTarget` からピクセルを読み取る。
180
+
181
+ ```typescript
182
+ import { readRenderTarget } from 'canvas-buffer-viewer';
183
+
184
+ viewer.capture('RT', () => readRenderTarget(renderer, myRenderTarget));
185
+ ```
186
+
187
+ #### `readPixels(gl, framebuffer?)`
188
+
189
+ WebGL コンテキストからピクセルを読み取る。`framebuffer` を省略すると現在のバインディングから読み取る。
190
+
191
+ ```typescript
192
+ import { readPixels } from 'canvas-buffer-viewer';
193
+
194
+ // 現在のフレームバッファから読み取り
195
+ viewer.capture('Current', () => readPixels(gl));
196
+
197
+ // 特定のフレームバッファから読み取り
198
+ viewer.capture('Shadow', () => readPixels(gl, shadowFBO));
199
+ ```
200
+
201
+ #### `readCanvas(source)`
202
+
203
+ Canvas2D コンテキストまたはキャンバス要素からピクセルを読み取る。
204
+
205
+ ```typescript
206
+ import { readCanvas } from 'canvas-buffer-viewer';
207
+
208
+ viewer.capture('Canvas', () => readCanvas(canvas));
209
+ viewer.capture('Canvas', () => readCanvas(ctx));
210
+ ```
211
+
212
+ ## ポストプロセスパイプラインのデバッグ
213
+
214
+ マルチパスレンダリングのデバッグは一般的なユースケースです:
215
+
216
+ ```typescript
217
+ import { BufferViewer, readRenderTarget } from 'canvas-buffer-viewer';
218
+
219
+ const viewer = BufferViewer.getInstance({ fps: 15 });
220
+
221
+ function render() {
222
+ // パス1: シーン
223
+ renderer.setRenderTarget(sceneRT);
224
+ renderer.render(scene, camera);
225
+ viewer.capture('Scene', () => readRenderTarget(renderer, sceneRT), 'ベースシーンレンダー');
226
+
227
+ // パス2: ブルームしきい値
228
+ renderer.setRenderTarget(bloomRT);
229
+ renderer.render(bloomScene, postCamera);
230
+ viewer.capture('Bloom', () => readRenderTarget(renderer, bloomRT), '明部抽出');
231
+
232
+ // パス3: ブラー
233
+ renderer.setRenderTarget(blurRT);
234
+ renderer.render(blurScene, postCamera);
235
+ viewer.capture('Blur', () => readRenderTarget(renderer, blurRT));
236
+
237
+ // 最終合成
238
+ renderer.setRenderTarget(null);
239
+ renderer.render(compositeScene, postCamera);
240
+
241
+ requestAnimationFrame(render);
242
+ }
243
+ ```
244
+
245
+ ## キーボードショートカットの例
246
+
247
+ 便利なトグルショートカットを追加:
248
+
249
+ ```typescript
250
+ const viewer = BufferViewer.getInstance({ active: false });
251
+
252
+ window.addEventListener('keydown', (e) => {
253
+ if (e.key === 'F2') {
254
+ viewer.toggle();
255
+ }
256
+ });
257
+ ```
258
+
259
+ ## ライセンス
260
+
261
+ MIT
package/README.md ADDED
@@ -0,0 +1,261 @@
1
+ # Canvas Buffer Viewer
2
+
3
+ A lightweight debug tool for visualizing WebGL framebuffers, render targets, and Canvas2D contents in real-time. Perfect for debugging complex rendering pipelines and post-processing effects.
4
+
5
+ ![License](https://img.shields.io/badge/license-MIT-blue.svg)
6
+
7
+ ## Features
8
+
9
+ - **Real-time visualization** of framebuffers and render targets as thumbnail overlays
10
+ - **FPS throttling** to minimize performance impact during debugging
11
+ - **Multi-framework support**: Three.js, raw WebGL, and Canvas2D
12
+ - **Automatic flip handling** for WebGL's bottom-to-top pixel order
13
+ - **Customizable positioning** (top-left, top-right, bottom-left, bottom-right)
14
+ - **Zero dependencies** - Three.js is optional and only needed for Three.js helpers
15
+ - **Web Components based** - encapsulated UI with Shadow DOM
16
+
17
+ ## Installation
18
+
19
+ ```bash
20
+ npm install canvas-buffer-viewer
21
+ ```
22
+
23
+ ## Quick Start
24
+
25
+ ### Basic Usage
26
+
27
+ ```typescript
28
+ import { BufferViewer } from 'canvas-buffer-viewer';
29
+
30
+ // Get the singleton instance
31
+ const viewer = BufferViewer.getInstance({
32
+ fps: 10, // Capture rate (default: 10)
33
+ corner: 'top-right', // Position (default: 'top-right')
34
+ active: true // Start active (default: true)
35
+ });
36
+
37
+ // In your render loop, capture buffers
38
+ viewer.capture('My Buffer', () => ({
39
+ data: pixelData, // Uint8Array of RGBA pixels
40
+ width: 512,
41
+ height: 512,
42
+ flipY: true // true for WebGL (default), false for Canvas2D
43
+ }));
44
+ ```
45
+
46
+ ### Three.js Integration
47
+
48
+ ```typescript
49
+ import { BufferViewer, readRenderTarget } from 'canvas-buffer-viewer';
50
+ import * as THREE from 'three';
51
+
52
+ const renderer = new THREE.WebGLRenderer();
53
+ const renderTarget = new THREE.WebGLRenderTarget(512, 512);
54
+ const viewer = BufferViewer.getInstance({ fps: 20 });
55
+
56
+ function animate() {
57
+ // Render to target
58
+ renderer.setRenderTarget(renderTarget);
59
+ renderer.render(scene, camera);
60
+
61
+ // Capture for visualization
62
+ viewer.capture('Scene RT', () => readRenderTarget(renderer, renderTarget));
63
+
64
+ // Render to screen
65
+ renderer.setRenderTarget(null);
66
+ renderer.render(scene, camera);
67
+
68
+ requestAnimationFrame(animate);
69
+ }
70
+ ```
71
+
72
+ ### Raw WebGL
73
+
74
+ ```typescript
75
+ import { BufferViewer, readPixels } from 'canvas-buffer-viewer';
76
+
77
+ const canvas = document.createElement('canvas');
78
+ const gl = canvas.getContext('webgl2');
79
+ const viewer = BufferViewer.getInstance();
80
+
81
+ function render() {
82
+ // ... your WebGL rendering code ...
83
+
84
+ // Capture the current framebuffer
85
+ viewer.capture('Main FB', () => readPixels(gl));
86
+
87
+ // Or capture a specific framebuffer
88
+ viewer.capture('Shadow Map', () => readPixels(gl, shadowFramebuffer));
89
+
90
+ requestAnimationFrame(render);
91
+ }
92
+ ```
93
+
94
+ ### Canvas2D
95
+
96
+ ```typescript
97
+ import { BufferViewer, readCanvas } from 'canvas-buffer-viewer';
98
+
99
+ const canvas = document.createElement('canvas');
100
+ const ctx = canvas.getContext('2d');
101
+ const viewer = BufferViewer.getInstance();
102
+
103
+ function render() {
104
+ // ... your Canvas2D drawing code ...
105
+
106
+ // Capture the canvas contents
107
+ viewer.capture('2D Canvas', () => readCanvas(canvas));
108
+ // Or pass the context directly
109
+ viewer.capture('2D Canvas', () => readCanvas(ctx));
110
+
111
+ requestAnimationFrame(render);
112
+ }
113
+ ```
114
+
115
+ ## API Reference
116
+
117
+ ### `BufferViewer`
118
+
119
+ The main class for managing buffer visualization. Uses the singleton pattern.
120
+
121
+ #### `BufferViewer.getInstance(options?)`
122
+
123
+ Returns the singleton instance, creating it if necessary.
124
+
125
+ ```typescript
126
+ interface ViewerOptions {
127
+ active?: boolean; // Start active (default: true)
128
+ fps?: number; // Capture rate limit (default: 10)
129
+ corner?: Corner; // 'top-left' | 'top-right' | 'bottom-left' | 'bottom-right'
130
+ }
131
+ ```
132
+
133
+ #### `viewer.capture(label, getData, note?)`
134
+
135
+ Capture and display buffer data.
136
+
137
+ - `label`: Unique identifier for this buffer slot
138
+ - `getData`: Callback returning `CaptureData` (only called when FPS throttle allows)
139
+ - `note`: Optional description text displayed below the label
140
+
141
+ ```typescript
142
+ interface CaptureData {
143
+ data: Uint8Array; // RGBA pixel data
144
+ width?: number; // Required on first capture
145
+ height?: number; // Required on first capture
146
+ flipY?: boolean; // true for WebGL (default), false for Canvas2D
147
+ }
148
+ ```
149
+
150
+ #### `viewer.active`
151
+
152
+ Get or set the active state. When inactive, captures are skipped and the overlay is hidden.
153
+
154
+ ```typescript
155
+ viewer.active = false; // Hide the viewer
156
+ viewer.active = true; // Show the viewer
157
+ ```
158
+
159
+ #### `viewer.toggle()`
160
+
161
+ Toggle the viewer on/off.
162
+
163
+ #### `viewer.setFps(fps)`
164
+
165
+ Change the capture rate limit.
166
+
167
+ #### `viewer.removeBuffer(label)`
168
+
169
+ Remove a specific buffer from the display.
170
+
171
+ #### `viewer.dispose()`
172
+
173
+ Clean up all resources and remove the overlay.
174
+
175
+ ### Helper Functions
176
+
177
+ #### `readRenderTarget(renderer, renderTarget)`
178
+
179
+ Read pixels from a Three.js `WebGLRenderTarget`.
180
+
181
+ ```typescript
182
+ import { readRenderTarget } from 'canvas-buffer-viewer';
183
+
184
+ viewer.capture('RT', () => readRenderTarget(renderer, myRenderTarget));
185
+ ```
186
+
187
+ #### `readPixels(gl, framebuffer?)`
188
+
189
+ Read pixels from a WebGL context. If `framebuffer` is omitted, reads from the current binding.
190
+
191
+ ```typescript
192
+ import { readPixels } from 'canvas-buffer-viewer';
193
+
194
+ // Read from current framebuffer
195
+ viewer.capture('Current', () => readPixels(gl));
196
+
197
+ // Read from specific framebuffer
198
+ viewer.capture('Shadow', () => readPixels(gl, shadowFBO));
199
+ ```
200
+
201
+ #### `readCanvas(source)`
202
+
203
+ Read pixels from a Canvas2D context or canvas element.
204
+
205
+ ```typescript
206
+ import { readCanvas } from 'canvas-buffer-viewer';
207
+
208
+ viewer.capture('Canvas', () => readCanvas(canvas));
209
+ viewer.capture('Canvas', () => readCanvas(ctx));
210
+ ```
211
+
212
+ ## Debugging Post-Processing Pipelines
213
+
214
+ A common use case is debugging multi-pass rendering:
215
+
216
+ ```typescript
217
+ import { BufferViewer, readRenderTarget } from 'canvas-buffer-viewer';
218
+
219
+ const viewer = BufferViewer.getInstance({ fps: 15 });
220
+
221
+ function render() {
222
+ // Pass 1: Scene
223
+ renderer.setRenderTarget(sceneRT);
224
+ renderer.render(scene, camera);
225
+ viewer.capture('Scene', () => readRenderTarget(renderer, sceneRT), 'Base scene render');
226
+
227
+ // Pass 2: Bloom threshold
228
+ renderer.setRenderTarget(bloomRT);
229
+ renderer.render(bloomScene, postCamera);
230
+ viewer.capture('Bloom', () => readRenderTarget(renderer, bloomRT), 'Bright pass');
231
+
232
+ // Pass 3: Blur
233
+ renderer.setRenderTarget(blurRT);
234
+ renderer.render(blurScene, postCamera);
235
+ viewer.capture('Blur', () => readRenderTarget(renderer, blurRT));
236
+
237
+ // Final composite
238
+ renderer.setRenderTarget(null);
239
+ renderer.render(compositeScene, postCamera);
240
+
241
+ requestAnimationFrame(render);
242
+ }
243
+ ```
244
+
245
+ ## Keyboard Shortcut Example
246
+
247
+ Add a toggle shortcut for convenience:
248
+
249
+ ```typescript
250
+ const viewer = BufferViewer.getInstance({ active: false });
251
+
252
+ window.addEventListener('keydown', (e) => {
253
+ if (e.key === 'F2') {
254
+ viewer.toggle();
255
+ }
256
+ });
257
+ ```
258
+
259
+ ## License
260
+
261
+ MIT