diff --git a/apps/client/package.json b/apps/client/package.json index 09be443..a2efbe5 100644 --- a/apps/client/package.json +++ b/apps/client/package.json @@ -4,7 +4,7 @@ "version": "0.0.0", "type": "module", "scripts": { - "dev": "vite", + "dev": "vite --host", "build": "tsc -b && vite build", "preview": "vite preview" }, diff --git a/apps/server/package.json b/apps/server/package.json index 5aec1eb..210e48d 100644 --- a/apps/server/package.json +++ b/apps/server/package.json @@ -13,11 +13,11 @@ "packageManager": "pnpm@10.28.2", "dependencies": { "@repo/shared": "workspace:*", - "ws": "^8.19.0" + "socket.io": "^4.8.3" }, "devDependencies": { "@types/node": "^24.10.11", - "@types/ws": "^8.18.1", + "@types/socket.io": "^3.0.2", "tsx": "^4.21.0", "typescript": "^5.9.3" } diff --git "a/docs/01_Env/ENV_01_\347\222\260\345\242\203\346\247\213\347\257\211\343\203\273\346\212\200\350\241\223\343\202\271\343\202\277\343\203\203\343\202\257.txt" "b/docs/01_Env/ENV_01_\347\222\260\345\242\203\346\247\213\347\257\211\343\203\273\346\212\200\350\241\223\343\202\271\343\202\277\343\203\203\343\202\257.txt" new file mode 100644 index 0000000..ea61c96 --- /dev/null +++ "b/docs/01_Env/ENV_01_\347\222\260\345\242\203\346\247\213\347\257\211\343\203\273\346\212\200\350\241\223\343\202\271\343\202\277\343\203\203\343\202\257.txt" @@ -0,0 +1,151 @@ +======================================================================== +Pixel Paint War - 開発環境・技術スタック定義書 +======================================================================== + +1. プロジェクト基本方針 +------------------------------------------------------------------------ + +1-1. アーキテクチャ構成: Monorepo (モノレポ) + ・目的: クライアント(Client)とサーバー(Server)で,言語(TypeScript)およびゲームロジック(移動演算・定数・型定義)を完全共有するため. + ・パッケージ管理: pnpm workspaces を採用. + +1-2. コア・コンセプト + ・言語: TypeScript (Strict mode) + ・通信: WebSocket + Hybrid Protocol + - Core Game (移動・塗り): Custom Binary (DataView) による極小パケット通信 + - Meta Data (ロビー・チャット): JSON (開発効率とデバッグ容易性を優先) + ・描画: WebGL 2D (Pixi.js) + ・同期: サーバー権限 (Authoritative) + クライアント予測 (Prediction) + +1-3. AI活用型開発 (AI-Assisted Development) + ・採用ツール: + - Gemini Pro (学校提供ライセンス) + - GitHub Copilot Pro (GitHub Student Developer Pack) + ・言語選定の優位性: + TypeScriptを採用することで厳密な型定義(Type/Interface)を保持する. + これによりAIがコードの文脈や意図を正確に解釈可能となり, + 型のないJavaScriptと比較して,コード生成・補完・リファクタリングの精度が著しく向上する. + + +2. ディレクトリ構造 (Directory Structure) +------------------------------------------------------------------------ + +2-1. 構成一覧 + root/ + ├── package.json # pnpm workspace 定義 + ├── pnpm-workspace.yaml # ワークスペース設定 + ├── .npmrc # 依存関係解決の設定 + │ + ├── apps/ + │ ├── client/ # 【演出】フロントエンド (Browser) + │ │ ├── src/ + │ │ │ ├── assets/ # 画像・音声リソース + │ │ │ ├── core/ # クライアントの心臓部 (GameApp, MainLoop) + │ │ │ ├── entities/ # 描画用エンティティ (PlayerSprite - 補間・描画ロジック含む) + │ │ │ ├── input/ # 入力処理 (Joystick, Keyboard) + │ │ │ ├── network/ # 通信処理 (SocketClient, Reconciler/補正処理) + │ │ │ ├── scenes/ # 画面管理 (Title, Lobby, Game, Result) + │ │ │ ├── ui/ # HTML UI管理 (HUD, Modal) + │ │ │ └── main.ts # エントリーポイント + │ │ ├── index.html + │ │ ├── vite.config.ts + │ │ └── package.json + │ │ + │ └── server/ # 【権限】バックエンド (Node.js) + │ ├── src/ + │ │ ├── core/ # サーバーの心臓部 (GameLoop, ServerEngine) + │ │ ├── entities/ # サーバー側エンティティ (Player, Item - 状態管理のみ) + │ │ ├── managers/ # 管理クラス (RoomManager, ScoreManager) + │ │ ├── network/ # WebSocket処理 (Connection, PacketHandler) + │ │ └── index.ts # エントリーポイント + │ ├── tsconfig.json + │ └── package.json + │ + └── packages/ + └── shared/ # 【最重要】「真実」の定義場所(型、定数、純粋ロジック) + ├── src/ + │ ├── config/ # ゲーム定数 (マップサイズ, TickRate, 物理定数) + │ ├── protocol/ # 通信規約 (パケット構造, OpCode, バイナリ定義) + │ ├── types/ # 型定義 (PlayerState, InputData, RoomInfo) + │ ├── utils/ # 純粋関数 (Vector計算, 衝突判定, グリッド計算) + │ └── index.ts # エントリーポイント (tsupビルド対象) + ├── tsup.config.ts # ビルド設定 + └── package.json + + ※ shared は client/server 両方から import して使用する. + + +3. 技術スタック詳細 (Tech Stack) +------------------------------------------------------------------------ + +3-1. 共通・基盤 (Common / Shared) + ・Runtime: Node.js (v20 LTS 以上) + ・Package Manager: pnpm + ・Build Tool: tsup (高速で軽量なTypeScriptバンドラ) + ・Serialization: Custom Binary (Standard DataView API) + - 採用理由: ライブラリ依存をなくし、仕様書要件(30KB/s以下)を満たす最適化を行うため。 + - 用途: 座標データ、入力情報の圧縮通信。 + +3-2. フロントエンド (Client) + ・Build Tool: Vite + ・Language: TypeScript + ・Rendering Engine: Pixi.js (v8) + - 採用理由: 50人同時対戦時の大量のスプライト描画と60fps維持のため. + ・UI Library: Preact (または Vanilla HTML/CSS) + - 採用理由: ゲームループへの負荷を避けつつ,軽量なHUDを構築するため. + ・Network: Native WebSocket API + +3-3. バックエンド (Server) + ・Runtime: Node.js + ・Execution: tsx (開発時の高速実行・ウォッチ用) + ・WebSocket Library: ws + - 採用理由: 軽量かつ標準的.uWebSockets.js への移行も視野に入れるが初期は ws で実装. + ・Logic: 独自ループ (20Hz固定) + - Physics Engine: 使用しない (shared/physics.ts による独自グリッド判定) + +3-4. 開発ツール (Dev Tools) + ・Linter: ESLint + ・Formatter: Prettier + ・Test: Vitest (共通ロジックの単体テスト用) + ・AI Assistant: GitHub Copilot Pro, Gemini Pro + + +4. 開発マシンの前提条件 (Prerequisites) +------------------------------------------------------------------------ +以下のツールがインストールされていること. + + 1. Node.js (v20.x LTS) + $ node -v + + 2. pnpm (Corepack enabled or standalone install) + $ pnpm -v + + 3. VS Code (推奨エディタ) + 以下の拡張機能を導入推奨: + - ESLint + - Prettier - Code formatter + - EditorConfig for VS Code + - Hex Editor (バイナリパケットのデバッグ用・Microsoft公式) + - GitHub Copilot (要ログイン確認) + + 4. AI・アカウント環境 + - 学校提供の Gemini Pro へのアクセス権限確認 + - GitHub Copilot Pro (Student) の有効化確認 + + +5. 実装上の重要ルール (Implementation Rules) +------------------------------------------------------------------------ + +5-1. ロジックの一元管理 + - 「移動速度」「ヒット判定」「マップ更新」の計算式は必ず `packages/shared` に記述する. + - Client と Server で別の計算式を書くことを禁止する(同期ズレ防止). + +5-2. 座標系 + - 内部計算: Float (浮動小数点) + - 通信データ: Integer (整数 / 100倍して送信など圧縮を考慮) + - 描画: Float (補間処理あり) + +5-3. 依存方向 + - OK: Client -> Shared + - OK: Server -> Shared + - NG: Client -> Server / Server -> Client (直接参照禁止) \ No newline at end of file diff --git "a/docs/01_Env/ENV_02_\347\222\260\345\242\203\346\247\213\347\257\211\346\211\213\351\240\206\346\233\270.txt" "b/docs/01_Env/ENV_02_\347\222\260\345\242\203\346\247\213\347\257\211\346\211\213\351\240\206\346\233\270.txt" new file mode 100644 index 0000000..f8d5e5b --- /dev/null +++ "b/docs/01_Env/ENV_02_\347\222\260\345\242\203\346\247\213\347\257\211\346\211\213\351\240\206\346\233\270.txt" @@ -0,0 +1,401 @@ +======================================================================== +Pixel Paint War - 環境構築ガイド (Environment Setup Guide) +======================================================================== + +1. 事前準備 (Prerequisites) +------------------------------------------------------------------------ + +1-0. 目的 + 本ドキュメントは,「Pixel Paint War」のMonorepo構成による開発環境を構築 + するための手順書である. + ※ 本プロジェクトは Node.js v20 LTS 以上を必須とする. + +1-1. 必須ツールのインストール + 開発を開始する前に,以下のツールをインストールしバージョンを確認する. + + 1. Node.js (v20.x LTS) + ・Nodesource リポジトリを使用してインストールする. + # リポジトリのセットアップとインストール + $ curl -fsSL https://deb.nodesource.com/setup_20.x | sudo -E bash - + $ sudo apt-get install -y nodejs + + ・確認コマンド: + $ node -v # v20.x.x と表示されること + + 2. pnpm (Package Manager) + ・Node.js 標準の npm ではなく pnpm を使用する. + ・Corepack (Node.js同梱) を有効化してインストールする. + $ sudo corepack enable + $ corepack prepare pnpm@latest --activate + + ・確認コマンド: + $ pnpm -v + + +2. プロジェクト初期化 (Project Initialization) +------------------------------------------------------------------------ + +2-1. ディレクトリ作成と初期化 + 1. プロジェクトルートの作成 + 任意の場所にプロジェクトフォルダを作成し,移動する. + $ mkdir SkillSemiWebGame + $ cd SkillSemiWebGame + + 2. Gitの初期化 + $ git init + + 3. pnpm の初期化 + $ pnpm init + +2-2. ワークスペース設定 (Monorepo Setup) + ルートディレクトリに以下の設定ファイルを作成し,モノレポ構成を定義する. + + 1. pnpm-workspace.yaml + ・packages/shared を共通ライブラリとし,apps 配下にアプリを配置する. + ・内容: + packages: + - 'apps/*' + - 'packages/*' + + 2. .npmrc + ・依存関係解決の設定を行う (shamefully-hoist=true 推奨). + ・内容: + shamefully-hoist=true + +2-3. ディレクトリ構造の構築 + 以下の構成になるようにディレクトリを作成する. + + root/ + ├── apps/ + │ ├── client/ # フロントエンド (Browser) + │ └── server/ # バックエンド (Node.js) + └── packages/ + └── shared/ # 共通ロジック (Shared Library) + + ・作成コマンド例: + $ mkdir -p apps/client apps/server packages/shared + +2-4. Git除外設定 (Git Ignore Setup) + 不要なファイル(依存ライブラリやビルド成果物)がGit管理下に置かれないよう, + 除外設定を行う. + + 1. 設定ファイルの作成 + プロジェクトルートディレクトリに `.gitignore` ファイルを作成する. + $ touch .gitignore + + 2. 除外ルールの記述 + 以下の内容をファイルに記述し保存する. + ・node_modules: 依存ライブラリフォルダ. + ・dist, build: ビルド生成物. + ・.env: 環境変数ファイル(セキュリティ保持のため). + + # Dependencies + node_modules/ + .pnpm-store/ + + # Build Outputs + dist/ + build/ + out/ + + # Logs + *.log + npm-debug.log* + pnpm-debug.log* + + # Environment Variables + .env + .env.local + .env.*.local + + # Editor / OS + .vscode/* + !.vscode/extensions.json + !.vscode/settings.json + !.vscode/launch.json + .idea/ + .DS_Store + Thumbs.db + + # Testing + coverage/ + + # Unignore packages (Fix for parent gitignore) + !packages/ + + 3. 設定の反映確認 + Gitのステータスを確認し,`node_modules/` 等が含まれていないことを確認する. + $ git status + +2-5. 初回コミット (Initial Commit) + 環境構築の区切りとして,現在の状態をリポジトリに保存する. + + 1. ステータス確認 + `.gitignore` が正しく適用されているか確認する. + $ git status + ※ `node_modules/` が表示されていないことを確認する. + + 2. ステージング + 変更された全てのファイルをコミット対象に追加する. + $ git add . + + 3. コミット実行 + 構築内容を示すメッセージを付与してコミットする. + $ git commit -m "chore: Project initialization (Monorepo, pnpm, Vite)" + +3. パッケージ・ライブラリ導入 (Dependency Installation) +------------------------------------------------------------------------ + +3-1. 共通ライブラリ (packages/shared) + 共通ロジック用のパッケージ設定を行う. + + 1. 初期化とビルドツール導入 + $ cd packages/shared + $ pnpm init + $ pnpm add -D typescript tsup + + 2. 設定ファイルの調整 (package.json) + ・name: "@repo/shared" と命名する(推奨). + ・main: "./dist/index.js", types: "./dist/index.d.ts" を指定する. + ・scripts: "build": "tsup src/index.ts --format cjs,esm --dts" を追加する. + + 3. エントリーポイントの作成 + tsupがビルド対象とするファイルを作成する. + + $ mkdir src + $ touch src/index.ts + + ※ 現時点では空ファイルでよいが,将来的に constants.ts 等を export する記述を行う. + (例: export * from './constants';) + + 4. TypeScript設定ファイルの作成 (tsconfig.json) + ビルドと型定義生成のための設定ファイルを作成する. + ・ファイル: packages/shared/tsconfig.json + ・内容: + { + "compilerOptions": { + "target": "ES2020", + "module": "ESNext", + "moduleResolution": "Bundler", + "lib": ["ES2020", "DOM", "DOM.Iterable"], + "declaration": true, + "declarationMap": true, + "sourceMap": true, + "outDir": "./dist", + "rootDir": "./src", + "strict": true, + "esModuleInterop": true, + "skipLibCheck": true, + "forceConsistentCasingInFileNames": true + }, + "include": ["src/**/*"], + "exclude": ["node_modules", "dist"] + } + +3-2. フロントエンド (apps/client) + Vite プロジェクトとして初期化を行う. + + 1. プロジェクト作成 + $ cd ../../apps/client + $ pnpm create vite . --template preact-ts + ※ 実行中に表示される選択肢には以下のように回答すること: + ? Use rolldown-vite (Experimental)? » No + ? Install with pnpm and start now? » No + + 2. 依存ライブラリのインストール + ・Pixi.js (描画エンジン) を追加する. + ・共通ライブラリへの依存を追加する. + $ pnpm add pixi.js + $ pnpm add @repo/shared --workspace + +3-3. バックエンド (apps/server) + Node.js アプリケーションとして初期化を行う. + + 1. 初期化 + $ cd ../../apps/server + $ pnpm init + + 2. 依存ライブラリのインストール + ・ws (WebSocket) を追加する. + ・開発用ツール (tsx, typescript, @types/node, @types/ws) を追加する. + ・共通ライブラリへの依存を追加する. + $ pnpm add ws + $ pnpm add -D tsx typescript @types/node @types/ws + $ pnpm add @repo/shared --workspace + + 3. サーバー用ディレクトリとファイルの作成 + tsxが実行対象とするエントリーポイントを作成する. + $ mkdir src + $ touch src/index.ts + + 4. 実行スクリプトの定義 + package.json にサーバー起動用のコマンドを追加する. + ・編集ファイル: apps/server/package.json + ・内容: + "scripts": { + "dev": "tsx watch src/index.ts" + } + + 5. TypeScript設定ファイルの作成 (tsconfig.json) + 開発時の実行環境とパス解決のための設定ファイルを作成する. + ・ファイル: apps/server/tsconfig.json + ・内容: + { + "compilerOptions": { + "target": "ES2022", + "module": "NodeNext", + "moduleResolution": "NodeNext", + "lib": ["ES2022"], + "strict": true, + "noEmit": true, + "esModuleInterop": true, + "skipLibCheck": true, + "forceConsistentCasingInFileNames": true, + "baseUrl": ".", + "paths": { + "@repo/shared": ["../../packages/shared/src/index.ts"] + } + }, + "include": ["src/**/*"], + "exclude": ["node_modules"] + } + + +4. 開発ツール設定 (Dev Tools Setup) +------------------------------------------------------------------------ + +4-1. VS Code 拡張機能 + 推奨エディタである VS Code に以下の拡張機能をインストールする. + + ■ 必須拡張機能 + ・ESLint + ・Prettier - Code formatter + ・EditorConfig for VS Code + + ■ 推奨拡張機能 + ・Hex Editor (バイナリパケットのデバッグ用・Microsoft公式) + ・GitHub Copilot + +4-2. AI アシスタント設定 + 開発効率化のため,以下のAIツールのアカウント設定を確認する. + + 1. Gemini Pro + ・学校提供ライセンスでのアクセス権限を確認する. + + 2. GitHub Copilot Pro + ・Student Developer Pack が有効化されているか確認する. + ・VS Code 右下のアイコンからログイン状態を確認する. + + +5. 構成確認 (Configuration Check) +------------------------------------------------------------------------ + +5-1. 最終ディレクトリ構成 + 構築完了時点で,以下のディレクトリおよびファイルが存在することを確認する. + + SkillSemiWebGame/ <-- プロジェクトルート + ├── .git/ <-- git init で作成 + ├── .gitignore <-- Git除外設定 + ├── .npmrc <-- 依存解決設定 + ├── package.json <-- ルート定義 + ├── pnpm-lock.yaml <-- pnpm install で自動生成 + ├── pnpm-workspace.yaml <-- ワークスペース定義 + ├── node_modules/ <-- 依存ライブラリ + │ + ├── apps/ <-- アプリケーション格納用 + │ ├── client/ <-- フロントエンド (Vite + Preact) + │ │ ├── node_modules/ + │ │ ├── src/ + │ │ │ ├── main.tsx (または index.tsx) + │ │ │ └── ... (Viteテンプレートファイル群) + │ │ ├── index.html + │ │ ├── package.json <-- pixi.js, @repo/shared 依存あり + │ │ ├── tsconfig.json + │ │ └── vite.config.ts + │ │ + │ └── server/ <-- バックエンド (Node.js) + │ ├── node_modules/ + │ ├── src/ + │ │ └── index.ts <-- エントリーポイント + │ ├── package.json <-- ws, @repo/shared 依存あり + │ └── tsconfig.json <-- pnpm init 等で生成(または要作成) + │ + └── packages/ <-- 共通パッケージ格納用 + └── shared/ <-- 共通ロジック + ├── node_modules/ + ├── dist/ <-- ビルド後に生成される (index.js, index.d.ts) + ├── src/ + │ └── index.ts <-- 空または定数export用 + ├── package.json <-- buildスクリプト定義あり + └── tsconfig.json <-- tsup/typescript設定用 + +5-2. 重要ファイル設定確認 + 各パッケージの連携設定が正しいか確認する. + + ■ root/pnpm-workspace.yaml + packages: + - 'apps/*' + - 'packages/*' + + ■ packages/shared/package.json + ・name: "@repo/shared" + ・main: "./dist/index.js" + ・types: "./dist/index.d.ts" + + ■ apps/client/package.json + ・dependencies: + "@repo/shared": "workspace:*" + + ■ apps/server/package.json + ・dependencies: + "@repo/shared": "workspace:*" + + +6. 動作確認 (Verification) +------------------------------------------------------------------------ + +6-1. ビルド確認 + ルートディレクトリから全体の依存関係をインストールし,ビルドを試行する. + + $ cd ../../ + $ pnpm install + $ pnpm --filter @repo/shared build + + ※ shared のビルドが成功することを確認する. + +6-2. 開発サーバー起動 + モノレポ構成のため,個別のディレクトリに移動せず,プロジェクトルートから + --filter オプションを使用して各アプリを起動する. + ※ ターミナルを2つ開き,両方を同時に起動した状態で開発を進めることを推奨. + + 1.Client (フロントエンド) の動作確認 + ・ルートディレクトリにて以下のコマンドを実行する. + $ pnpm --filter client dev + + ・ブラウザでの確認: + ターミナルに「➜ Local: http://localhost:5173/」と表示されたら, + Google Chrome等のブラウザを開き,アドレスバーに上記URLを貼り付けて実行する. + + ・正常動作の判断基準: + 画面に「Vite + Preact」のロゴと「Vite + Preact + TypeScript」といった + テキストが表示されていれば,フロントエンドの環境構築は成功である. + + 2. Server (バックエンド) の動作確認 + ・テスト用コードの作成: + 動作確認用のエントリーポイントを作成する. + $ touch apps/server/src/index.ts + + ファイルに以下の内容を記述する. + console.log("Server is running!"); + + ・コマンド: + $ pnpm --filter server dev + + ・正常動作の判断基準: + ターミナルに「Server is running!」と出力されれば構築成功である. + + 3.終了方法 (重要) + ・動作確認を終了し,開発サーバーを停止させる場合は,ターミナル上で + 「Ctrl + C」を押下する. + ・停止後はブラウザでURLにアクセスしても接続不可となるが,再度起動 + コマンドを実行すればいつでも再開可能である. \ No newline at end of file diff --git "a/docs/01_Env/ENV_03_TypeScript\346\246\202\350\246\201.txt" "b/docs/01_Env/ENV_03_TypeScript\346\246\202\350\246\201.txt" new file mode 100644 index 0000000..e489c79 --- /dev/null +++ "b/docs/01_Env/ENV_03_TypeScript\346\246\202\350\246\201.txt" @@ -0,0 +1,90 @@ +======================================================================== +TypeScript概要 (TypeScript Overview) +======================================================================== + +1. 概要 (Overview) +------------------------------------------------------------------------ +本プロジェクト(Pixel Paint War)において採用するプログラミング言語「TypeScript」に関する基礎知識,選定理由,およびAI活用開発における優位性を定義する. +本ドキュメントは,開発チーム内での技術認識の統一を目的とする. + + +2. TypeScriptとは (What is TypeScript) +------------------------------------------------------------------------ +Microsoftによって開発されたオープンソースのプログラミング言語である.JavaScriptのスーパーセット(上位互換)として設計されており,大規模なアプリケーション開発に適した機能が拡張されている. + +2-1. JavaScriptとの違い + ・静的型付け (Static Typing): + 変数や関数の引数,戻り値に「型(Type)」を指定できる.JavaScriptは動的型付け言語であり,実行時まで型が決まらないが,TypeScriptはコンパイル(トランスパイル)時に整合性をチェックする. + ・クラスベースオブジェクト指向: + インターフェース(Interface),ジェネリクス(Generics),アクセス修飾子(public/private)など,JavaやC#に近いオブジェクト指向構文をサポートする. + ・コンパイルの必要性: + ブラウザやNode.jsはTypeScriptを直接実行できないため,JavaScriptファイルへ変換(トランスパイル)して使用する. + +2-2. 一般的な利用目的 + ・大規模Webアプリケーション開発: + コード量が増えても型定義により保守性を維持しやすい. + ・チーム開発: + 型定義がそのまま「仕様書」としての役割を果たし,メンバー間の認識齟齬を防ぐ. + ・フルスタック開発: + フロントエンド(React/Vue/Angular等)とバックエンド(Node.js/Deno等)で言語を統一し,型定義を共有する. + + +3. 言語の強み (Strengths) +------------------------------------------------------------------------ + +3-1. 安全性と品質向上 + ・コンパイルエラーによる早期発見: + 「undefinedのプロパティ参照」や「数値と文字列の誤った演算」など,JavaScriptで頻発する実行時エラーを,コードを書いている段階(コンパイル時)で検出できる. + +3-2. 開発効率の向上 + ・強力な入力補完 (IntelliSense): + VS Code等のエディタにおいて,型情報を元にした正確なコード補完,メソッドの候補表示,定義元へのジャンプが可能となる. + ・リファクタリングの容易さ: + 変数名や関数名の変更を行っても,依存する箇所をエディタが一括で修正・検知できるため,改修コストが低い. + + +4. AI活用型開発における利点 (Benefits in AI-Assisted Development) +------------------------------------------------------------------------ +本プロジェクトの方針である「AI活用型開発(Gemini Pro / GitHub Copilot Pro)」において,TypeScriptはJavaScriptと比較して以下の決定的な優位性を持つ. + +■ コンテキストの正確な伝達 + 型定義(Type/Interface)が存在することで,AIは変数の意図やデータ構造を推測ではなく「確定情報」として認識できる.これにより,提案されるコードの精度が向上する. + +■ ハルシネーション(嘘の生成)の抑制 + 存在しないプロパティや誤ったメソッドをAIが提案した場合でも,TypeScriptのコンパイラが即座にエラーを出すため,誤ったコードが実装に含まれるリスクを自動的に排除できる. + +■ 意図の明示化 + 「ENV_01」で定義された `packages/shared` のような共通型定義を参照させることで,AIはクライアント・サーバー間の通信仕様を正確に理解し,一貫性のあるロジックを生成可能となる. + + +5. 歴史と現状 (History and Current Status) +------------------------------------------------------------------------ + +5-1. 歴史 + ・開発者: Anders Hejlsberg(C#やTurbo Pascalの設計者)らが中心となり開発. + ・初版公開: 2012年10月. + ・背景: 当時,大規模化するWebアプリ開発においてJavaScriptの仕様(ES5)では保守が困難であったため,静的型付けの需要が高まっていた. + +5-2. 現在のステータス + ・世界No.1の使用率 (GitHub Octoverse 2025): + 2025年のGitHub年次レポートにおいて,長年トップであったPythonおよびJavaScriptを上回り,世界で最も使用されている言語(第1位)となった. + このランキングは,単なるコードの総量ではなく「貢献者数(Unique Contributors)」に基づいており,現在世界中で最も多くのアクティブユーザーが開発を行っている言語であることを示している. + ・デファクトスタンダード: + 現在,モダンなフロントエンド開発(React, Next.js, Vue.jsなど)において,TypeScriptは標準的な選択肢となっている. + ・普及率: + 「State of JS」などの開発者アンケートにおいて,長年「使用率」および「満足度」で上位を維持している.また,Google社内の標準言語としても採用されている(Alligator等). + + +6. 参考文献 (References) +------------------------------------------------------------------------ +・TypeScript Official Website + https://www.typescriptlang.org/ + +・The State of JS 2022/2023 (Usage & Satisfaction) + https://stateofjs.com/ + +・GitHub Octoverse 2025 + https://octoverse.github.com/ + +・Google Engineering Practices Documentation + https://google.github.io/eng-practices/ \ No newline at end of file diff --git "a/docs/01_Env/ENV_04_\343\202\271\343\203\236\343\203\233\345\256\237\346\251\237\343\203\207\343\203\220\343\203\203\343\202\260\346\211\213\351\240\206.txt" "b/docs/01_Env/ENV_04_\343\202\271\343\203\236\343\203\233\345\256\237\346\251\237\343\203\207\343\203\220\343\203\203\343\202\260\346\211\213\351\240\206.txt" new file mode 100644 index 0000000..06c1f56 --- /dev/null +++ "b/docs/01_Env/ENV_04_\343\202\271\343\203\236\343\203\233\345\256\237\346\251\237\343\203\207\343\203\220\343\203\203\343\202\260\346\211\213\351\240\206.txt" @@ -0,0 +1,122 @@ +======================================================================== +スマホ実機デバッグ手順 (Smartphone Debugging Guide) +======================================================================== + + +1. 概要 (Overview) +------------------------------------------------------------------------ + +1-0. 目的 + 本ドキュメントは,開発中のWebゲーム「Pixel Paint War」をスマホ実機で動作 + 確認するための手順書である. + 学校や組織のネットワーク(Fortinet等)による制限や,WSL2特有のネットワー + クの壁を回避するため,トンネリングツール「ngrok」を使用した外部公開手順 + を採用する. + +1-1. 前提条件 + ・WSL2 (Ubuntu等) 上で開発環境が構築済みであること. + ・ngrok の公式サイトでアカウント作成済みであること. + ・Authtoken (認証トークン) が取得済みであること. + + +2. ngrokのインストール (Installation) +------------------------------------------------------------------------ +Linux (WSL2) 環境へのインストール手順を記述する. +※ apt パッケージマネージャ経由ではエラーが発生しやすいため,バイナリ直接 +インストール方式を採用する. + +2-1. ダウンロードと配置 + 1. 圧縮ファイルのダウンロード + ターミナルで以下のコマンドを実行し,Linux版バイナリを取得する. + $ wget https://bin.equinox.io/c/bNyj1mQVY4c/ngrok-v3-stable-linux-amd64.tgz + + 2. 解凍とインストール + ダウンロードしたファイルを解凍し,実行パスの通ったディレクトリに移動する. + $ sudo tar xvzf ngrok-v3-stable-linux-amd64.tgz -C /usr/local/bin + + 3. 動作確認 + バージョン情報が表示されるか確認する. + $ ngrok --version + ※ "ngrok version 3.x.x" 等と表示されれば成功である. + +2-2. アカウント認証 (Authentication) + ngrok のダッシュボード (https://dashboard.ngrok.com/get-started/your-authtoken) + からトークンを確認し,以下のコマンドで設定する. + + ■ トークンの登録 + $ ngrok config add-authtoken [あなたのAuthtoken] + ※ "[あなたのAuthtoken]" の部分は実際の文字列に置き換える. + + +3. デバッグ実行手順 (Execution Steps) +------------------------------------------------------------------------ + +3-1. Client設定の修正 (Update Configuration) + 開発サーバーが外部 (ngrok) からの接続を受け付けるよう,設定を変更する. + + ■ package.json の編集 + `apps/client/package.json` を開き,`scripts` ブロックの `dev` コマンドに `--host` オプションを追加する. + + [修正前] + "dev": "vite" + + [修正後] + "dev": "vite --host" + +3-2. 開発サーバーの起動 (Launch Dev Server) + まず,ローカル環境でアプリケーションを起動する. + + ■ Clientアプリの起動 + プロジェクトルートで以下のコマンドを実行する. + $ pnpm --filter client dev + ※ ターミナルに `Network: http://x.x.x.x:5173/` と表示されれば設定成功である. + +3-3. ngrokによる公開 (Expose via ngrok) + 新しいターミナルウィンドウを開き,以下の手順でトンネルを作成する. + + 1. ngrokの起動 + Vite の Host ヘッダーチェックを回避するため,オプションを付与して実行する. + $ ngrok http 5173 --host-header="localhost" + + 2. 公開URLの確認 + 起動後に表示されるステータス画面から,"Forwarding" の行を確認する. + + Session Status online + Account User Name (Plan: Free) + Forwarding https://xxxx-xxxx.ngrok-free.app -> http://localhost:5173 + + 上記の "https://xxxx-xxxx.ngrok-free.app" が公開URLとなる. + +3-4. スマホからのアクセス (Access from Smartphone) + 1. URLの共有 + 発行された URL をスマホに送信する(QRコード作成ツールやチャット等を使用). + + 2. ブラウザでの確認 + スマホのブラウザ(Chrome,Safari等)で URL にアクセスする. + タイトル画面が表示されれば接続成功である. + + +4. 注意事項とトラブルシューティング (Notes & Troubleshooting) +------------------------------------------------------------------------ + +4-1. Freeプランの制限 + ・同時接続数: Freeプランでは同時に1つのポートしか公開できない. + ・Client/Server構成の注意: + 本手順ではフロントエンド (Port 5173) のみ公開している. + バックエンド (Port 3000) への WebSocket 通信が必要な場合,ゲーム開始時 + に接続エラーとなる可能性がある. + - 対策: UIレイアウトや描画負荷の確認を主目的として使用する. + +4-2. エラー対応 + ■ "ERR_NGROK_3200" (Tunnel already open) + ・既に別のターミナルで ngrok が起動している場合に発生する. + - 対策: 起動中の ngrok を終了 (Ctrl + C) してから再実行する. + + ■ "Invalid Host Header" (画面が真っ白になる) + ・Vite が不正なドメインからのアクセスを拒否している. + - 対策: 起動コマンドに `--host-header="localhost"` が含まれているか再確認する. + + ■ "ERR_CERT_AUTHORITY_INVALID" (Fortinet等の警告) + ・ngrok を使用せずローカルIPで接続しようとした場合に,組織内ネットワーク + のセキュリティ機器にブロックされる現象である. + - 対策: 必ず本手順の ngrok 経由 (https) で接続する. \ No newline at end of file diff --git "a/docs/02_Guide/GUIDE_01_\343\203\211\343\202\255\343\203\245\343\203\241\343\203\263\343\203\210\344\275\234\346\210\220\343\202\254\343\202\244\343\203\211.txt" "b/docs/02_Guide/GUIDE_01_\343\203\211\343\202\255\343\203\245\343\203\241\343\203\263\343\203\210\344\275\234\346\210\220\343\202\254\343\202\244\343\203\211.txt" new file mode 100644 index 0000000..07dd34b --- /dev/null +++ "b/docs/02_Guide/GUIDE_01_\343\203\211\343\202\255\343\203\245\343\203\241\343\203\263\343\203\210\344\275\234\346\210\220\343\202\254\343\202\244\343\203\211.txt" @@ -0,0 +1,96 @@ +======================================================================== +ドキュメント作成ガイドライン (Style Guide) +======================================================================== + +1. 基本フォーマット (Basic Format) +------------------------------------------------------------------------ +・文字コード: UTF-8 +・改行コード: LF (推奨) または CRLF +・インデント: 半角スペース4つ (4 spaces) + - タブ文字は使用せず、スペースに展開して揃える. + +■ ファイルヘッダー (File Header) +・ファイルの先頭には必ずタイトルブロックを記述する. +・書式: 上下を「=」(イコール)の列(72文字程度)で挟む. +・例: + ======================================================================== + ドキュメントタイトル (English Title) + ======================================================================== + + +2. 句読点・約物 (Punctuation) +------------------------------------------------------------------------ +・句読点: 「,」(全角カンマ)と「.」(全角ピリオド)を使用する. + - 「、」「。」は使用しない. +・コロン: 半角コロン+半角スペース「: 」を使用する. + - NG: 全角コロン「:」,スペースなし「:」 +・括弧: 原則として半角括弧 `( )` を使用するが、強調や補足には全角 `( )` や `「 」` も許容する. +・注釈: 文末や段落末の補足には「※」(全角米印)+半角スペースを使用する. + - 例: ※ shared は client/server 両方から import して使用する. + + +3. 階層構造と見出し (Headings & Hierarchy) +------------------------------------------------------------------------ + +3-1. レベル1:大見出し (Section) + ・書式: 数字 + ドット + 半角スペース + タイトル + (英語タイトル) + ・装飾: 下行にハイフン「-」による区切り線を挿入する. + ・例: + 1. 基本設計 (Basic Design) + ------------------------------------------------------------------------ + +3-2. レベル2:中見出し (Subsection) + ・書式: 数字-数字 + ドット + 半角スペース + タイトル + ・例: + 1-1. 製品概要 + +3-3. レベル3:小見出し (Group Heading) + ・書式: 「■」+ 半角スペース + タイトル + ・使い分け: + - セクション内で独立したトピック(カテゴリ)を列挙する場合は「■」を使用する. + - 手順やフロー、順序のある項目を示す場合は「1. 」「2. 」を使用する. + + A. 並列・カテゴリ列挙(順序不問) + - 記号: 「■ 」(全角四角+半角スペース) + - 例: ■ フィールド仕様 + + B. 手順・優先順位・ランキング(順序重要) + - 記号: 「1. 」「2. 」(半角数字+ドット+半角スペース) + - 例: 1. ユーザ体験の理想 + +3-4. レベル4:リスト項目 (List Item) + ・記号: 「・」(全角中黒) + ・書式: 「・項目名: 内容」または「・項目名」のみ. + ・例: + ・タイトル: Paint War + +3-5. レベル5:詳細項目 (Detail Item) + ・記号: 「- 」(半角ハイフン+半角スペース) + ・インデント: 親項目のテキスト開始位置に合わせる(基本はスペース8つ). + ・例: + ・親項目 (Level 4) + - 子項目: 詳細内容 (Level 5) + +3-6. 特殊なナンバリング (Zero Indexing) + ・目的定義: セクションの冒頭で目的や定義を述べる場合、「X-0. 目的」というナンバリング(ゼロ始まり)を使用してもよい. + - 例: 1-0. 目的 + +3-7. 階層の順守 + ・上位レベルから下位レベルへ順に記述し,階層を飛ばさないこと. + - NG例: レベル1(1. XX)の直下にレベル3(■ XX)を記述する. + - 対策: 必要に応じてレベル2(1-1. 概要 等)を設ける. + + +4. 余白・改行ルール (Spacing) +------------------------------------------------------------------------ +・大見出しの上: 2行空ける. +・中見出し(X-X)の上: 1行空ける. +・小見出し(■や数字)の上: 1行空ける. +・セクション内のリスト: 原則として行間を詰め、まとまりごとに適宜空行を入れる. + + +5. 技術記述・コード表記 (Technical & Code) +------------------------------------------------------------------------ +・コマンドライン: 先頭に `$ ` を付与して区別する. +・ディレクトリ構造: ツリー記号(`├──`, `│`, `└──`)を使用し,ルートディレクトリからの階層を示す. +・インデント: コードブロック内は,親の箇条書きレベルに合わせて開始位置を揃える. \ No newline at end of file diff --git "a/docs/02_Guide/GUIDE_02_\343\203\225\343\202\241\343\202\244\343\203\253\345\221\275\345\220\215\350\246\217\345\211\207.txt" "b/docs/02_Guide/GUIDE_02_\343\203\225\343\202\241\343\202\244\343\203\253\345\221\275\345\220\215\350\246\217\345\211\207.txt" new file mode 100644 index 0000000..c47a0e1 --- /dev/null +++ "b/docs/02_Guide/GUIDE_02_\343\203\225\343\202\241\343\202\244\343\203\253\345\221\275\345\220\215\350\246\217\345\211\207.txt" @@ -0,0 +1,53 @@ +======================================================================== +ドキュメント管理・ファイル命名規則 (File Naming Conventions) +======================================================================== + +1. 命名の基本方針 (Basic Policy) +------------------------------------------------------------------------ +プロジェクトの規模拡大に伴うファイルの散乱を防ぎ,開発メンバーおよびAI(Gemini/Copilot)がファイルの内容・文脈を即座に特定できるようにするため,以下の規則を適用する. + +■ 基本フォーマット +`[カテゴリ]_[連番]_[ファイル名].txt` + +・区切り文字: アンダースコア `_` を使用する. +・連番: 01から始まる2桁の数字とする. +・拡張子: プレーンテキスト `.txt` とする. + + +2. カテゴリ定義 (Category Definitions) +------------------------------------------------------------------------ +ファイル名の先頭に付与するプレフィックス(接頭辞)定義. + +■ GUIDE_ (Guide) +・内容: チーム全体のルール,規約,運用フローなど,「メタ情報」に関する定義. +・対象例: スタイルガイド,命名規則,Git運用ルール. + +■ PLAN_ (Planning) +・内容: プロジェクトの進行計画,スケジュール,要件定義など,「管理・進行」に関する定義. +・対象例: WBS,ロードマップ,要件定義書,タスク一覧. + +■ ENV_ (Environment) +・内容: 開発環境,ディレクトリ構造,ライブラリ選定など,プロジェクトの「土台」に関する定義. +・対象例: 環境構築手順,技術スタック一覧,パッケージ構成図. + +■ SPEC_ (Specification) +・内容: 企画,ゲームルール,UI/UXなど,ユーザーから見える「仕様」に関する定義. +・対象例: ゲーム企画書,画面遷移図,パラメータ設定(マップサイズ・速度など). + +■ TECH_ (Technical) +・内容: 実装詳細,アルゴリズム,データ構造など,エンジニア向けの「技術設計」に関する定義. +・対象例: 通信プロトコル仕様,同期ロジック,データベース設計,クラス設計. + +■ TEST_ (Test) +・内容: テスト計画,テストケース,品質保証手順など,「検証・品質」に関する定義. +・対象例: 単体テスト仕様書,シナリオテスト計画,テストケース一覧,品質基準. + + +3. 運用ルール (Operational Rules) +------------------------------------------------------------------------ +・1ファイル1テーマ: + ファイルサイズが肥大化しすぎないよう,トピック(例: 通信仕様,判定ロジック)ごとにファイルを分割することを推奨する. + これにより,AIへのコンテキスト入力精度が向上する. + +・スタイルの継承: + 新規作成するファイルも,必ず `GUIDE_01_スタイルガイド.txt` に記載された書式(見出し,句読点「,.」等)に従うこと. \ No newline at end of file diff --git "a/docs/02_Guide/GUIDE_03_Git\351\201\213\347\224\250\343\203\253\343\203\274\343\203\253.txt" "b/docs/02_Guide/GUIDE_03_Git\351\201\213\347\224\250\343\203\253\343\203\274\343\203\253.txt" new file mode 100644 index 0000000..8b5bf95 --- /dev/null +++ "b/docs/02_Guide/GUIDE_03_Git\351\201\213\347\224\250\343\203\253\343\203\274\343\203\253.txt" @@ -0,0 +1,125 @@ +======================================================================== +Git運用ルール (Git Operation Rules) +======================================================================== + +1. 基本方針 (Basic Policy) +------------------------------------------------------------------------ +チーム開発におけるコードの整合性を保ち,手戻りを防ぐために以下の運用フローを徹底する. + +・メインブランチ (main): + - 本番環境または常に動作可能な状態を維持するブランチ. + - 直接のコミット(直プッシュ)は禁止する.必ずプルリクエスト(PR)経由でマージする. +・作業ブランチ (Feature Branch): + - 機能追加やバグ修正ごとに `main` から派生させて作成する. + - 作業完了後,`main` へマージし,原則として削除する. + + +2. ブランチ命名規則 (Branch Naming) +------------------------------------------------------------------------ +2-1. プレフィックス (Prefix) +作業の種類を一目で判別するために,以下のプレフィックスを使用する. + +■ カテゴリ一覧 + ・feature/: 新機能の実装,仕様変更 + ・fix/: バグ修正 + ・refactor/: コードの整理(挙動は変えない) + ・docs/: ドキュメントの追記・修正 + ・chore/: ビルド設定やツール導入など,雑多な作業 + +2-2. 書式 (Format) + ・書式: `[プレフィックス][日付(YYMMDD)]_[概要]` + ・区切り: スラッシュ `/` および アンダースコア `_` を使用する. + ・例: + - feature/260207_player_jump + - fix/260208_collision_bug + - docs/260210_guide_update + + +3. 開発フロー (Development Workflow) +------------------------------------------------------------------------ +作業を開始してからマージされるまでの手順. + +1. ローカルの最新化 + ・作業開始前は必ず `main` ブランチに切り替え,リモートの最新状態を取り込む. + ・コマンド: + $ git checkout main + $ git pull origin main + +2. 作業ブランチの作成 + ・最新の `main` から新しいブランチを作成して移動する. + ・コマンド: + $ git checkout -b feature/01_new_function + +3. 実装とコミット + ・作業単位(意味のあるまとまり)ごとにコミットする. + ・巨大なコミットは避け,レビューしやすい粒度を心がける. + ・コマンド: + $ git add . + $ git commit -m "[add] 新機能を実装" + +4. リモートへのプッシュ + ・作業ブランチをリモートリポジトリへ送信する. + ・コマンド: + $ git push origin feature/01_new_function + +5. プルリクエスト (PR) の作成 + ・GitHubのリポジトリ画面上部に表示される「Compare & pull request」ボタンをクリックする. + ・Baseを `main`、Compareを自分の「作業ブランチ」に設定する. + ・「Reviewers」メニューからチームメンバーを選択し、レビューを依頼する. + ・「Create pull request」ボタンを押してPRをオープンする. + +6. レビューと修正の対応 + ・レビュワーのコメントを確認し、修正が必要な場合はローカルで修正・コミット・プッシュを繰り返す. + ・GitHub上で全ての指摘に対し「Resolve conversation」を行い、やり取りを完了させる. + ・レビュワーから「Approve(承認)」のスタンプまたはメッセージをもらう. + +7. マージの実行(マージボタンの操作) + ・PR画面下部の「Merge pull request」ボタンをクリックする. + ・確認用の「Confirm merge」ボタンを押し、`main` への統合を完了させる. + ・マージ直後に表示される「Delete branch」ボタンを押し、リモート上の作業ブランチを削除する. + +8. ローカル環境のクリーンアップ + ・マージ完了後はローカル環境も最新状態に戻し、古いブランチを削除する. + $ git checkout main + $ git pull origin main + $ git branch -d [作業ブランチ名] + + +4. コミットメッセージ (Commit Messages) +------------------------------------------------------------------------ +4-1. 書式 + ・書式: `[タグ] 内容` + ・言語: 日本語 (Japanese) + ・句読点: 末尾に句点は不要. + +4-2. タグ一覧 + ・[add]: ファイルや機能の追加 + ・[update]: 機能やデータの更新・修正 + ・[fix]: バグ修正 + ・[remove]: 削除 + ・[clean]: 整理,リファクタリング + + +5. トラブルシューティング (Troubleshooting) +------------------------------------------------------------------------ +■ コンフリクト (Conflict) が発生した場合 +他メンバーの変更と競合した場合の対処手順. + +1. main の取り込み + ・作業ブランチに `main` の最新内容をマージして競合箇所を洗い出す. + ・コマンド: + $ git checkout main + $ git pull origin main + $ git checkout feature/XX_working + $ git merge main + +2. 競合の解消 + ・エディタ上で `<<<<<<<`, `=======`, `>>>>>>>` で囲まれた箇所を手動で修正する. + ・修正後,再度コミットしてプッシュする. + +■ 間違えて main にコミットしてしまった場合 + ・まだプッシュしていない場合,コミットを取り消して新しいブランチへ移動させる. + ・コマンド: + $ git reset --soft HEAD^ + $ git checkout -b feature/XX_recover_branch + $ git commit -m "..." \ No newline at end of file diff --git "a/docs/03_Plan/PLAN_01_\347\247\273\345\213\225\343\203\206\343\202\271\343\203\210\345\256\237\350\243\205\350\250\210\347\224\273.txt" "b/docs/03_Plan/PLAN_01_\347\247\273\345\213\225\343\203\206\343\202\271\343\203\210\345\256\237\350\243\205\350\250\210\347\224\273.txt" new file mode 100644 index 0000000..262bd72 --- /dev/null +++ "b/docs/03_Plan/PLAN_01_\347\247\273\345\213\225\343\203\206\343\202\271\343\203\210\345\256\237\350\243\205\350\250\210\347\224\273.txt" @@ -0,0 +1,79 @@ +======================================================================== +Pixel Paint War - プロトタイプ実装計画 (Prototype Implementation Plan) +======================================================================== + +1. 概要 (Overview) +------------------------------------------------------------------------ +本ドキュメントは,「SPEC_03_プロトタイプ_移動テスト.txt」で定義された50人同時接続テストを達成するための段階的な実装ロードマップである. +複雑性を排除するため,最小構成から機能を積み上げる(Step-by-Step)方式を採用する. + + +2. 実装フェーズ定義 (Implementation Phases) +------------------------------------------------------------------------ + +2-1. Step 1: クライアント単体移動 (Local Movement) + ■ 目標 + サーバーを介さず,ブラウザ上でジョイスティック操作によりキャラクターが移動・描画されること. + + ■ 実装対象 + ・packages/shared/ + - src/config/gameConfig.ts: マップサイズ,移動速度等の定数定義. + - src/utils/math.ts: ベクトル計算,移動ロジック (Pos += Vel * Speed * DT). + ・apps/client/ + - src/input/Joystick.ts: タッチ入力の正規化,デッドゾーン処理. + - src/entities/PlayerSprite.ts: 描画更新処理. + - src/core/GameLoop.ts: Pixi.js Tickerを用いたメインループ. + +2-2. Step 2: サーバー開通・単体通信 (Single Player Network) + ■ 目標 + WebSocketサーバーと接続し,バイナリパケットの送受信(エコーテスト)に成功すること. + + ■ 実装対象 + ・packages/shared/ + - src/protocol/schema.ts: DataViewを用いたバイナリエンコード/デコード処理. + ・apps/server/ + - src/index.ts: WebSocketサーバー起動 (wsライブラリ). + - src/network/Connection.ts: 接続管理. + ・apps/client/ + - src/network/SocketClient.ts: バイナリ送受信の実装. + +2-3. Step 3: 複数人同期・補間 (Multiplayer Sync) + ■ 目標 + 2つのクライアント間で位置同期が行われ,他プレイヤーの動きが補間により滑らかに表示されること. + + ■ 実装対象 + ・apps/server/ + - src/managers/RoomManager.ts: 接続IDと座標の管理. + - src/network/PacketHandler.ts: 全員分の座標スナップショット作成とブロードキャスト. + ・apps/client/ + - src/entities/RemotePlayer.ts: 他プレイヤー描画クラス. + - src/network/Reconciler.ts: 線形補間 (Lerp) ロジックの実装. + +2-4. Step 4: 50人規模最適化 (Optimization & Scaling) + ■ 目標 + パケットサイズを削減し,50人同時動作時の帯域負荷を仕様内(30KB/s以下)に抑えること. + + ■ 実装対象 + ・packages/shared/ + - src/utils/quantization.ts: 座標の圧縮 (Float -> Uint16). + ・apps/server/ + - src/core/ServerEngine.ts: ループ処理の最適化,必要に応じたAoI(関心領域)判定. + +2-5. Step 5: メタデータ・UI実装 (Meta Data & UI) + ■ 目標 + ゲーム開始前のロビー画面およびUIを実装し,ゲームサイクルを完成させること. + + ■ 実装対象 + ・apps/client/ + - src/scenes/TitleScene.ts: 名前入力とスタート処理. + - src/ui/UIManager.ts: DOMベースのUIオーバーレイ. + ・packages/shared/ + - src/types/index.ts: ロビー用JSONメッセージの型定義. + + +3. 開発ルール (Development Rules) +------------------------------------------------------------------------ +・ロジックの共通化: + 移動計算式や衝突判定は必ず `packages/shared` に実装し,Client/Server間でコードを共有する. +・検証優先: + 各Step完了ごとに動作確認を行い,バグを次工程に持ち越さない. \ No newline at end of file diff --git "a/docs/04_Spec/SPEC_03_\343\203\227\343\203\255\343\203\210\343\202\277\343\202\244\343\203\227_\347\247\273\345\213\225\343\203\206\343\202\271\343\203\210.txt" "b/docs/04_Spec/SPEC_03_\343\203\227\343\203\255\343\203\210\343\202\277\343\202\244\343\203\227_\347\247\273\345\213\225\343\203\206\343\202\271\343\203\210.txt" new file mode 100644 index 0000000..b4400cd --- /dev/null +++ "b/docs/04_Spec/SPEC_03_\343\203\227\343\203\255\343\203\210\343\202\277\343\202\244\343\203\227_\347\247\273\345\213\225\343\203\206\343\202\271\343\203\210.txt" @@ -0,0 +1,107 @@ +======================================================================== +プロトタイプ仕様書:50人同時移動テスト (Prototype Spec: Movement Test) +======================================================================== + + +1. プロトタイプ概要 (Overview) +------------------------------------------------------------------------ + +1-0. 目的 + 50人のプレイヤーが同じフィールド上で遅延なく移動できる通信基盤を検証する. + 衝突判定,塗り処理,ゲーム進行管理などの付随要素は実装せず,純粋な「移動同期」と「負荷検証」にフォーカスする. + +1-1. 検証範囲 + ・マップ: 100×100マスのグリッドマップ + ・人数: 最大50クライアント同時接続 + ・動作: 360度移動,カメラ追従,他者位置の同期表示 + + +2. クライアント実装仕様 (Client Implementation) +------------------------------------------------------------------------ + +2-0. 目的 + 入力処理,移動計算,および描画の基本ロジックを定義する. + +2-1. 入力・操作系 + ■ ジョイスティック操作 + ・左側エリア: 画面左半分をタッチ可能な移動ジョイスティック領域とする. + ・入力形式: 360°全方位入力. + ・ベクトル正規化: + - 入力ベクトルの長さが1.0を超える場合,1.0に正規化する. + - これにより,斜め移動時の意図しない加速を防止する. + + ■ 誤操作防止 (UX Protection) + ・スクリーンロック: + - ゲーム画面に対するスクロール,拡大縮小(ピンチ操作)を無効化する. + ・エッジデッドゾーン: + - 画面左右の端(10px〜)を入力無効領域とし,OSのジェスチャー機能暴発を防ぐ. + +2-2. 移動・演算ロジック + ■ キャラクター仕様 + ・サイズ: 0.8マス×0.8マス + ・移動速度: 秒速4〜5マス + + ■ 時間管理 (Time Management) + ・DeltaTime対応: + - 毎フレームの移動量計算に「前フレームからの経過時間 (DeltaTime)」を乗算する. + - 計算式: `Position += Velocity * Speed * DeltaTime` + - 目的: 端末のフレームレート(30fps/60fps/120fps)に依存せず,移動速度を一定に保つ. + + ■ 座標管理 + ・内部座標(計算・通信用): + - Float(浮動小数点)で管理し,滑らかな移動を実現する. + ・グリッド座標(表示目安): + - 内部座標の小数点以下を切り捨て(Floor)た値を現在のマスとする. + +2-3. カメラシステム (Camera System) + ■ カメラ追従 (Camera Follow) + ・挙動: + - 常に「自キャラクター」が画面の中央に配置されるよう,カメラ座標を毎フレーム更新する. + - マップ端に到達した場合のクランプ(固定)処理は,本プロトタイプでは実装不要とする(黒背景が見えても良い). + + +3. 通信アーキテクチャ (Network Architecture) +------------------------------------------------------------------------ + +3-0. 目的 + 50人の座標をリアルタイムに同期するためのデータ構造と通信フローを定義する. + +3-1. 通信フローと役割分担 + | カテゴリ | クライアント (Client) | サーバー (Server) | + | :--- | :--- | :--- | + | **自キャラ** | **予測 (Prediction)**: 入力を即時反映し座標を更新・送信. | **中継 (Relay)**: 受信座標を正とし,他者へブロードキャスト. | + | **他キャラ** | **補間 (Interpolation)**: 受信した過去の座標間を滑らかに補間移動. | **間引き (AoI)**: 距離に応じ送信情報を圧縮・除外. | + +3-2. サーバー更新ループ (Server Loop) + ■ ティックレート (Tick Rate) + ・頻度: 20Hz(50ms間隔) + ・処理内容: + 1. 受信バッファ内の全クライアントからの入力を取り出す. + 2. AoI(関心領域)判定を行い,各クライアントに必要なデータをフィルタリングする. + 3. 全クライアントへ「スナップショット」を一斉送信する. + + ■ スナップショット送信 (Snapshot) + ・送信データ: + - 視界範囲内にいる全キャラクターの ID,座標,向き. + - サーバータイムスタンプ(補間計算用). + +3-3. データ構造・最適化 + ■ パケット設計 + ・形式: バイナリパケット(ArrayBuffer等)を採用し,JSON等のテキスト形式は使用しない. + + ■ 座標の量子化 (Quantization) + ・目的: 通信帯域の削減. + ・手法: + - Float座標(0.0〜100.0)を,Unsigned Short(0〜65535)の整数値に変換して送信する. + - 受信側で再度Floatに戻して使用する. + + ■ 送信データ (Input Data) + クライアントからサーバーへ毎フレーム(または間引き)送信するデータ. + ・現在座標 (Position): 物理演算(DeltaTime適用)後の確定座標 (x, y). + ・移動ベクトル (Velocity): 補間予測用の補助データ. + ・角度 (Rotation): キャラクターの向き. + + ■ エリア別同期 (AoI) + ・ロジック: + - 各プレイヤーを中心とした一定範囲(例: 画面サイズの1.5倍)外にいる他プレイヤーの座標データは送信しない. + - これにより,50人全員が動いていても,各端末が受け取るデータ量を視界内のみに限定する. \ No newline at end of file diff --git "a/docs/ENV_01_\347\222\260\345\242\203\346\247\213\347\257\211\343\203\273\346\212\200\350\241\223\343\202\271\343\202\277\343\203\203\343\202\257.txt" "b/docs/ENV_01_\347\222\260\345\242\203\346\247\213\347\257\211\343\203\273\346\212\200\350\241\223\343\202\271\343\202\277\343\203\203\343\202\257.txt" deleted file mode 100644 index ea61c96..0000000 --- "a/docs/ENV_01_\347\222\260\345\242\203\346\247\213\347\257\211\343\203\273\346\212\200\350\241\223\343\202\271\343\202\277\343\203\203\343\202\257.txt" +++ /dev/null @@ -1,151 +0,0 @@ -======================================================================== -Pixel Paint War - 開発環境・技術スタック定義書 -======================================================================== - -1. プロジェクト基本方針 ------------------------------------------------------------------------- - -1-1. アーキテクチャ構成: Monorepo (モノレポ) - ・目的: クライアント(Client)とサーバー(Server)で,言語(TypeScript)およびゲームロジック(移動演算・定数・型定義)を完全共有するため. - ・パッケージ管理: pnpm workspaces を採用. - -1-2. コア・コンセプト - ・言語: TypeScript (Strict mode) - ・通信: WebSocket + Hybrid Protocol - - Core Game (移動・塗り): Custom Binary (DataView) による極小パケット通信 - - Meta Data (ロビー・チャット): JSON (開発効率とデバッグ容易性を優先) - ・描画: WebGL 2D (Pixi.js) - ・同期: サーバー権限 (Authoritative) + クライアント予測 (Prediction) - -1-3. AI活用型開発 (AI-Assisted Development) - ・採用ツール: - - Gemini Pro (学校提供ライセンス) - - GitHub Copilot Pro (GitHub Student Developer Pack) - ・言語選定の優位性: - TypeScriptを採用することで厳密な型定義(Type/Interface)を保持する. - これによりAIがコードの文脈や意図を正確に解釈可能となり, - 型のないJavaScriptと比較して,コード生成・補完・リファクタリングの精度が著しく向上する. - - -2. ディレクトリ構造 (Directory Structure) ------------------------------------------------------------------------- - -2-1. 構成一覧 - root/ - ├── package.json # pnpm workspace 定義 - ├── pnpm-workspace.yaml # ワークスペース設定 - ├── .npmrc # 依存関係解決の設定 - │ - ├── apps/ - │ ├── client/ # 【演出】フロントエンド (Browser) - │ │ ├── src/ - │ │ │ ├── assets/ # 画像・音声リソース - │ │ │ ├── core/ # クライアントの心臓部 (GameApp, MainLoop) - │ │ │ ├── entities/ # 描画用エンティティ (PlayerSprite - 補間・描画ロジック含む) - │ │ │ ├── input/ # 入力処理 (Joystick, Keyboard) - │ │ │ ├── network/ # 通信処理 (SocketClient, Reconciler/補正処理) - │ │ │ ├── scenes/ # 画面管理 (Title, Lobby, Game, Result) - │ │ │ ├── ui/ # HTML UI管理 (HUD, Modal) - │ │ │ └── main.ts # エントリーポイント - │ │ ├── index.html - │ │ ├── vite.config.ts - │ │ └── package.json - │ │ - │ └── server/ # 【権限】バックエンド (Node.js) - │ ├── src/ - │ │ ├── core/ # サーバーの心臓部 (GameLoop, ServerEngine) - │ │ ├── entities/ # サーバー側エンティティ (Player, Item - 状態管理のみ) - │ │ ├── managers/ # 管理クラス (RoomManager, ScoreManager) - │ │ ├── network/ # WebSocket処理 (Connection, PacketHandler) - │ │ └── index.ts # エントリーポイント - │ ├── tsconfig.json - │ └── package.json - │ - └── packages/ - └── shared/ # 【最重要】「真実」の定義場所(型、定数、純粋ロジック) - ├── src/ - │ ├── config/ # ゲーム定数 (マップサイズ, TickRate, 物理定数) - │ ├── protocol/ # 通信規約 (パケット構造, OpCode, バイナリ定義) - │ ├── types/ # 型定義 (PlayerState, InputData, RoomInfo) - │ ├── utils/ # 純粋関数 (Vector計算, 衝突判定, グリッド計算) - │ └── index.ts # エントリーポイント (tsupビルド対象) - ├── tsup.config.ts # ビルド設定 - └── package.json - - ※ shared は client/server 両方から import して使用する. - - -3. 技術スタック詳細 (Tech Stack) ------------------------------------------------------------------------- - -3-1. 共通・基盤 (Common / Shared) - ・Runtime: Node.js (v20 LTS 以上) - ・Package Manager: pnpm - ・Build Tool: tsup (高速で軽量なTypeScriptバンドラ) - ・Serialization: Custom Binary (Standard DataView API) - - 採用理由: ライブラリ依存をなくし、仕様書要件(30KB/s以下)を満たす最適化を行うため。 - - 用途: 座標データ、入力情報の圧縮通信。 - -3-2. フロントエンド (Client) - ・Build Tool: Vite - ・Language: TypeScript - ・Rendering Engine: Pixi.js (v8) - - 採用理由: 50人同時対戦時の大量のスプライト描画と60fps維持のため. - ・UI Library: Preact (または Vanilla HTML/CSS) - - 採用理由: ゲームループへの負荷を避けつつ,軽量なHUDを構築するため. - ・Network: Native WebSocket API - -3-3. バックエンド (Server) - ・Runtime: Node.js - ・Execution: tsx (開発時の高速実行・ウォッチ用) - ・WebSocket Library: ws - - 採用理由: 軽量かつ標準的.uWebSockets.js への移行も視野に入れるが初期は ws で実装. - ・Logic: 独自ループ (20Hz固定) - - Physics Engine: 使用しない (shared/physics.ts による独自グリッド判定) - -3-4. 開発ツール (Dev Tools) - ・Linter: ESLint - ・Formatter: Prettier - ・Test: Vitest (共通ロジックの単体テスト用) - ・AI Assistant: GitHub Copilot Pro, Gemini Pro - - -4. 開発マシンの前提条件 (Prerequisites) ------------------------------------------------------------------------- -以下のツールがインストールされていること. - - 1. Node.js (v20.x LTS) - $ node -v - - 2. pnpm (Corepack enabled or standalone install) - $ pnpm -v - - 3. VS Code (推奨エディタ) - 以下の拡張機能を導入推奨: - - ESLint - - Prettier - Code formatter - - EditorConfig for VS Code - - Hex Editor (バイナリパケットのデバッグ用・Microsoft公式) - - GitHub Copilot (要ログイン確認) - - 4. AI・アカウント環境 - - 学校提供の Gemini Pro へのアクセス権限確認 - - GitHub Copilot Pro (Student) の有効化確認 - - -5. 実装上の重要ルール (Implementation Rules) ------------------------------------------------------------------------- - -5-1. ロジックの一元管理 - - 「移動速度」「ヒット判定」「マップ更新」の計算式は必ず `packages/shared` に記述する. - - Client と Server で別の計算式を書くことを禁止する(同期ズレ防止). - -5-2. 座標系 - - 内部計算: Float (浮動小数点) - - 通信データ: Integer (整数 / 100倍して送信など圧縮を考慮) - - 描画: Float (補間処理あり) - -5-3. 依存方向 - - OK: Client -> Shared - - OK: Server -> Shared - - NG: Client -> Server / Server -> Client (直接参照禁止) \ No newline at end of file diff --git "a/docs/ENV_02_\347\222\260\345\242\203\346\247\213\347\257\211\346\211\213\351\240\206\346\233\270.txt" "b/docs/ENV_02_\347\222\260\345\242\203\346\247\213\347\257\211\346\211\213\351\240\206\346\233\270.txt" deleted file mode 100644 index f8d5e5b..0000000 --- "a/docs/ENV_02_\347\222\260\345\242\203\346\247\213\347\257\211\346\211\213\351\240\206\346\233\270.txt" +++ /dev/null @@ -1,401 +0,0 @@ -======================================================================== -Pixel Paint War - 環境構築ガイド (Environment Setup Guide) -======================================================================== - -1. 事前準備 (Prerequisites) ------------------------------------------------------------------------- - -1-0. 目的 - 本ドキュメントは,「Pixel Paint War」のMonorepo構成による開発環境を構築 - するための手順書である. - ※ 本プロジェクトは Node.js v20 LTS 以上を必須とする. - -1-1. 必須ツールのインストール - 開発を開始する前に,以下のツールをインストールしバージョンを確認する. - - 1. Node.js (v20.x LTS) - ・Nodesource リポジトリを使用してインストールする. - # リポジトリのセットアップとインストール - $ curl -fsSL https://deb.nodesource.com/setup_20.x | sudo -E bash - - $ sudo apt-get install -y nodejs - - ・確認コマンド: - $ node -v # v20.x.x と表示されること - - 2. pnpm (Package Manager) - ・Node.js 標準の npm ではなく pnpm を使用する. - ・Corepack (Node.js同梱) を有効化してインストールする. - $ sudo corepack enable - $ corepack prepare pnpm@latest --activate - - ・確認コマンド: - $ pnpm -v - - -2. プロジェクト初期化 (Project Initialization) ------------------------------------------------------------------------- - -2-1. ディレクトリ作成と初期化 - 1. プロジェクトルートの作成 - 任意の場所にプロジェクトフォルダを作成し,移動する. - $ mkdir SkillSemiWebGame - $ cd SkillSemiWebGame - - 2. Gitの初期化 - $ git init - - 3. pnpm の初期化 - $ pnpm init - -2-2. ワークスペース設定 (Monorepo Setup) - ルートディレクトリに以下の設定ファイルを作成し,モノレポ構成を定義する. - - 1. pnpm-workspace.yaml - ・packages/shared を共通ライブラリとし,apps 配下にアプリを配置する. - ・内容: - packages: - - 'apps/*' - - 'packages/*' - - 2. .npmrc - ・依存関係解決の設定を行う (shamefully-hoist=true 推奨). - ・内容: - shamefully-hoist=true - -2-3. ディレクトリ構造の構築 - 以下の構成になるようにディレクトリを作成する. - - root/ - ├── apps/ - │ ├── client/ # フロントエンド (Browser) - │ └── server/ # バックエンド (Node.js) - └── packages/ - └── shared/ # 共通ロジック (Shared Library) - - ・作成コマンド例: - $ mkdir -p apps/client apps/server packages/shared - -2-4. Git除外設定 (Git Ignore Setup) - 不要なファイル(依存ライブラリやビルド成果物)がGit管理下に置かれないよう, - 除外設定を行う. - - 1. 設定ファイルの作成 - プロジェクトルートディレクトリに `.gitignore` ファイルを作成する. - $ touch .gitignore - - 2. 除外ルールの記述 - 以下の内容をファイルに記述し保存する. - ・node_modules: 依存ライブラリフォルダ. - ・dist, build: ビルド生成物. - ・.env: 環境変数ファイル(セキュリティ保持のため). - - # Dependencies - node_modules/ - .pnpm-store/ - - # Build Outputs - dist/ - build/ - out/ - - # Logs - *.log - npm-debug.log* - pnpm-debug.log* - - # Environment Variables - .env - .env.local - .env.*.local - - # Editor / OS - .vscode/* - !.vscode/extensions.json - !.vscode/settings.json - !.vscode/launch.json - .idea/ - .DS_Store - Thumbs.db - - # Testing - coverage/ - - # Unignore packages (Fix for parent gitignore) - !packages/ - - 3. 設定の反映確認 - Gitのステータスを確認し,`node_modules/` 等が含まれていないことを確認する. - $ git status - -2-5. 初回コミット (Initial Commit) - 環境構築の区切りとして,現在の状態をリポジトリに保存する. - - 1. ステータス確認 - `.gitignore` が正しく適用されているか確認する. - $ git status - ※ `node_modules/` が表示されていないことを確認する. - - 2. ステージング - 変更された全てのファイルをコミット対象に追加する. - $ git add . - - 3. コミット実行 - 構築内容を示すメッセージを付与してコミットする. - $ git commit -m "chore: Project initialization (Monorepo, pnpm, Vite)" - -3. パッケージ・ライブラリ導入 (Dependency Installation) ------------------------------------------------------------------------- - -3-1. 共通ライブラリ (packages/shared) - 共通ロジック用のパッケージ設定を行う. - - 1. 初期化とビルドツール導入 - $ cd packages/shared - $ pnpm init - $ pnpm add -D typescript tsup - - 2. 設定ファイルの調整 (package.json) - ・name: "@repo/shared" と命名する(推奨). - ・main: "./dist/index.js", types: "./dist/index.d.ts" を指定する. - ・scripts: "build": "tsup src/index.ts --format cjs,esm --dts" を追加する. - - 3. エントリーポイントの作成 - tsupがビルド対象とするファイルを作成する. - - $ mkdir src - $ touch src/index.ts - - ※ 現時点では空ファイルでよいが,将来的に constants.ts 等を export する記述を行う. - (例: export * from './constants';) - - 4. TypeScript設定ファイルの作成 (tsconfig.json) - ビルドと型定義生成のための設定ファイルを作成する. - ・ファイル: packages/shared/tsconfig.json - ・内容: - { - "compilerOptions": { - "target": "ES2020", - "module": "ESNext", - "moduleResolution": "Bundler", - "lib": ["ES2020", "DOM", "DOM.Iterable"], - "declaration": true, - "declarationMap": true, - "sourceMap": true, - "outDir": "./dist", - "rootDir": "./src", - "strict": true, - "esModuleInterop": true, - "skipLibCheck": true, - "forceConsistentCasingInFileNames": true - }, - "include": ["src/**/*"], - "exclude": ["node_modules", "dist"] - } - -3-2. フロントエンド (apps/client) - Vite プロジェクトとして初期化を行う. - - 1. プロジェクト作成 - $ cd ../../apps/client - $ pnpm create vite . --template preact-ts - ※ 実行中に表示される選択肢には以下のように回答すること: - ? Use rolldown-vite (Experimental)? » No - ? Install with pnpm and start now? » No - - 2. 依存ライブラリのインストール - ・Pixi.js (描画エンジン) を追加する. - ・共通ライブラリへの依存を追加する. - $ pnpm add pixi.js - $ pnpm add @repo/shared --workspace - -3-3. バックエンド (apps/server) - Node.js アプリケーションとして初期化を行う. - - 1. 初期化 - $ cd ../../apps/server - $ pnpm init - - 2. 依存ライブラリのインストール - ・ws (WebSocket) を追加する. - ・開発用ツール (tsx, typescript, @types/node, @types/ws) を追加する. - ・共通ライブラリへの依存を追加する. - $ pnpm add ws - $ pnpm add -D tsx typescript @types/node @types/ws - $ pnpm add @repo/shared --workspace - - 3. サーバー用ディレクトリとファイルの作成 - tsxが実行対象とするエントリーポイントを作成する. - $ mkdir src - $ touch src/index.ts - - 4. 実行スクリプトの定義 - package.json にサーバー起動用のコマンドを追加する. - ・編集ファイル: apps/server/package.json - ・内容: - "scripts": { - "dev": "tsx watch src/index.ts" - } - - 5. TypeScript設定ファイルの作成 (tsconfig.json) - 開発時の実行環境とパス解決のための設定ファイルを作成する. - ・ファイル: apps/server/tsconfig.json - ・内容: - { - "compilerOptions": { - "target": "ES2022", - "module": "NodeNext", - "moduleResolution": "NodeNext", - "lib": ["ES2022"], - "strict": true, - "noEmit": true, - "esModuleInterop": true, - "skipLibCheck": true, - "forceConsistentCasingInFileNames": true, - "baseUrl": ".", - "paths": { - "@repo/shared": ["../../packages/shared/src/index.ts"] - } - }, - "include": ["src/**/*"], - "exclude": ["node_modules"] - } - - -4. 開発ツール設定 (Dev Tools Setup) ------------------------------------------------------------------------- - -4-1. VS Code 拡張機能 - 推奨エディタである VS Code に以下の拡張機能をインストールする. - - ■ 必須拡張機能 - ・ESLint - ・Prettier - Code formatter - ・EditorConfig for VS Code - - ■ 推奨拡張機能 - ・Hex Editor (バイナリパケットのデバッグ用・Microsoft公式) - ・GitHub Copilot - -4-2. AI アシスタント設定 - 開発効率化のため,以下のAIツールのアカウント設定を確認する. - - 1. Gemini Pro - ・学校提供ライセンスでのアクセス権限を確認する. - - 2. GitHub Copilot Pro - ・Student Developer Pack が有効化されているか確認する. - ・VS Code 右下のアイコンからログイン状態を確認する. - - -5. 構成確認 (Configuration Check) ------------------------------------------------------------------------- - -5-1. 最終ディレクトリ構成 - 構築完了時点で,以下のディレクトリおよびファイルが存在することを確認する. - - SkillSemiWebGame/ <-- プロジェクトルート - ├── .git/ <-- git init で作成 - ├── .gitignore <-- Git除外設定 - ├── .npmrc <-- 依存解決設定 - ├── package.json <-- ルート定義 - ├── pnpm-lock.yaml <-- pnpm install で自動生成 - ├── pnpm-workspace.yaml <-- ワークスペース定義 - ├── node_modules/ <-- 依存ライブラリ - │ - ├── apps/ <-- アプリケーション格納用 - │ ├── client/ <-- フロントエンド (Vite + Preact) - │ │ ├── node_modules/ - │ │ ├── src/ - │ │ │ ├── main.tsx (または index.tsx) - │ │ │ └── ... (Viteテンプレートファイル群) - │ │ ├── index.html - │ │ ├── package.json <-- pixi.js, @repo/shared 依存あり - │ │ ├── tsconfig.json - │ │ └── vite.config.ts - │ │ - │ └── server/ <-- バックエンド (Node.js) - │ ├── node_modules/ - │ ├── src/ - │ │ └── index.ts <-- エントリーポイント - │ ├── package.json <-- ws, @repo/shared 依存あり - │ └── tsconfig.json <-- pnpm init 等で生成(または要作成) - │ - └── packages/ <-- 共通パッケージ格納用 - └── shared/ <-- 共通ロジック - ├── node_modules/ - ├── dist/ <-- ビルド後に生成される (index.js, index.d.ts) - ├── src/ - │ └── index.ts <-- 空または定数export用 - ├── package.json <-- buildスクリプト定義あり - └── tsconfig.json <-- tsup/typescript設定用 - -5-2. 重要ファイル設定確認 - 各パッケージの連携設定が正しいか確認する. - - ■ root/pnpm-workspace.yaml - packages: - - 'apps/*' - - 'packages/*' - - ■ packages/shared/package.json - ・name: "@repo/shared" - ・main: "./dist/index.js" - ・types: "./dist/index.d.ts" - - ■ apps/client/package.json - ・dependencies: - "@repo/shared": "workspace:*" - - ■ apps/server/package.json - ・dependencies: - "@repo/shared": "workspace:*" - - -6. 動作確認 (Verification) ------------------------------------------------------------------------- - -6-1. ビルド確認 - ルートディレクトリから全体の依存関係をインストールし,ビルドを試行する. - - $ cd ../../ - $ pnpm install - $ pnpm --filter @repo/shared build - - ※ shared のビルドが成功することを確認する. - -6-2. 開発サーバー起動 - モノレポ構成のため,個別のディレクトリに移動せず,プロジェクトルートから - --filter オプションを使用して各アプリを起動する. - ※ ターミナルを2つ開き,両方を同時に起動した状態で開発を進めることを推奨. - - 1.Client (フロントエンド) の動作確認 - ・ルートディレクトリにて以下のコマンドを実行する. - $ pnpm --filter client dev - - ・ブラウザでの確認: - ターミナルに「➜ Local: http://localhost:5173/」と表示されたら, - Google Chrome等のブラウザを開き,アドレスバーに上記URLを貼り付けて実行する. - - ・正常動作の判断基準: - 画面に「Vite + Preact」のロゴと「Vite + Preact + TypeScript」といった - テキストが表示されていれば,フロントエンドの環境構築は成功である. - - 2. Server (バックエンド) の動作確認 - ・テスト用コードの作成: - 動作確認用のエントリーポイントを作成する. - $ touch apps/server/src/index.ts - - ファイルに以下の内容を記述する. - console.log("Server is running!"); - - ・コマンド: - $ pnpm --filter server dev - - ・正常動作の判断基準: - ターミナルに「Server is running!」と出力されれば構築成功である. - - 3.終了方法 (重要) - ・動作確認を終了し,開発サーバーを停止させる場合は,ターミナル上で - 「Ctrl + C」を押下する. - ・停止後はブラウザでURLにアクセスしても接続不可となるが,再度起動 - コマンドを実行すればいつでも再開可能である. \ No newline at end of file diff --git "a/docs/ENV_03_TypeScript\346\246\202\350\246\201.txt" "b/docs/ENV_03_TypeScript\346\246\202\350\246\201.txt" deleted file mode 100644 index e489c79..0000000 --- "a/docs/ENV_03_TypeScript\346\246\202\350\246\201.txt" +++ /dev/null @@ -1,90 +0,0 @@ -======================================================================== -TypeScript概要 (TypeScript Overview) -======================================================================== - -1. 概要 (Overview) ------------------------------------------------------------------------- -本プロジェクト(Pixel Paint War)において採用するプログラミング言語「TypeScript」に関する基礎知識,選定理由,およびAI活用開発における優位性を定義する. -本ドキュメントは,開発チーム内での技術認識の統一を目的とする. - - -2. TypeScriptとは (What is TypeScript) ------------------------------------------------------------------------- -Microsoftによって開発されたオープンソースのプログラミング言語である.JavaScriptのスーパーセット(上位互換)として設計されており,大規模なアプリケーション開発に適した機能が拡張されている. - -2-1. JavaScriptとの違い - ・静的型付け (Static Typing): - 変数や関数の引数,戻り値に「型(Type)」を指定できる.JavaScriptは動的型付け言語であり,実行時まで型が決まらないが,TypeScriptはコンパイル(トランスパイル)時に整合性をチェックする. - ・クラスベースオブジェクト指向: - インターフェース(Interface),ジェネリクス(Generics),アクセス修飾子(public/private)など,JavaやC#に近いオブジェクト指向構文をサポートする. - ・コンパイルの必要性: - ブラウザやNode.jsはTypeScriptを直接実行できないため,JavaScriptファイルへ変換(トランスパイル)して使用する. - -2-2. 一般的な利用目的 - ・大規模Webアプリケーション開発: - コード量が増えても型定義により保守性を維持しやすい. - ・チーム開発: - 型定義がそのまま「仕様書」としての役割を果たし,メンバー間の認識齟齬を防ぐ. - ・フルスタック開発: - フロントエンド(React/Vue/Angular等)とバックエンド(Node.js/Deno等)で言語を統一し,型定義を共有する. - - -3. 言語の強み (Strengths) ------------------------------------------------------------------------- - -3-1. 安全性と品質向上 - ・コンパイルエラーによる早期発見: - 「undefinedのプロパティ参照」や「数値と文字列の誤った演算」など,JavaScriptで頻発する実行時エラーを,コードを書いている段階(コンパイル時)で検出できる. - -3-2. 開発効率の向上 - ・強力な入力補完 (IntelliSense): - VS Code等のエディタにおいて,型情報を元にした正確なコード補完,メソッドの候補表示,定義元へのジャンプが可能となる. - ・リファクタリングの容易さ: - 変数名や関数名の変更を行っても,依存する箇所をエディタが一括で修正・検知できるため,改修コストが低い. - - -4. AI活用型開発における利点 (Benefits in AI-Assisted Development) ------------------------------------------------------------------------- -本プロジェクトの方針である「AI活用型開発(Gemini Pro / GitHub Copilot Pro)」において,TypeScriptはJavaScriptと比較して以下の決定的な優位性を持つ. - -■ コンテキストの正確な伝達 - 型定義(Type/Interface)が存在することで,AIは変数の意図やデータ構造を推測ではなく「確定情報」として認識できる.これにより,提案されるコードの精度が向上する. - -■ ハルシネーション(嘘の生成)の抑制 - 存在しないプロパティや誤ったメソッドをAIが提案した場合でも,TypeScriptのコンパイラが即座にエラーを出すため,誤ったコードが実装に含まれるリスクを自動的に排除できる. - -■ 意図の明示化 - 「ENV_01」で定義された `packages/shared` のような共通型定義を参照させることで,AIはクライアント・サーバー間の通信仕様を正確に理解し,一貫性のあるロジックを生成可能となる. - - -5. 歴史と現状 (History and Current Status) ------------------------------------------------------------------------- - -5-1. 歴史 - ・開発者: Anders Hejlsberg(C#やTurbo Pascalの設計者)らが中心となり開発. - ・初版公開: 2012年10月. - ・背景: 当時,大規模化するWebアプリ開発においてJavaScriptの仕様(ES5)では保守が困難であったため,静的型付けの需要が高まっていた. - -5-2. 現在のステータス - ・世界No.1の使用率 (GitHub Octoverse 2025): - 2025年のGitHub年次レポートにおいて,長年トップであったPythonおよびJavaScriptを上回り,世界で最も使用されている言語(第1位)となった. - このランキングは,単なるコードの総量ではなく「貢献者数(Unique Contributors)」に基づいており,現在世界中で最も多くのアクティブユーザーが開発を行っている言語であることを示している. - ・デファクトスタンダード: - 現在,モダンなフロントエンド開発(React, Next.js, Vue.jsなど)において,TypeScriptは標準的な選択肢となっている. - ・普及率: - 「State of JS」などの開発者アンケートにおいて,長年「使用率」および「満足度」で上位を維持している.また,Google社内の標準言語としても採用されている(Alligator等). - - -6. 参考文献 (References) ------------------------------------------------------------------------- -・TypeScript Official Website - https://www.typescriptlang.org/ - -・The State of JS 2022/2023 (Usage & Satisfaction) - https://stateofjs.com/ - -・GitHub Octoverse 2025 - https://octoverse.github.com/ - -・Google Engineering Practices Documentation - https://google.github.io/eng-practices/ \ No newline at end of file diff --git "a/docs/ENV_04_\343\202\271\343\203\236\343\203\233\345\256\237\346\251\237\343\203\207\343\203\220\343\203\203\343\202\260\346\211\213\351\240\206.txt" "b/docs/ENV_04_\343\202\271\343\203\236\343\203\233\345\256\237\346\251\237\343\203\207\343\203\220\343\203\203\343\202\260\346\211\213\351\240\206.txt" deleted file mode 100644 index b609f72..0000000 --- "a/docs/ENV_04_\343\202\271\343\203\236\343\203\233\345\256\237\346\251\237\343\203\207\343\203\220\343\203\203\343\202\260\346\211\213\351\240\206.txt" +++ /dev/null @@ -1,69 +0,0 @@ -======================================================================== -スマホ実機デバッグ手順 (Smartphone Debugging Guide) -======================================================================== - - -1. 基本手順 (Basic Steps) ------------------------------------------------------------------------- - -1-1. 事前準備と起動 (Preparation & Launch) - ・PC とスマホを同一の Wi-Fi ネットワークに接続する. - ・VS Code でターミナルを開く (`Ctrl + @`). - ・以下のコマンドを実行し,ホストモードで開発サーバーを起動する. - $ pnpm --filter client dev -- --host - ・ターミナルに表示された「Network」の URL を確認する. - - 例: http://192.168.1.10:5173 - - ※ Vite のデフォルトポートは 5173 だが,状況により異なる場合がある. - -1-2. PC の IP アドレス確認 (Check IP Address) - ・ターミナルに表示された Network URL (例: 192.168.1.10) を使用する. - ・表示されない場合は以下の手順で確認する. - - ■ Windows の場合 - 1. Win + R キーを押し,「cmd」と入力して Enter キーを押下する. - 2. コマンドプロンプトで以下のコマンドを実行する. - $ ipconfig - 3. 表示された「IPv4 アドレス」の数値を控える. - - ■ Mac の場合 - 1. 「システム設定」>「ネットワーク」を開く. - 2. 接続中の Wi-Fi の「詳細」をクリックし,IP アドレスを確認する. - -1-3. スマホからのアクセス (Access from Smartphone) - ・スマホのブラウザ(Safari,Chrome 等)を起動する. - ・アドレスバーに以下の形式で URL を入力し,アクセスする. - - 書式: http://[PCのIPアドレス]:[ポート番号] - - 例: http://192.168.1.10:5173 - - -2. トラブルシューティング (Troubleshooting) ------------------------------------------------------------------------- - -2-1. 接続できない場合の確認事項 - ■ ネットワーク設定 - ・PC とスマホが同じ Wi-Fi に接続されているか確認する. - - ※ ゲスト用 Wi-Fi など,機器間の通信が遮断されているネットワークでは接続できない. - - ■ ファイアウォール設定 - ・PC のセキュリティソフトやファイアウォールが,外部からの接続をブロックしている可能性がある. - - 対策: 一時的にファイアウォールを無効化するか,Node.js (node.exe) の通信を許可する設定を追加する. - - ■ WebSocket 接続エラー (Game Loop が動かない場合) - ・クライアントコード (`apps/client/src/config` 等) の接続先設定を確認する. - ・接続先が `ws://localhost:xxxx` の場合,スマホからは接続できない. - - 対策: PC の IP アドレス (例: `ws://192.168.1.10:xxxx`) に書き換える. - - -3. 外部ネットワークからの接続 (Port Forwarding) ------------------------------------------------------------------------- - -3-0. 概要 - ・VSCode 標準のポート転送機能を使用し,異なるネットワーク(4G/5G や外部 Wi-Fi)からデバッグを行う手順. - -3-1. 設定手順 - 1. VSCode 下部パネルの「ポート (Ports)」タブを選択する. - 2. 「ポートの追加」ボタンを押し,Live Server のポート番号(例: 5500)を入力する. - 3. 追加されたポートの「可視性 (Visibility)」列を右クリックし,「パブリック (Public)」に変更する. - 4. 「転送されたアドレス」列に表示された URL をコピーする. - - 書式: https://[ランダムな文字列].vscode-server.net... - 5. 発行された URL をスマホに送り,ブラウザで開く. \ No newline at end of file diff --git "a/docs/GUIDE_01_\343\203\211\343\202\255\343\203\245\343\203\241\343\203\263\343\203\210\344\275\234\346\210\220\343\202\254\343\202\244\343\203\211.txt" "b/docs/GUIDE_01_\343\203\211\343\202\255\343\203\245\343\203\241\343\203\263\343\203\210\344\275\234\346\210\220\343\202\254\343\202\244\343\203\211.txt" deleted file mode 100644 index 07dd34b..0000000 --- "a/docs/GUIDE_01_\343\203\211\343\202\255\343\203\245\343\203\241\343\203\263\343\203\210\344\275\234\346\210\220\343\202\254\343\202\244\343\203\211.txt" +++ /dev/null @@ -1,96 +0,0 @@ -======================================================================== -ドキュメント作成ガイドライン (Style Guide) -======================================================================== - -1. 基本フォーマット (Basic Format) ------------------------------------------------------------------------- -・文字コード: UTF-8 -・改行コード: LF (推奨) または CRLF -・インデント: 半角スペース4つ (4 spaces) - - タブ文字は使用せず、スペースに展開して揃える. - -■ ファイルヘッダー (File Header) -・ファイルの先頭には必ずタイトルブロックを記述する. -・書式: 上下を「=」(イコール)の列(72文字程度)で挟む. -・例: - ======================================================================== - ドキュメントタイトル (English Title) - ======================================================================== - - -2. 句読点・約物 (Punctuation) ------------------------------------------------------------------------- -・句読点: 「,」(全角カンマ)と「.」(全角ピリオド)を使用する. - - 「、」「。」は使用しない. -・コロン: 半角コロン+半角スペース「: 」を使用する. - - NG: 全角コロン「:」,スペースなし「:」 -・括弧: 原則として半角括弧 `( )` を使用するが、強調や補足には全角 `( )` や `「 」` も許容する. -・注釈: 文末や段落末の補足には「※」(全角米印)+半角スペースを使用する. - - 例: ※ shared は client/server 両方から import して使用する. - - -3. 階層構造と見出し (Headings & Hierarchy) ------------------------------------------------------------------------- - -3-1. レベル1:大見出し (Section) - ・書式: 数字 + ドット + 半角スペース + タイトル + (英語タイトル) - ・装飾: 下行にハイフン「-」による区切り線を挿入する. - ・例: - 1. 基本設計 (Basic Design) - ------------------------------------------------------------------------ - -3-2. レベル2:中見出し (Subsection) - ・書式: 数字-数字 + ドット + 半角スペース + タイトル - ・例: - 1-1. 製品概要 - -3-3. レベル3:小見出し (Group Heading) - ・書式: 「■」+ 半角スペース + タイトル - ・使い分け: - - セクション内で独立したトピック(カテゴリ)を列挙する場合は「■」を使用する. - - 手順やフロー、順序のある項目を示す場合は「1. 」「2. 」を使用する. - - A. 並列・カテゴリ列挙(順序不問) - - 記号: 「■ 」(全角四角+半角スペース) - - 例: ■ フィールド仕様 - - B. 手順・優先順位・ランキング(順序重要) - - 記号: 「1. 」「2. 」(半角数字+ドット+半角スペース) - - 例: 1. ユーザ体験の理想 - -3-4. レベル4:リスト項目 (List Item) - ・記号: 「・」(全角中黒) - ・書式: 「・項目名: 内容」または「・項目名」のみ. - ・例: - ・タイトル: Paint War - -3-5. レベル5:詳細項目 (Detail Item) - ・記号: 「- 」(半角ハイフン+半角スペース) - ・インデント: 親項目のテキスト開始位置に合わせる(基本はスペース8つ). - ・例: - ・親項目 (Level 4) - - 子項目: 詳細内容 (Level 5) - -3-6. 特殊なナンバリング (Zero Indexing) - ・目的定義: セクションの冒頭で目的や定義を述べる場合、「X-0. 目的」というナンバリング(ゼロ始まり)を使用してもよい. - - 例: 1-0. 目的 - -3-7. 階層の順守 - ・上位レベルから下位レベルへ順に記述し,階層を飛ばさないこと. - - NG例: レベル1(1. XX)の直下にレベル3(■ XX)を記述する. - - 対策: 必要に応じてレベル2(1-1. 概要 等)を設ける. - - -4. 余白・改行ルール (Spacing) ------------------------------------------------------------------------- -・大見出しの上: 2行空ける. -・中見出し(X-X)の上: 1行空ける. -・小見出し(■や数字)の上: 1行空ける. -・セクション内のリスト: 原則として行間を詰め、まとまりごとに適宜空行を入れる. - - -5. 技術記述・コード表記 (Technical & Code) ------------------------------------------------------------------------- -・コマンドライン: 先頭に `$ ` を付与して区別する. -・ディレクトリ構造: ツリー記号(`├──`, `│`, `└──`)を使用し,ルートディレクトリからの階層を示す. -・インデント: コードブロック内は,親の箇条書きレベルに合わせて開始位置を揃える. \ No newline at end of file diff --git "a/docs/GUIDE_02_\343\203\225\343\202\241\343\202\244\343\203\253\345\221\275\345\220\215\350\246\217\345\211\207.txt" "b/docs/GUIDE_02_\343\203\225\343\202\241\343\202\244\343\203\253\345\221\275\345\220\215\350\246\217\345\211\207.txt" deleted file mode 100644 index c47a0e1..0000000 --- "a/docs/GUIDE_02_\343\203\225\343\202\241\343\202\244\343\203\253\345\221\275\345\220\215\350\246\217\345\211\207.txt" +++ /dev/null @@ -1,53 +0,0 @@ -======================================================================== -ドキュメント管理・ファイル命名規則 (File Naming Conventions) -======================================================================== - -1. 命名の基本方針 (Basic Policy) ------------------------------------------------------------------------- -プロジェクトの規模拡大に伴うファイルの散乱を防ぎ,開発メンバーおよびAI(Gemini/Copilot)がファイルの内容・文脈を即座に特定できるようにするため,以下の規則を適用する. - -■ 基本フォーマット -`[カテゴリ]_[連番]_[ファイル名].txt` - -・区切り文字: アンダースコア `_` を使用する. -・連番: 01から始まる2桁の数字とする. -・拡張子: プレーンテキスト `.txt` とする. - - -2. カテゴリ定義 (Category Definitions) ------------------------------------------------------------------------- -ファイル名の先頭に付与するプレフィックス(接頭辞)定義. - -■ GUIDE_ (Guide) -・内容: チーム全体のルール,規約,運用フローなど,「メタ情報」に関する定義. -・対象例: スタイルガイド,命名規則,Git運用ルール. - -■ PLAN_ (Planning) -・内容: プロジェクトの進行計画,スケジュール,要件定義など,「管理・進行」に関する定義. -・対象例: WBS,ロードマップ,要件定義書,タスク一覧. - -■ ENV_ (Environment) -・内容: 開発環境,ディレクトリ構造,ライブラリ選定など,プロジェクトの「土台」に関する定義. -・対象例: 環境構築手順,技術スタック一覧,パッケージ構成図. - -■ SPEC_ (Specification) -・内容: 企画,ゲームルール,UI/UXなど,ユーザーから見える「仕様」に関する定義. -・対象例: ゲーム企画書,画面遷移図,パラメータ設定(マップサイズ・速度など). - -■ TECH_ (Technical) -・内容: 実装詳細,アルゴリズム,データ構造など,エンジニア向けの「技術設計」に関する定義. -・対象例: 通信プロトコル仕様,同期ロジック,データベース設計,クラス設計. - -■ TEST_ (Test) -・内容: テスト計画,テストケース,品質保証手順など,「検証・品質」に関する定義. -・対象例: 単体テスト仕様書,シナリオテスト計画,テストケース一覧,品質基準. - - -3. 運用ルール (Operational Rules) ------------------------------------------------------------------------- -・1ファイル1テーマ: - ファイルサイズが肥大化しすぎないよう,トピック(例: 通信仕様,判定ロジック)ごとにファイルを分割することを推奨する. - これにより,AIへのコンテキスト入力精度が向上する. - -・スタイルの継承: - 新規作成するファイルも,必ず `GUIDE_01_スタイルガイド.txt` に記載された書式(見出し,句読点「,.」等)に従うこと. \ No newline at end of file diff --git "a/docs/GUIDE_03_Git\351\201\213\347\224\250\343\203\253\343\203\274\343\203\253.txt" "b/docs/GUIDE_03_Git\351\201\213\347\224\250\343\203\253\343\203\274\343\203\253.txt" deleted file mode 100644 index 8b5bf95..0000000 --- "a/docs/GUIDE_03_Git\351\201\213\347\224\250\343\203\253\343\203\274\343\203\253.txt" +++ /dev/null @@ -1,125 +0,0 @@ -======================================================================== -Git運用ルール (Git Operation Rules) -======================================================================== - -1. 基本方針 (Basic Policy) ------------------------------------------------------------------------- -チーム開発におけるコードの整合性を保ち,手戻りを防ぐために以下の運用フローを徹底する. - -・メインブランチ (main): - - 本番環境または常に動作可能な状態を維持するブランチ. - - 直接のコミット(直プッシュ)は禁止する.必ずプルリクエスト(PR)経由でマージする. -・作業ブランチ (Feature Branch): - - 機能追加やバグ修正ごとに `main` から派生させて作成する. - - 作業完了後,`main` へマージし,原則として削除する. - - -2. ブランチ命名規則 (Branch Naming) ------------------------------------------------------------------------- -2-1. プレフィックス (Prefix) -作業の種類を一目で判別するために,以下のプレフィックスを使用する. - -■ カテゴリ一覧 - ・feature/: 新機能の実装,仕様変更 - ・fix/: バグ修正 - ・refactor/: コードの整理(挙動は変えない) - ・docs/: ドキュメントの追記・修正 - ・chore/: ビルド設定やツール導入など,雑多な作業 - -2-2. 書式 (Format) - ・書式: `[プレフィックス][日付(YYMMDD)]_[概要]` - ・区切り: スラッシュ `/` および アンダースコア `_` を使用する. - ・例: - - feature/260207_player_jump - - fix/260208_collision_bug - - docs/260210_guide_update - - -3. 開発フロー (Development Workflow) ------------------------------------------------------------------------- -作業を開始してからマージされるまでの手順. - -1. ローカルの最新化 - ・作業開始前は必ず `main` ブランチに切り替え,リモートの最新状態を取り込む. - ・コマンド: - $ git checkout main - $ git pull origin main - -2. 作業ブランチの作成 - ・最新の `main` から新しいブランチを作成して移動する. - ・コマンド: - $ git checkout -b feature/01_new_function - -3. 実装とコミット - ・作業単位(意味のあるまとまり)ごとにコミットする. - ・巨大なコミットは避け,レビューしやすい粒度を心がける. - ・コマンド: - $ git add . - $ git commit -m "[add] 新機能を実装" - -4. リモートへのプッシュ - ・作業ブランチをリモートリポジトリへ送信する. - ・コマンド: - $ git push origin feature/01_new_function - -5. プルリクエスト (PR) の作成 - ・GitHubのリポジトリ画面上部に表示される「Compare & pull request」ボタンをクリックする. - ・Baseを `main`、Compareを自分の「作業ブランチ」に設定する. - ・「Reviewers」メニューからチームメンバーを選択し、レビューを依頼する. - ・「Create pull request」ボタンを押してPRをオープンする. - -6. レビューと修正の対応 - ・レビュワーのコメントを確認し、修正が必要な場合はローカルで修正・コミット・プッシュを繰り返す. - ・GitHub上で全ての指摘に対し「Resolve conversation」を行い、やり取りを完了させる. - ・レビュワーから「Approve(承認)」のスタンプまたはメッセージをもらう. - -7. マージの実行(マージボタンの操作) - ・PR画面下部の「Merge pull request」ボタンをクリックする. - ・確認用の「Confirm merge」ボタンを押し、`main` への統合を完了させる. - ・マージ直後に表示される「Delete branch」ボタンを押し、リモート上の作業ブランチを削除する. - -8. ローカル環境のクリーンアップ - ・マージ完了後はローカル環境も最新状態に戻し、古いブランチを削除する. - $ git checkout main - $ git pull origin main - $ git branch -d [作業ブランチ名] - - -4. コミットメッセージ (Commit Messages) ------------------------------------------------------------------------- -4-1. 書式 - ・書式: `[タグ] 内容` - ・言語: 日本語 (Japanese) - ・句読点: 末尾に句点は不要. - -4-2. タグ一覧 - ・[add]: ファイルや機能の追加 - ・[update]: 機能やデータの更新・修正 - ・[fix]: バグ修正 - ・[remove]: 削除 - ・[clean]: 整理,リファクタリング - - -5. トラブルシューティング (Troubleshooting) ------------------------------------------------------------------------- -■ コンフリクト (Conflict) が発生した場合 -他メンバーの変更と競合した場合の対処手順. - -1. main の取り込み - ・作業ブランチに `main` の最新内容をマージして競合箇所を洗い出す. - ・コマンド: - $ git checkout main - $ git pull origin main - $ git checkout feature/XX_working - $ git merge main - -2. 競合の解消 - ・エディタ上で `<<<<<<<`, `=======`, `>>>>>>>` で囲まれた箇所を手動で修正する. - ・修正後,再度コミットしてプッシュする. - -■ 間違えて main にコミットしてしまった場合 - ・まだプッシュしていない場合,コミットを取り消して新しいブランチへ移動させる. - ・コマンド: - $ git reset --soft HEAD^ - $ git checkout -b feature/XX_recover_branch - $ git commit -m "..." \ No newline at end of file diff --git "a/docs/PLAN_01_\347\247\273\345\213\225\343\203\206\343\202\271\343\203\210\345\256\237\350\243\205\350\250\210\347\224\273.txt" "b/docs/PLAN_01_\347\247\273\345\213\225\343\203\206\343\202\271\343\203\210\345\256\237\350\243\205\350\250\210\347\224\273.txt" deleted file mode 100644 index 262bd72..0000000 --- "a/docs/PLAN_01_\347\247\273\345\213\225\343\203\206\343\202\271\343\203\210\345\256\237\350\243\205\350\250\210\347\224\273.txt" +++ /dev/null @@ -1,79 +0,0 @@ -======================================================================== -Pixel Paint War - プロトタイプ実装計画 (Prototype Implementation Plan) -======================================================================== - -1. 概要 (Overview) ------------------------------------------------------------------------- -本ドキュメントは,「SPEC_03_プロトタイプ_移動テスト.txt」で定義された50人同時接続テストを達成するための段階的な実装ロードマップである. -複雑性を排除するため,最小構成から機能を積み上げる(Step-by-Step)方式を採用する. - - -2. 実装フェーズ定義 (Implementation Phases) ------------------------------------------------------------------------- - -2-1. Step 1: クライアント単体移動 (Local Movement) - ■ 目標 - サーバーを介さず,ブラウザ上でジョイスティック操作によりキャラクターが移動・描画されること. - - ■ 実装対象 - ・packages/shared/ - - src/config/gameConfig.ts: マップサイズ,移動速度等の定数定義. - - src/utils/math.ts: ベクトル計算,移動ロジック (Pos += Vel * Speed * DT). - ・apps/client/ - - src/input/Joystick.ts: タッチ入力の正規化,デッドゾーン処理. - - src/entities/PlayerSprite.ts: 描画更新処理. - - src/core/GameLoop.ts: Pixi.js Tickerを用いたメインループ. - -2-2. Step 2: サーバー開通・単体通信 (Single Player Network) - ■ 目標 - WebSocketサーバーと接続し,バイナリパケットの送受信(エコーテスト)に成功すること. - - ■ 実装対象 - ・packages/shared/ - - src/protocol/schema.ts: DataViewを用いたバイナリエンコード/デコード処理. - ・apps/server/ - - src/index.ts: WebSocketサーバー起動 (wsライブラリ). - - src/network/Connection.ts: 接続管理. - ・apps/client/ - - src/network/SocketClient.ts: バイナリ送受信の実装. - -2-3. Step 3: 複数人同期・補間 (Multiplayer Sync) - ■ 目標 - 2つのクライアント間で位置同期が行われ,他プレイヤーの動きが補間により滑らかに表示されること. - - ■ 実装対象 - ・apps/server/ - - src/managers/RoomManager.ts: 接続IDと座標の管理. - - src/network/PacketHandler.ts: 全員分の座標スナップショット作成とブロードキャスト. - ・apps/client/ - - src/entities/RemotePlayer.ts: 他プレイヤー描画クラス. - - src/network/Reconciler.ts: 線形補間 (Lerp) ロジックの実装. - -2-4. Step 4: 50人規模最適化 (Optimization & Scaling) - ■ 目標 - パケットサイズを削減し,50人同時動作時の帯域負荷を仕様内(30KB/s以下)に抑えること. - - ■ 実装対象 - ・packages/shared/ - - src/utils/quantization.ts: 座標の圧縮 (Float -> Uint16). - ・apps/server/ - - src/core/ServerEngine.ts: ループ処理の最適化,必要に応じたAoI(関心領域)判定. - -2-5. Step 5: メタデータ・UI実装 (Meta Data & UI) - ■ 目標 - ゲーム開始前のロビー画面およびUIを実装し,ゲームサイクルを完成させること. - - ■ 実装対象 - ・apps/client/ - - src/scenes/TitleScene.ts: 名前入力とスタート処理. - - src/ui/UIManager.ts: DOMベースのUIオーバーレイ. - ・packages/shared/ - - src/types/index.ts: ロビー用JSONメッセージの型定義. - - -3. 開発ルール (Development Rules) ------------------------------------------------------------------------- -・ロジックの共通化: - 移動計算式や衝突判定は必ず `packages/shared` に実装し,Client/Server間でコードを共有する. -・検証優先: - 各Step完了ごとに動作確認を行い,バグを次工程に持ち越さない. \ No newline at end of file diff --git "a/docs/SPEC_03_\343\203\227\343\203\255\343\203\210\343\202\277\343\202\244\343\203\227_\347\247\273\345\213\225\343\203\206\343\202\271\343\203\210.txt" "b/docs/SPEC_03_\343\203\227\343\203\255\343\203\210\343\202\277\343\202\244\343\203\227_\347\247\273\345\213\225\343\203\206\343\202\271\343\203\210.txt" deleted file mode 100644 index b4400cd..0000000 --- "a/docs/SPEC_03_\343\203\227\343\203\255\343\203\210\343\202\277\343\202\244\343\203\227_\347\247\273\345\213\225\343\203\206\343\202\271\343\203\210.txt" +++ /dev/null @@ -1,107 +0,0 @@ -======================================================================== -プロトタイプ仕様書:50人同時移動テスト (Prototype Spec: Movement Test) -======================================================================== - - -1. プロトタイプ概要 (Overview) ------------------------------------------------------------------------- - -1-0. 目的 - 50人のプレイヤーが同じフィールド上で遅延なく移動できる通信基盤を検証する. - 衝突判定,塗り処理,ゲーム進行管理などの付随要素は実装せず,純粋な「移動同期」と「負荷検証」にフォーカスする. - -1-1. 検証範囲 - ・マップ: 100×100マスのグリッドマップ - ・人数: 最大50クライアント同時接続 - ・動作: 360度移動,カメラ追従,他者位置の同期表示 - - -2. クライアント実装仕様 (Client Implementation) ------------------------------------------------------------------------- - -2-0. 目的 - 入力処理,移動計算,および描画の基本ロジックを定義する. - -2-1. 入力・操作系 - ■ ジョイスティック操作 - ・左側エリア: 画面左半分をタッチ可能な移動ジョイスティック領域とする. - ・入力形式: 360°全方位入力. - ・ベクトル正規化: - - 入力ベクトルの長さが1.0を超える場合,1.0に正規化する. - - これにより,斜め移動時の意図しない加速を防止する. - - ■ 誤操作防止 (UX Protection) - ・スクリーンロック: - - ゲーム画面に対するスクロール,拡大縮小(ピンチ操作)を無効化する. - ・エッジデッドゾーン: - - 画面左右の端(10px〜)を入力無効領域とし,OSのジェスチャー機能暴発を防ぐ. - -2-2. 移動・演算ロジック - ■ キャラクター仕様 - ・サイズ: 0.8マス×0.8マス - ・移動速度: 秒速4〜5マス - - ■ 時間管理 (Time Management) - ・DeltaTime対応: - - 毎フレームの移動量計算に「前フレームからの経過時間 (DeltaTime)」を乗算する. - - 計算式: `Position += Velocity * Speed * DeltaTime` - - 目的: 端末のフレームレート(30fps/60fps/120fps)に依存せず,移動速度を一定に保つ. - - ■ 座標管理 - ・内部座標(計算・通信用): - - Float(浮動小数点)で管理し,滑らかな移動を実現する. - ・グリッド座標(表示目安): - - 内部座標の小数点以下を切り捨て(Floor)た値を現在のマスとする. - -2-3. カメラシステム (Camera System) - ■ カメラ追従 (Camera Follow) - ・挙動: - - 常に「自キャラクター」が画面の中央に配置されるよう,カメラ座標を毎フレーム更新する. - - マップ端に到達した場合のクランプ(固定)処理は,本プロトタイプでは実装不要とする(黒背景が見えても良い). - - -3. 通信アーキテクチャ (Network Architecture) ------------------------------------------------------------------------- - -3-0. 目的 - 50人の座標をリアルタイムに同期するためのデータ構造と通信フローを定義する. - -3-1. 通信フローと役割分担 - | カテゴリ | クライアント (Client) | サーバー (Server) | - | :--- | :--- | :--- | - | **自キャラ** | **予測 (Prediction)**: 入力を即時反映し座標を更新・送信. | **中継 (Relay)**: 受信座標を正とし,他者へブロードキャスト. | - | **他キャラ** | **補間 (Interpolation)**: 受信した過去の座標間を滑らかに補間移動. | **間引き (AoI)**: 距離に応じ送信情報を圧縮・除外. | - -3-2. サーバー更新ループ (Server Loop) - ■ ティックレート (Tick Rate) - ・頻度: 20Hz(50ms間隔) - ・処理内容: - 1. 受信バッファ内の全クライアントからの入力を取り出す. - 2. AoI(関心領域)判定を行い,各クライアントに必要なデータをフィルタリングする. - 3. 全クライアントへ「スナップショット」を一斉送信する. - - ■ スナップショット送信 (Snapshot) - ・送信データ: - - 視界範囲内にいる全キャラクターの ID,座標,向き. - - サーバータイムスタンプ(補間計算用). - -3-3. データ構造・最適化 - ■ パケット設計 - ・形式: バイナリパケット(ArrayBuffer等)を採用し,JSON等のテキスト形式は使用しない. - - ■ 座標の量子化 (Quantization) - ・目的: 通信帯域の削減. - ・手法: - - Float座標(0.0〜100.0)を,Unsigned Short(0〜65535)の整数値に変換して送信する. - - 受信側で再度Floatに戻して使用する. - - ■ 送信データ (Input Data) - クライアントからサーバーへ毎フレーム(または間引き)送信するデータ. - ・現在座標 (Position): 物理演算(DeltaTime適用)後の確定座標 (x, y). - ・移動ベクトル (Velocity): 補間予測用の補助データ. - ・角度 (Rotation): キャラクターの向き. - - ■ エリア別同期 (AoI) - ・ロジック: - - 各プレイヤーを中心とした一定範囲(例: 画面サイズの1.5倍)外にいる他プレイヤーの座標データは送信しない. - - これにより,50人全員が動いていても,各端末が受け取るデータ量を視界内のみに限定する. \ No newline at end of file diff --git a/packages/shared/src/index.ts b/packages/shared/src/index.ts index e69de29..9797972 100644 --- a/packages/shared/src/index.ts +++ b/packages/shared/src/index.ts @@ -0,0 +1 @@ +export * from './config/gameConfig'; \ No newline at end of file diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index ab4dacf..a5bc9ba 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -13,16 +13,31 @@ '@repo/shared': specifier: workspace:* version: link:../../packages/shared + '@types/react': + specifier: ^19.2.13 + version: 19.2.13 + '@types/react-dom': + specifier: ^19.2.3 + version: 19.2.3(@types/react@19.2.13) + '@vitejs/plugin-react': + specifier: ^5.1.3 + version: 5.1.3(vite@7.3.1(@types/node@24.10.11)(tsx@4.21.0)) pixi.js: specifier: ^8.16.0 version: 8.16.0 - preact: - specifier: ^10.27.2 - version: 10.28.3 + react: + specifier: ^19.2.4 + version: 19.2.4 + react-dom: + specifier: ^19.2.4 + version: 19.2.4(react@19.2.4) + react-joystick-component: + specifier: ^6.2.1 + version: 6.2.1(react-dom@19.2.4(react@19.2.4))(react@19.2.4) + socket.io-client: + specifier: ^4.8.3 + version: 4.8.3 devDependencies: - '@preact/preset-vite': - specifier: ^2.10.2 - version: 2.10.3(@babel/core@7.29.0)(preact@10.28.3)(rollup@4.57.1)(vite@7.3.1(@types/node@24.10.11)(tsx@4.21.0)) '@types/node': specifier: ^24.10.1 version: 24.10.11 @@ -38,16 +53,16 @@ '@repo/shared': specifier: workspace:* version: link:../../packages/shared - ws: - specifier: ^8.19.0 - version: 8.19.0 + socket.io: + specifier: ^4.8.3 + version: 4.8.3 devDependencies: '@types/node': specifier: ^24.10.11 version: 24.10.11 - '@types/ws': - specifier: ^8.18.1 - version: 8.18.1 + '@types/socket.io': + specifier: ^3.0.2 + version: 3.0.2 tsx: specifier: ^4.21.0 version: 4.21.0 @@ -82,10 +97,6 @@ resolution: {integrity: sha512-qsaF+9Qcm2Qv8SRIMMscAvG4O3lJ0F1GuMo5HR/Bp02LopNgnZBC/EkbevHFeGs4ls/oPz9v+Bsmzbkbe+0dUw==} engines: {node: '>=6.9.0'} - '@babel/helper-annotate-as-pure@7.27.3': - resolution: {integrity: sha512-fXSwMQqitTGeHLBC08Eq5yXz2m37E4pJX1qAU1+2cNedz/ifv/bVXft90VeSav5nFO61EcNgwr0aJxbyPaWBPg==} - engines: {node: '>=6.9.0'} - '@babel/helper-compilation-targets@7.28.6': resolution: {integrity: sha512-JYtls3hqi15fcx5GaSNL7SCTJ2MNmjrkHXg4FSpOA/grxK8KwyZ5bubHsCq8FXCkua6xhuaaBit+3b7+VZRfcA==} engines: {node: '>=6.9.0'} @@ -129,20 +140,14 @@ engines: {node: '>=6.0.0'} hasBin: true - '@babel/plugin-syntax-jsx@7.28.6': - resolution: {integrity: sha512-wgEmr06G6sIpqr8YDwA2dSRTE3bJ+V0IfpzfSY3Lfgd7YWOaAdlykvJi13ZKBt8cZHfgH1IXN+CL656W3uUa4w==} + '@babel/plugin-transform-react-jsx-self@7.27.1': + resolution: {integrity: sha512-6UzkCs+ejGdZ5mFFC/OCUrv028ab2fp1znZmCZjAOBKiBK2jXD1O+BPSfX8X2qjJ75fZBMSnQn3Rq2mrBJK2mw==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 - '@babel/plugin-transform-react-jsx-development@7.27.1': - resolution: {integrity: sha512-ykDdF5yI4f1WrAolLqeF3hmYU12j9ntLQl/AOG1HAS21jxyg1Q0/J/tpREuYLfatGdGmXp/3yS0ZA76kOlVq9Q==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - - '@babel/plugin-transform-react-jsx@7.28.6': - resolution: {integrity: sha512-61bxqhiRfAACulXSLd/GxqmAedUSrRZIu/cbaT18T1CetkTmtDN15it7i80ru4DVqRK1WMxQhXs+Lf9kajm5Ow==} + '@babel/plugin-transform-react-jsx-source@7.27.1': + resolution: {integrity: sha512-zbwoTsBruTeKB9hSq73ha66iFeJHuaFkUbwvqElnygoNbj/jHRsSeokowZFN3CZ64IvEqcmmkVe89OPXc7ldAw==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 @@ -334,41 +339,8 @@ '@pixi/colord@2.9.6': resolution: {integrity: sha512-nezytU2pw587fQstUu1AsJZDVEynjskwOL+kibwcdxsMBFqPsFFNA7xl0ii/gXuDi6M0xj3mfRJj8pBSc2jCfA==} - '@preact/preset-vite@2.10.3': - resolution: {integrity: sha512-1SiS+vFItpkNdBs7q585PSAIln0wBeBdcpJYbzPs1qipsb/FssnkUioNXuRsb8ZnU8YEQHr+3v8+/mzWSnTQmg==} - peerDependencies: - '@babel/core': 7.x - vite: 2.x || 3.x || 4.x || 5.x || 6.x || 7.x - - '@prefresh/babel-plugin@0.5.2': - resolution: {integrity: sha512-AOl4HG6dAxWkJ5ndPHBgBa49oo/9bOiJuRDKHLSTyH+Fd9x00shTXpdiTj1W41l6oQIwUOAgJeHMn4QwIDpHkA==} - - '@prefresh/core@1.5.9': - resolution: {integrity: sha512-IKBKCPaz34OFVC+adiQ2qaTF5qdztO2/4ZPf4KsRTgjKosWqxVXmEbxCiUydYZRY8GVie+DQlKzQr9gt6HQ+EQ==} - peerDependencies: - preact: ^10.0.0 || ^11.0.0-0 - - '@prefresh/utils@1.2.1': - resolution: {integrity: sha512-vq/sIuN5nYfYzvyayXI4C2QkprfNaHUQ9ZX+3xLD8nL3rWyzpxOm1+K7RtMbhd+66QcaISViK7amjnheQ/4WZw==} - - '@prefresh/vite@2.4.11': - resolution: {integrity: sha512-/XjURQqdRiCG3NpMmWqE9kJwrg9IchIOWHzulCfqg2sRe/8oQ1g5De7xrk9lbqPIQLn7ntBkKdqWXIj4E9YXyg==} - peerDependencies: - preact: ^10.4.0 || ^11.0.0-0 - vite: '>=2.0.0' - - '@rollup/pluginutils@4.2.1': - resolution: {integrity: sha512-iKnFXr7NkdZAIHiIWE+BX5ULi/ucVFYWD6TbAV+rZctiRTY2PL6tsIKhoIOaoskiWAkgu+VsbXgUVDNLHf+InQ==} - engines: {node: '>= 8.0.0'} - - '@rollup/pluginutils@5.3.0': - resolution: {integrity: sha512-5EdhGZtnu3V88ces7s53hhfK5KSASnJZv8Lulpc04cWO3REESroJXg73DFsOmgbU2BhwV0E20bu2IDZb3VKW4Q==} - engines: {node: '>=14.0.0'} - peerDependencies: - rollup: ^1.20.0||^2.0.0||^3.0.0||^4.0.0 - peerDependenciesMeta: - rollup: - optional: true + '@rolldown/pluginutils@1.0.0-rc.2': + resolution: {integrity: sha512-izyXV/v+cHiRfozX62W9htOAvwMo4/bXKDrQ+vom1L1qRuexPock/7VZDAhnpHCLNejd3NJ6hiab+tO0D44Rgw==} '@rollup/rollup-android-arm-eabi@4.57.1': resolution: {integrity: sha512-A6ehUVSiSaaliTxai040ZpZ2zTevHYbvu/lDoeAteHI8QnaosIzm4qwtezfRg1jOYaUmnzLX1AOD6Z+UJjtifg==} @@ -508,6 +480,24 @@ cpu: [x64] os: [win32] + '@socket.io/component-emitter@3.1.2': + resolution: {integrity: sha512-9BCxFwvbGg/RsZK9tjXd8s4UcwR0MWeFQ1XEKIQVVvAGJyINdrqKMcTRyLoK8Rse1GjzLV9cwjWV1olXRWEXVA==} + + '@types/babel__core@7.20.5': + resolution: {integrity: sha512-qoQprZvz5wQFJwMDqeseRXWv3rqMvhgpbXFfVyWhbx9X47POIA6i/+dXefEmZKoAgOaTdaIgNSMqMIU61yRyzA==} + + '@types/babel__generator@7.27.0': + resolution: {integrity: sha512-ufFd2Xi92OAVPYsy+P4n7/U7e68fex0+Ee8gSG9KX7eo084CWiQ4sdxktvdl0bOPupXtVJPY19zk6EwWqUQ8lg==} + + '@types/babel__template@7.4.4': + resolution: {integrity: sha512-h/NUaSyG5EyxBIp8YRxo4RMe2/qQgvyowRwVMzhYhBCONbW8PUsg4lkFMrhgZhUe5z3L3MiLDuvyJ/CaPa2A8A==} + + '@types/babel__traverse@7.28.0': + resolution: {integrity: sha512-8PvcXf70gTDZBgt9ptxJ8elBeBjcLOAcOtoO/mPJjtji1+CdGbHgm77om1GrsPxsiE+uXIpNSK64UYaIwQXd4Q==} + + '@types/cors@2.8.19': + resolution: {integrity: sha512-mFNylyeyqN93lfe/9CSxOGREz8cpzAhH+E93xJ4xWQf62V8sQ/24reV2nyzUWM6H6Xji+GGHpkbLe7pVoUEskg==} + '@types/earcut@3.0.0': resolution: {integrity: sha512-k/9fOUGO39yd2sCjrbAJvGDEQvRwRnQIZlBz43roGwUZo5SHAmyVvSFyaVVZkicRVCaDXPKlbxrUcBuJoSWunQ==} @@ -517,8 +507,23 @@ '@types/node@24.10.11': resolution: {integrity: sha512-/Af7O8r1frCVgOz0I62jWUtMohJ0/ZQU/ZoketltOJPZpnb17yoNc9BSoVuV9qlaIXJiPNOpsfq4ByFajSArNQ==} - '@types/ws@8.18.1': - resolution: {integrity: sha512-ThVF6DCVhA8kUGy+aazFQ4kXQ7E1Ty7A3ypFOe0IcJV8O/M511G99AW24irKrW56Wt44yG9+ij8FaqoBGkuBXg==} + '@types/react-dom@19.2.3': + resolution: {integrity: sha512-jp2L/eY6fn+KgVVQAOqYItbF0VY/YApe5Mz2F0aykSO8gx31bYCZyvSeYxCHKvzHG5eZjc+zyaS5BrBWya2+kQ==} + peerDependencies: + '@types/react': ^19.2.0 + + '@types/react@19.2.13': + resolution: {integrity: sha512-KkiJeU6VbYbUOp5ITMIc7kBfqlYkKA5KhEHVrGMmUUMt7NeaZg65ojdPk+FtNrBAOXNVM5QM72jnADjM+XVRAQ==} + + '@types/socket.io@3.0.2': + resolution: {integrity: sha512-pu0sN9m5VjCxBZVK8hW37ZcMe8rjn4HHggBN5CbaRTvFwv5jOmuIRZEuddsBPa9Th0ts0SIo3Niukq+95cMBbQ==} + deprecated: This is a stub types definition. socket.io provides its own type definitions, so you do not need this installed. + + '@vitejs/plugin-react@5.1.3': + resolution: {integrity: sha512-NVUnA6gQCl8jfoYqKqQU5Clv0aPw14KkZYCsX6T9Lfu9slI0LOU10OTwFHS/WmptsMMpshNd/1tuWsHQ2Uk+cg==} + engines: {node: ^20.19.0 || >=22.12.0} + peerDependencies: + vite: ^4.2.0 || ^5.0.0 || ^6.0.0 || ^7.0.0 '@webgpu/types@0.1.69': resolution: {integrity: sha512-RPmm6kgRbI8e98zSD3RVACvnuktIja5+yLgDAkTmxLr90BEwdTXRQWNLF3ETTTyH/8mKhznZuN5AveXYFEsMGQ==} @@ -527,6 +532,10 @@ resolution: {integrity: sha512-cQzWCtO6C8TQiYl1ruKNn2U6Ao4o4WBBcbL61yJl84x+j5sOWWFU9X7DpND8XZG3daDppSsigMdfAIl2upQBRw==} engines: {node: '>=10.0.0'} + accepts@1.3.8: + resolution: {integrity: sha512-PYAthTa2m2VKxuvSD3DPC/Gy+U+sOA1LAuT8mkmRuvw+NACSaeXEQ+NHcVF7rONl6qcaxV3Uuemwawk+7+SJLw==} + engines: {node: '>= 0.6'} + acorn@8.15.0: resolution: {integrity: sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==} engines: {node: '>=0.4.0'} @@ -535,18 +544,14 @@ any-promise@1.3.0: resolution: {integrity: sha512-7UvmKalWRt1wgjL1RrGxoSJW/0QZFIegpeGvZG9kjp8vrRu55XTHbwnqq2GpXm9uLbcuhxm3IqX9OB4MZR1b2A==} - babel-plugin-transform-hook-names@1.0.2: - resolution: {integrity: sha512-5gafyjyyBTTdX/tQQ0hRgu4AhNHG/hqWi0ZZmg2xvs2FgRkJXzDNKBZCyoYqgFkovfDrgM8OoKg8karoUvWeCw==} - peerDependencies: - '@babel/core': ^7.12.10 + base64id@2.0.0: + resolution: {integrity: sha512-lGe34o6EHj9y3Kts9R4ZYs/Gr+6N7MCaMlIFA3F1R2O5/m7K06AxfSeO5530PEERE6/WyEg3lsuyw4GHlPZHog==} + engines: {node: ^4.5.0 || >= 5.9} baseline-browser-mapping@2.9.19: resolution: {integrity: sha512-ipDqC8FrAl/76p2SSWKSI+H9tFwm7vYqXQrItCuiVPt26Km0jS+NzSsBWAaBusvSbQcfJG+JitdMm+wZAgTYqg==} hasBin: true - boolbase@1.0.0: - resolution: {integrity: sha512-JZOSA7Mo9sNGB8+UjSgzdLtokWAky1zbztM3WRLCbZ70/3cTANmQmOdR7y2g+J0e2WXywy1yS468tY+IruqEww==} - browserslist@4.28.1: resolution: {integrity: sha512-ZC5Bd0LgJXgwGqUknZY/vkUQ04r8NXnJZ3yYi4vDmSiZmC/pdSN0NbNRPxZpbtO4uAfDUAFffO8IZoM3Gj8IkA==} engines: {node: ^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7} @@ -583,12 +588,16 @@ convert-source-map@2.0.0: resolution: {integrity: sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==} - css-select@5.2.2: - resolution: {integrity: sha512-TizTzUddG/xYLA3NXodFM0fSbNizXjOKhqiQQwvhlspadZokn1KDy0NZFS0wuEubIYAV5/c1/lAr0TaaFXEXzw==} + cookie@0.7.2: + resolution: {integrity: sha512-yki5XnKuf750l50uGTllt6kKILY4nQ1eNIQatoXEByZ5dWgnKqbnqmTrBE5B4N7lrMJKQ2ytWMiTO2o0v6Ew/w==} + engines: {node: '>= 0.6'} - css-what@6.2.2: - resolution: {integrity: sha512-u/O3vwbptzhMs3L1fQE82ZSLHQQfto5gyZzwteVIEyeaY5Fc7R4dapF/BvRoSYFeqfBk4m0V1Vafq5Pjv25wvA==} - engines: {node: '>= 6'} + cors@2.8.6: + resolution: {integrity: sha512-tJtZBBHA6vjIAaF6EnIaq6laBBP9aq/Y3ouVJjEfoHbRBcHBAHYcMh/w8LDrk2PvIMMq8gmopa5D4V8RmbrxGw==} + engines: {node: '>= 0.10'} + + csstype@3.2.3: + resolution: {integrity: sha512-z1HGKcYy2xA8AGQfwrn0PAy+PB7X/GSj3UVJW9qKyn43xWa+gl5nXmU4qqLMRzWVLFC8KusUX8T/0kCiOYpAIQ==} debug@4.4.3: resolution: {integrity: sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==} @@ -599,28 +608,22 @@ supports-color: optional: true - dom-serializer@2.0.0: - resolution: {integrity: sha512-wIkAryiqt/nV5EQKqQpo3SToSOV9J0DnbJqwK7Wv/Trc92zIAYZ4FlMu+JPFW1DfGFt81ZTCGgDEabffXeLyJg==} - - domelementtype@2.3.0: - resolution: {integrity: sha512-OLETBj6w0OsagBwdXnPdN0cnMfF9opN69co+7ZrbfPGrdpPVNBUj02spi6B1N7wChLQiPn4CSH/zJvXw56gmHw==} - - domhandler@5.0.3: - resolution: {integrity: sha512-cgwlv/1iFQiFnU96XXgROh8xTeetsnJiDsTc7TYCLFd9+/WNkIqPTxiM/8pSd8VIrhXGTf1Ny1q1hquVqDJB5w==} - engines: {node: '>= 4'} - - domutils@3.2.2: - resolution: {integrity: sha512-6kZKyUajlDuqlHKVX1w7gyslj9MPIXzIFiz/rGu35uC1wMi+kMhQwGhl4lt9unC9Vb9INnY9Z3/ZA3+FhASLaw==} - earcut@3.0.2: resolution: {integrity: sha512-X7hshQbLyMJ/3RPhyObLARM2sNxxmRALLKx1+NVFFnQ9gKzmCrxm9+uLIAdBcvc8FNLpctqlQ2V6AE92Ol9UDQ==} electron-to-chromium@1.5.286: resolution: {integrity: sha512-9tfDXhJ4RKFNerfjdCcZfufu49vg620741MNs26a9+bhLThdB+plgMeou98CAaHu/WATj2iHOOHTp1hWtABj2A==} - entities@4.5.0: - resolution: {integrity: sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw==} - engines: {node: '>=0.12'} + engine.io-client@6.6.4: + resolution: {integrity: sha512-+kjUJnZGwzewFDw951CDWcwj35vMNf2fcj7xQWOctq1F2i1jkDdVvdFG9kM/BEChymCH36KgjnW0NsL58JYRxw==} + + engine.io-parser@5.2.3: + resolution: {integrity: sha512-HqD3yTBfnBxIrbnM1DoD6Pcq8NECnh8d4As1Qgh0z5Gg3jRRIqijury0CL3ghu/edArpUYiYqQiDUQBIs4np3Q==} + engines: {node: '>=10.0.0'} + + engine.io@6.6.5: + resolution: {integrity: sha512-2RZdgEbXmp5+dVbRm0P7HQUImZpICccJy7rN7Tv+SFa55pH+lxnuw6/K1ZxxBfHoYpSkHLAO92oa8O4SwFXA2A==} + engines: {node: '>=10.2.0'} esbuild@0.27.3: resolution: {integrity: sha512-8VwMnyGCONIs6cWue2IdpHxHnAjzxnw2Zr7MkVxB2vjmQ2ivqGFb4LEG3SMnv0Gb2F/G/2yA8zUaiL1gywDCCg==} @@ -631,9 +634,6 @@ resolution: {integrity: sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==} engines: {node: '>=6'} - estree-walker@2.0.2: - resolution: {integrity: sha512-Rfkk/Mp/DL7JVje3u18FxFujQlTNR2q6QfMSMB7AvCBx91NGj/ba3kCfza0f6dVDbw7YlRf/nDrn7pQrCCyQ/w==} - eventemitter3@5.0.4: resolution: {integrity: sha512-mlsTRyGaPBjPedk6Bvw+aqbsXDtoAyAzm5MO7JgU+yVRyMQ5O8bD4Kcci7BS85f93veegeCPkL8R4GLClnjLFw==} @@ -664,10 +664,6 @@ gifuct-js@2.1.2: resolution: {integrity: sha512-rI2asw77u0mGgwhV3qA+OEgYqaDn5UNqgs+Bx0FGwSpuqfYn+Ir6RQY5ENNQ8SbIiG/m5gVa7CD5RriO4f4Lsg==} - he@1.2.0: - resolution: {integrity: sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw==} - hasBin: true - ismobilejs@1.1.1: resolution: {integrity: sha512-VaFW53yt8QO61k2WJui0dHf4SlL8lxBofUuUmwBo0ljPk0Drz2TiuDW4jo3wDcv41qy/SxrJ+VAzJ/qYqsmzRw==} @@ -691,9 +687,6 @@ engines: {node: '>=6'} hasBin: true - kolorist@1.8.0: - resolution: {integrity: sha512-Y+60/zizpJ3HRH8DCss+q95yr6145JXZo46OTpFvDZWLfRCE4qChOyk1b26nMaNpfHHgxagk9dXT5OP0Tfe+dQ==} - lilconfig@3.1.3: resolution: {integrity: sha512-/vlFKAoH5Cgt3Ie+JLhRbwOsCQePABiU3tJ1egGvyQ+33R/vcwM2Zl2QR/LzjsBeItPt3oSVXapn+m4nQDvpzw==} engines: {node: '>=14'} @@ -711,6 +704,14 @@ magic-string@0.30.21: resolution: {integrity: sha512-vd2F4YUyEXKGcLHoq+TEyCjxueSeHnFxyyjNp80yg0XV4vUhnDer/lvvlqM/arB5bXQN5K2/3oinyCRyx8T2CQ==} + mime-db@1.52.0: + resolution: {integrity: sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==} + engines: {node: '>= 0.6'} + + mime-types@2.1.35: + resolution: {integrity: sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==} + engines: {node: '>= 0.6'} + mlly@1.8.0: resolution: {integrity: sha512-l8D9ODSRWLe2KHJSifWGwBqpTZXIXTeo8mlKjY+E2HAakaTeNpqAyBZ8GSqLzHgw4XmHmC8whvpjJNMbFZN7/g==} @@ -725,15 +726,13 @@ engines: {node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1} hasBin: true - node-html-parser@6.1.13: - resolution: {integrity: sha512-qIsTMOY4C/dAa5Q5vsobRpOOvPfC4pB61UVW2uSwZNUp0QU/jCekTal1vMmbO0DgdHeLUJpv/ARmDqErVxA3Sg==} + negotiator@0.6.3: + resolution: {integrity: sha512-+EUsqGPLsM+j/zdChZjsnX51g4XrHFOIXwfnCVPGlQk/k5giakcKsuxCObBRu6DSm9opw/O6slWbJdghQM4bBg==} + engines: {node: '>= 0.6'} node-releases@2.0.27: resolution: {integrity: sha512-nmh3lCkYZ3grZvqcCH+fjmQ7X+H0OeZgP40OierEaAptX4XofMh5kwNbWh7lBduUzCcV/8kZ+NDLCwm2iorIlA==} - nth-check@2.1.1: - resolution: {integrity: sha512-lqjrjmaOoAnWfMmBPL+XNnynZh2+swxiX3WUE0s4yEHI6m+AwrK2UZOimIRl3X/4QctVqS8AiZjFqyOGrMXb/w==} - object-assign@4.1.1: resolution: {integrity: sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==} engines: {node: '>=0.10.0'} @@ -747,10 +746,6 @@ picocolors@1.1.1: resolution: {integrity: sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==} - picomatch@2.3.1: - resolution: {integrity: sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==} - engines: {node: '>=8.6'} - picomatch@4.0.3: resolution: {integrity: sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q==} engines: {node: '>=12'} @@ -787,8 +782,24 @@ resolution: {integrity: sha512-3Ybi1tAuwAP9s0r1UQ2J4n5Y0G05bJkpUIO0/bI9MhwmD70S5aTWbXGBwxHrelT+XM1k6dM0pk+SwNkpTRN7Pg==} engines: {node: ^10 || ^12 || >=14} - preact@10.28.3: - resolution: {integrity: sha512-tCmoRkPQLpBeWzpmbhryairGnhW9tKV6c6gr/w+RhoRoKEJwsjzipwp//1oCpGPOchvSLaAPlpcJi9MwMmoPyA==} + react-dom@19.2.4: + resolution: {integrity: sha512-AXJdLo8kgMbimY95O2aKQqsz2iWi9jMgKJhRBAxECE4IFxfcazB2LmzloIoibJI3C12IlY20+KFaLv+71bUJeQ==} + peerDependencies: + react: ^19.2.4 + + react-joystick-component@6.2.1: + resolution: {integrity: sha512-0G5Y5aX4hNuXB3xJCwz6Q+nYQOtC6kprNGKmZxmfoPvhepNYUiid0DbLEGZxmr/UKip3S/LUbcQUobtRCuB8IQ==} + peerDependencies: + react: '>=17.0.2' + react-dom: '>=17.0.2' + + react-refresh@0.18.0: + resolution: {integrity: sha512-QgT5//D3jfjJb6Gsjxv0Slpj23ip+HtOpnNgnb2S5zU3CB26G/IDPGoy4RJB42wzFE46DRsstbW6tKHoKbhAxw==} + engines: {node: '>=0.10.0'} + + react@19.2.4: + resolution: {integrity: sha512-9nfp2hYpCwOjAN+8TZFGhtWEwgvWHXqESH8qT89AT/lWklpLON22Lc8pEtnpsZz7VmawabSU0gCjnj8aC0euHQ==} + engines: {node: '>=0.10.0'} readdirp@4.1.2: resolution: {integrity: sha512-GDhwkLfywWL2s6vEjyhri+eXmfH6j1L7JE27WhqLeYzoh/A3DBaYGEj2H/HFZCn/kMfim73FXxEJTw06WtxQwg==} @@ -806,12 +817,27 @@ engines: {node: '>=18.0.0', npm: '>=8.0.0'} hasBin: true + scheduler@0.27.0: + resolution: {integrity: sha512-eNv+WrVbKu1f3vbYJT/xtiF5syA5HPIMtf9IgY/nKg0sWqzAUEvqY/xm7OcZc/qafLx/iO9FgOmeSAp4v5ti/Q==} + semver@6.3.1: resolution: {integrity: sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==} hasBin: true - simple-code-frame@1.3.0: - resolution: {integrity: sha512-MB4pQmETUBlNs62BBeRjIFGeuy/x6gGKh7+eRUemn1rCFhqo7K+4slPqsyizCbcbYLnaYqaoZ2FWsZ/jN06D8w==} + socket.io-adapter@2.5.6: + resolution: {integrity: sha512-DkkO/dz7MGln0dHn5bmN3pPy+JmywNICWrJqVWiVOyvXjWQFIv9c2h24JrQLLFJ2aQVQf/Cvl1vblnd4r2apLQ==} + + socket.io-client@4.8.3: + resolution: {integrity: sha512-uP0bpjWrjQmUt5DTHq9RuoCBdFJF10cdX9X+a368j/Ft0wmaVgxlrjvK3kjvgCODOMMOz9lcaRzxmso0bTWZ/g==} + engines: {node: '>=10.0.0'} + + socket.io-parser@4.2.5: + resolution: {integrity: sha512-bPMmpy/5WWKHea5Y/jYAP6k74A+hvmRCQaJuJB6I/ML5JZq/KfNieUVo/3Mh7SAqn7TyFdIo6wqYHInG1MU1bQ==} + engines: {node: '>=10.0.0'} + + socket.io@4.8.3: + resolution: {integrity: sha512-2Dd78bqzzjE6KPkD5fHZmDAKRNe3J15q+YHDrIsy9WEkqttc7GY+kT9OBLSMaPbQaEd0x1BjcmtMtXkfpc+T5A==} + engines: {node: '>=10.2.0'} source-map-js@1.2.1: resolution: {integrity: sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA==} @@ -821,10 +847,6 @@ resolution: {integrity: sha512-i5uvt8C3ikiWeNZSVZNWcfZPItFQOsYTUAOkcUPGd8DqDy1uOUikjt5dG+uRlwyvR108Fb9DOd4GvXfT0N2/uQ==} engines: {node: '>= 12'} - stack-trace@1.0.0-pre2: - resolution: {integrity: sha512-2ztBJRek8IVofG9DBJqdy2N5kulaacX30Nz7xmkYF6ale9WBVmIy6mFBchvGX7Vx/MyjBhx+Rcxqrj+dbOnQ6A==} - engines: {node: '>=16'} - sucrase@3.35.1: resolution: {integrity: sha512-DhuTmvZWux4H1UOnWMB3sk0sbaCVOoQZjv8u1rDoTV0HTdGem9hkAZtl4JZy8P2z4Bg0nT+YMeOFyVr4zcG5Tw==} engines: {node: '>=16 || 14 >=14.17'} @@ -896,10 +918,9 @@ peerDependencies: browserslist: '>= 4.21.0' - vite-prerender-plugin@0.5.12: - resolution: {integrity: sha512-EiwhbMn+flg14EysbLTmZSzq8NGTxhytgK3bf4aGRF1evWLGwZiHiUJ1KZDvbxgKbMf2pG6fJWGEa3UZXOnR1g==} - peerDependencies: - vite: 5.x || 6.x || 7.x + vary@1.1.2: + resolution: {integrity: sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==} + engines: {node: '>= 0.8'} vite@7.3.1: resolution: {integrity: sha512-w+N7Hifpc3gRjZ63vYBXA56dvvRlNWRczTdmCBBa+CotUzAPf5b7YMdMR/8CQoeYE5LX3W4wj6RYTgonm1b9DA==} @@ -941,8 +962,8 @@ yaml: optional: true - ws@8.19.0: - resolution: {integrity: sha512-blAT2mjOEIi0ZzruJfIhb3nps74PRWTCz1IjglWEEpQl5XS/UNama6u2/rjFkDDouqr4L67ry+1aGIALViWjDg==} + ws@8.18.3: + resolution: {integrity: sha512-PEIGCY5tSlUt50cqyMXfCzX+oOPqN0vuGqWzbcJ2xvnkzkq46oOpz7dQaTDBdfICb4N14+GARUDw2XV2N4tvzg==} engines: {node: '>=10.0.0'} peerDependencies: bufferutil: ^4.0.1 @@ -953,6 +974,10 @@ utf-8-validate: optional: true + xmlhttprequest-ssl@2.1.2: + resolution: {integrity: sha512-TEU+nJVUUnA4CYJFLvK5X9AOeH4KvDvhIfm0vV1GaQRtchnG0hgK5p8hw/xjv8cunWYCsiPCSDzObPyhEwq3KQ==} + engines: {node: '>=0.4.0'} + yallist@3.1.1: resolution: {integrity: sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g==} @@ -994,10 +1019,6 @@ '@jridgewell/trace-mapping': 0.3.31 jsesc: 3.1.0 - '@babel/helper-annotate-as-pure@7.27.3': - dependencies: - '@babel/types': 7.29.0 - '@babel/helper-compilation-targets@7.28.6': dependencies: '@babel/compat-data': 7.29.0 @@ -1041,28 +1062,15 @@ dependencies: '@babel/types': 7.29.0 - '@babel/plugin-syntax-jsx@7.28.6(@babel/core@7.29.0)': + '@babel/plugin-transform-react-jsx-self@7.27.1(@babel/core@7.29.0)': dependencies: '@babel/core': 7.29.0 '@babel/helper-plugin-utils': 7.28.6 - '@babel/plugin-transform-react-jsx-development@7.27.1(@babel/core@7.29.0)': + '@babel/plugin-transform-react-jsx-source@7.27.1(@babel/core@7.29.0)': dependencies: '@babel/core': 7.29.0 - '@babel/plugin-transform-react-jsx': 7.28.6(@babel/core@7.29.0) - transitivePeerDependencies: - - supports-color - - '@babel/plugin-transform-react-jsx@7.28.6(@babel/core@7.29.0)': - dependencies: - '@babel/core': 7.29.0 - '@babel/helper-annotate-as-pure': 7.27.3 - '@babel/helper-module-imports': 7.28.6 '@babel/helper-plugin-utils': 7.28.6 - '@babel/plugin-syntax-jsx': 7.28.6(@babel/core@7.29.0) - '@babel/types': 7.29.0 - transitivePeerDependencies: - - supports-color '@babel/template@7.28.6': dependencies: @@ -1186,55 +1194,7 @@ '@pixi/colord@2.9.6': {} - '@preact/preset-vite@2.10.3(@babel/core@7.29.0)(preact@10.28.3)(rollup@4.57.1)(vite@7.3.1(@types/node@24.10.11)(tsx@4.21.0))': - dependencies: - '@babel/core': 7.29.0 - '@babel/plugin-transform-react-jsx': 7.28.6(@babel/core@7.29.0) - '@babel/plugin-transform-react-jsx-development': 7.27.1(@babel/core@7.29.0) - '@prefresh/vite': 2.4.11(preact@10.28.3)(vite@7.3.1(@types/node@24.10.11)(tsx@4.21.0)) - '@rollup/pluginutils': 5.3.0(rollup@4.57.1) - babel-plugin-transform-hook-names: 1.0.2(@babel/core@7.29.0) - debug: 4.4.3 - picocolors: 1.1.1 - vite: 7.3.1(@types/node@24.10.11)(tsx@4.21.0) - vite-prerender-plugin: 0.5.12(vite@7.3.1(@types/node@24.10.11)(tsx@4.21.0)) - transitivePeerDependencies: - - preact - - rollup - - supports-color - - '@prefresh/babel-plugin@0.5.2': {} - - '@prefresh/core@1.5.9(preact@10.28.3)': - dependencies: - preact: 10.28.3 - - '@prefresh/utils@1.2.1': {} - - '@prefresh/vite@2.4.11(preact@10.28.3)(vite@7.3.1(@types/node@24.10.11)(tsx@4.21.0))': - dependencies: - '@babel/core': 7.29.0 - '@prefresh/babel-plugin': 0.5.2 - '@prefresh/core': 1.5.9(preact@10.28.3) - '@prefresh/utils': 1.2.1 - '@rollup/pluginutils': 4.2.1 - preact: 10.28.3 - vite: 7.3.1(@types/node@24.10.11)(tsx@4.21.0) - transitivePeerDependencies: - - supports-color - - '@rollup/pluginutils@4.2.1': - dependencies: - estree-walker: 2.0.2 - picomatch: 2.3.1 - - '@rollup/pluginutils@5.3.0(rollup@4.57.1)': - dependencies: - '@types/estree': 1.0.8 - estree-walker: 2.0.2 - picomatch: 4.0.3 - optionalDependencies: - rollup: 4.57.1 + '@rolldown/pluginutils@1.0.0-rc.2': {} '@rollup/rollup-android-arm-eabi@4.57.1': optional: true @@ -1311,6 +1271,33 @@ '@rollup/rollup-win32-x64-msvc@4.57.1': optional: true + '@socket.io/component-emitter@3.1.2': {} + + '@types/babel__core@7.20.5': + dependencies: + '@babel/parser': 7.29.0 + '@babel/types': 7.29.0 + '@types/babel__generator': 7.27.0 + '@types/babel__template': 7.4.4 + '@types/babel__traverse': 7.28.0 + + '@types/babel__generator@7.27.0': + dependencies: + '@babel/types': 7.29.0 + + '@types/babel__template@7.4.4': + dependencies: + '@babel/parser': 7.29.0 + '@babel/types': 7.29.0 + + '@types/babel__traverse@7.28.0': + dependencies: + '@babel/types': 7.29.0 + + '@types/cors@2.8.19': + dependencies: + '@types/node': 24.10.11 + '@types/earcut@3.0.0': {} '@types/estree@1.0.8': {} @@ -1319,26 +1306,51 @@ dependencies: undici-types: 7.16.0 - '@types/ws@8.18.1': + '@types/react-dom@19.2.3(@types/react@19.2.13)': dependencies: - '@types/node': 24.10.11 + '@types/react': 19.2.13 + + '@types/react@19.2.13': + dependencies: + csstype: 3.2.3 + + '@types/socket.io@3.0.2': + dependencies: + socket.io: 4.8.3 + transitivePeerDependencies: + - bufferutil + - supports-color + - utf-8-validate + + '@vitejs/plugin-react@5.1.3(vite@7.3.1(@types/node@24.10.11)(tsx@4.21.0))': + dependencies: + '@babel/core': 7.29.0 + '@babel/plugin-transform-react-jsx-self': 7.27.1(@babel/core@7.29.0) + '@babel/plugin-transform-react-jsx-source': 7.27.1(@babel/core@7.29.0) + '@rolldown/pluginutils': 1.0.0-rc.2 + '@types/babel__core': 7.20.5 + react-refresh: 0.18.0 + vite: 7.3.1(@types/node@24.10.11)(tsx@4.21.0) + transitivePeerDependencies: + - supports-color '@webgpu/types@0.1.69': {} '@xmldom/xmldom@0.8.11': {} + accepts@1.3.8: + dependencies: + mime-types: 2.1.35 + negotiator: 0.6.3 + acorn@8.15.0: {} any-promise@1.3.0: {} - babel-plugin-transform-hook-names@1.0.2(@babel/core@7.29.0): - dependencies: - '@babel/core': 7.29.0 + base64id@2.0.0: {} baseline-browser-mapping@2.9.19: {} - boolbase@1.0.0: {} - browserslist@4.28.1: dependencies: baseline-browser-mapping: 2.9.19 @@ -1368,43 +1380,52 @@ convert-source-map@2.0.0: {} - css-select@5.2.2: - dependencies: - boolbase: 1.0.0 - css-what: 6.2.2 - domhandler: 5.0.3 - domutils: 3.2.2 - nth-check: 2.1.1 + cookie@0.7.2: {} - css-what@6.2.2: {} + cors@2.8.6: + dependencies: + object-assign: 4.1.1 + vary: 1.1.2 + + csstype@3.2.3: {} debug@4.4.3: dependencies: ms: 2.1.3 - dom-serializer@2.0.0: - dependencies: - domelementtype: 2.3.0 - domhandler: 5.0.3 - entities: 4.5.0 - - domelementtype@2.3.0: {} - - domhandler@5.0.3: - dependencies: - domelementtype: 2.3.0 - - domutils@3.2.2: - dependencies: - dom-serializer: 2.0.0 - domelementtype: 2.3.0 - domhandler: 5.0.3 - earcut@3.0.2: {} electron-to-chromium@1.5.286: {} - entities@4.5.0: {} + engine.io-client@6.6.4: + dependencies: + '@socket.io/component-emitter': 3.1.2 + debug: 4.4.3 + engine.io-parser: 5.2.3 + ws: 8.18.3 + xmlhttprequest-ssl: 2.1.2 + transitivePeerDependencies: + - bufferutil + - supports-color + - utf-8-validate + + engine.io-parser@5.2.3: {} + + engine.io@6.6.5: + dependencies: + '@types/cors': 2.8.19 + '@types/node': 24.10.11 + accepts: 1.3.8 + base64id: 2.0.0 + cookie: 0.7.2 + cors: 2.8.6 + debug: 4.4.3 + engine.io-parser: 5.2.3 + ws: 8.18.3 + transitivePeerDependencies: + - bufferutil + - supports-color + - utf-8-validate esbuild@0.27.3: optionalDependencies: @@ -1437,8 +1458,6 @@ escalade@3.2.0: {} - estree-walker@2.0.2: {} - eventemitter3@5.0.4: {} fdir@6.5.0(picomatch@4.0.3): @@ -1464,8 +1483,6 @@ dependencies: js-binary-schema-parser: 2.0.3 - he@1.2.0: {} - ismobilejs@1.1.1: {} joycon@3.1.1: {} @@ -1478,8 +1495,6 @@ json5@2.2.3: {} - kolorist@1.8.0: {} - lilconfig@3.1.3: {} lines-and-columns@1.2.4: {} @@ -1494,6 +1509,12 @@ dependencies: '@jridgewell/sourcemap-codec': 1.5.5 + mime-db@1.52.0: {} + + mime-types@2.1.35: + dependencies: + mime-db: 1.52.0 + mlly@1.8.0: dependencies: acorn: 8.15.0 @@ -1511,17 +1532,10 @@ nanoid@3.3.11: {} - node-html-parser@6.1.13: - dependencies: - css-select: 5.2.2 - he: 1.2.0 + negotiator@0.6.3: {} node-releases@2.0.27: {} - nth-check@2.1.1: - dependencies: - boolbase: 1.0.0 - object-assign@4.1.1: {} parse-svg-path@0.1.2: {} @@ -1530,8 +1544,6 @@ picocolors@1.1.1: {} - picomatch@2.3.1: {} - picomatch@4.0.3: {} pirates@4.0.7: {} @@ -1568,7 +1580,19 @@ picocolors: 1.1.1 source-map-js: 1.2.1 - preact@10.28.3: {} + react-dom@19.2.4(react@19.2.4): + dependencies: + react: 19.2.4 + scheduler: 0.27.0 + + react-joystick-component@6.2.1(react-dom@19.2.4(react@19.2.4))(react@19.2.4): + dependencies: + react: 19.2.4 + react-dom: 19.2.4(react@19.2.4) + + react-refresh@0.18.0: {} + + react@19.2.4: {} readdirp@4.1.2: {} @@ -1607,18 +1631,55 @@ '@rollup/rollup-win32-x64-msvc': 4.57.1 fsevents: 2.3.3 + scheduler@0.27.0: {} + semver@6.3.1: {} - simple-code-frame@1.3.0: + socket.io-adapter@2.5.6: dependencies: - kolorist: 1.8.0 + debug: 4.4.3 + ws: 8.18.3 + transitivePeerDependencies: + - bufferutil + - supports-color + - utf-8-validate + + socket.io-client@4.8.3: + dependencies: + '@socket.io/component-emitter': 3.1.2 + debug: 4.4.3 + engine.io-client: 6.6.4 + socket.io-parser: 4.2.5 + transitivePeerDependencies: + - bufferutil + - supports-color + - utf-8-validate + + socket.io-parser@4.2.5: + dependencies: + '@socket.io/component-emitter': 3.1.2 + debug: 4.4.3 + transitivePeerDependencies: + - supports-color + + socket.io@4.8.3: + dependencies: + accepts: 1.3.8 + base64id: 2.0.0 + cors: 2.8.6 + debug: 4.4.3 + engine.io: 6.6.5 + socket.io-adapter: 2.5.6 + socket.io-parser: 4.2.5 + transitivePeerDependencies: + - bufferutil + - supports-color + - utf-8-validate source-map-js@1.2.1: {} source-map@0.7.6: {} - stack-trace@1.0.0-pre2: {} - sucrase@3.35.1: dependencies: '@jridgewell/gen-mapping': 0.3.13 @@ -1697,15 +1758,7 @@ escalade: 3.2.0 picocolors: 1.1.1 - vite-prerender-plugin@0.5.12(vite@7.3.1(@types/node@24.10.11)(tsx@4.21.0)): - dependencies: - kolorist: 1.8.0 - magic-string: 0.30.21 - node-html-parser: 6.1.13 - simple-code-frame: 1.3.0 - source-map: 0.7.6 - stack-trace: 1.0.0-pre2 - vite: 7.3.1(@types/node@24.10.11)(tsx@4.21.0) + vary@1.1.2: {} vite@7.3.1(@types/node@24.10.11)(tsx@4.21.0): dependencies: @@ -1720,6 +1773,8 @@ fsevents: 2.3.3 tsx: 4.21.0 - ws@8.19.0: {} + ws@8.18.3: {} + + xmlhttprequest-ssl@2.1.2: {} yallist@3.1.1: {}