はじめに
定番トランプゲーム「大富豪」のiOSアプリをFlutterで開発しました。本記事では、18種のローカルルールをユーザーが自由にON/OFFできる設計や、CPUの思考アルゴリズム、階級システムの実装ポイントを紹介します。
使用技術
- Flutter (Dart) - UI・ビジネスロジックをすべてDartで実装
- AdMob - 収益化のためのバナー広告を導入
- Provider - 状態管理に使用
ルール設定の設計
ルールフラグの管理
各ローカルルールはRuleFlagというenumで定義し、RuleSettingsクラスでMap<RuleFlag, bool>として保持しました。設定画面ではSwitchListTileで各ルールをON/OFFし、変更は即座にChangeNotifierを通じてゲームロジックに反映されます。
enum RuleFlag { revolution, cutEight, tenDiscard, fiveSkip, jBack, sevenPass, twelveBomb, spadeThreeReturn, binding, timeBack, joker, staircase, pairBinding, classExchange, fall, forbiddenPlay }
class RuleSettings extends ChangeNotifier {
final Map<RuleFlag, bool> _flags = {};
bool isEnabled(RuleFlag flag) => _flags[flag] ?? false;
void toggle(RuleFlag flag) {
_flags[flag] = !( _flags[flag] ?? false);
notifyListeners();
}
}
ルールの説明表示
各ルールに「?」ボタンを設置し、ダイアログで説明を表示。説明文はRuleFlagごとにMapで定義し、保守しやすくしました。
CPU思考アルゴリズム
CPUは3段階の難易度を持ちます。
- 弱い: 手札の中で一番弱いカードから順に出せる組み合わせを探す
- 普通: 場のカードより少し強いカードを選ぶ。革命や8切りなどの特殊ルールを考慮
- 強い: 手札の組み合わせを分析し、最短で上がれる組み合わせを動的計画法で探索
実装上は、CpuStrategyという抽象クラスを定義し、難易度ごとにサブクラスで実装しました。
abstract class CpuStrategy {
List<Card> decidePlay(List<Card> hand, List<Card> table, RuleSettings rules);
}
階級交換の実装
ゲーム終了時に順位を判定し、大富豪→富豪→平民→貧民→大貧民の5階級を割り当てます。階級交換ルールがONのとき、上位階級のプレイヤーは下位階級のプレイヤーへカードを渡します。この処理はターン制の状態遷移として実装し、UIでは誰がどのカードを渡したかをアニメーションで表示しています。
苦労した点
- ローカルルールの組み合わせが膨大で、すべての組み合わせでバグが起きないよう網羅的なテストが必要だった
- 特殊ルールが重なったときの処理順序(例: 8切りと革命が同時に発生した場合)を定義するのが複雑だった
まとめ
Flutterで大富豪のルールを柔軟に設定できるアーキテクチャを構築し、リリースまでこぎつけました。状態管理とルールの分離を徹底することで、18種のルールを組み合わせても破綻しない設計を実現できたと思います。
アプリはこちらからダウンロードできます。