Skip to content

アプリケーション設計

概要

ぷよぷよゲームの設計方針と実装アプローチについて説明します。 テスト駆動開発(TDD)ドメイン駆動設計(DDD)を基盤とし、8つのイテレーションで段階的に機能を実装しました。

設計方針

基本方針

  • 変更を楽に安全にできて役に立つソフトウェアの実現
  • よいソフトウェアの原則に従った実装
  • 継続的な改善によるコード品質の向上

開発手法

  • テスト駆動開発(TDD): Red-Green-Refactorサイクル
  • ドメイン駆動設計(DDD): ビジネスロジック中心の設計
  • イテレーション開発: 段階的な機能実装

イテレーション設計

全体計画

uml diagram

各イテレーションの設計

イテレーション1: ゲーム基盤

設計目標: 最小限の動作するゲームを作成

uml diagram

主要決定事項: - 6x12のフィールドサイズ - PuyoPairによるぷよペア管理 - 60FPSのゲームループ

イテレーション2: ぷよ移動

設計目標: ユーザー操作によるぷよ制御

uml diagram

主要決定事項: - イベント駆動型入力処理 - 衝突判定の実装 - 30フレーム間隔の自由落下

イテレーション3: ぷよ回転

設計目標: ぷよペアの回転機能

uml diagram

主要決定事項: - 時計回り90度回転 - 左右1マスの壁キック - 不変オブジェクトパターン

イテレーション4: 高速落下

設計目標: 下キーによる高速落下

uml diagram

主要決定事項: - 既存移動システムの再利用 - 継続押下検出 - 通常落下との併存

イテレーション5: ぷよ消去

設計目標: 4つ以上連結したぷよの消去

uml diagram

主要決定事項: - 深度優先探索による連結判定 - 消去後の重力適用 - 複数グループの同時処理

イテレーション6: 連鎖システム

設計目標: 連続消去による連鎖反応

uml diagram

主要決定事項: - 再帰的連鎖判定 - 連鎖ボーナス計算式: 2^(連鎖数-1) - リアルタイムスコア表示

イテレーション7: 全消しボーナス

設計目標: フィールド全消去時の特別ボーナス

uml diagram

主要決定事項: - 全消し判定のタイミング - 連鎖発生時のみボーナス適用 - 固定ボーナス値(2000点)

イテレーション8: ゲームオーバー

設計目標: ゲーム終了とリスタート機能

uml diagram

主要決定事項: - ゲーム状態管理の導入 - 新ぷよ配置不可時のゲームオーバー - Rキーによるリスタート機能

設計パターン

使用したデザインパターン

1. State パターン

uml diagram

2. Strategy パターン

uml diagram

3. Observer パターン

uml diagram

SOLID原則の適用

単一責任の原則(SRP)

  • Game: ゲームロジックのみ
  • GameField: フィールド状態管理のみ
  • GameRenderer: 描画処理のみ
  • InputHandler: 入力処理のみ

開放閉鎖の原則(OCP)

  • 新しいぷよ色の追加: PuyoColor enum拡張
  • 新しい入力方式: InputStrategy実装
  • 新しい描画効果: GameRenderer拡張

依存関係逆転の原則(DIP)

uml diagram

テスト設計

テスト戦略

uml diagram

TDDサイクル

uml diagram

テストケース設計

ドメインモデルのテスト

// Game.test.ts の例
describe('ぷよ移動', () => {
  it('左に移動できる', () => {
    // Arrange
    const game = new Game()
    game.start()

    // Act  
    const result = game.movePuyo(-1, 0)

    // Assert
    expect(result).toBe(true)
  })
})

境界値のテスト

// GameField.test.ts の例  
describe('フィールド境界', () => {
  it('範囲外の座標はfalseを返す', () => {
    const field = new GameField()

    expect(field.isValidPosition(-1, 0)).toBe(false) // 左端外
    expect(field.isValidPosition(6, 0)).toBe(false)  // 右端外
    expect(field.isValidPosition(0, -2)).toBe(false) // 上端外
    expect(field.isValidPosition(0, 12)).toBe(false) // 下端外
  })
})

パフォーマンス設計

レンダリング最適化

uml diagram

メモリ管理

  • 不変オブジェクト: PuyoPair, Puyo
  • オブジェクトプール: 使用していない(将来の最適化候補)
  • ガベージコレクション: 最小限のオブジェクト生成

計算量の最適化

処理 計算量 最適化手法
ぷよ移動判定 O(1) 座標計算のみ
連結判定 O(n) 深度優先探索
重力適用 O(n) 列ごとの処理
描画処理 O(n) 差分描画(将来)

エラーハンドリング設計

エラー分類

uml diagram

エラー処理戦略

  • 入力エラー: 無視して続行
  • 状態エラー: ログ出力して安全な状態に復帰
  • システムエラー: ゲーム停止とエラー表示

セキュリティ設計

脅威モデル

脅威 対策
不正な入力 入力値検証
チート行為 クライアントサイドのみなので対象外
XSS攻撃 HTML要素への直接出力なし

セキュリティ対策

  • 入力サニタイゼーション: キー入力の妥当性チェック
  • 状態整合性: ゲーム状態の不正変更防止
  • 型安全性: TypeScriptによる静的チェック

拡張性設計

将来の拡張項目

uml diagram

拡張ポイント

  1. 新しいゲームモード: GameState拡張
  2. 新しい入力デバイス: InputHandler拡張
  3. 新しい描画効果: GameRenderer拡張
  4. 新しいAI: Strategy パターンでAI実装

まとめ

本設計により以下を実現:

  • 高品質: TDDによる網羅的テスト
  • 保守性: 明確な責務分離と設計パターン適用
  • 拡張性: SOLID原則に基づく柔軟な設計
  • パフォーマンス: 効率的なアルゴリズムと描画
  • 安全性: 型安全性とエラーハンドリング