
C言語入門|STEP17:アイテムと装備処理の実装-所持管理・使用・装備判定の考え方
はじめに:アイテムがあるから冒険は続く
STEP16では、ターン制バトルの内部構造を解説しました。
STEP17では、RPGに欠かせない アイテムと装備の仕組み を詳しく見ていきます。
アイテムは、
- ピンチを立て直す
- 戦略の幅を広げる
- 探索のご褒美になる
といった重要な役割を持っています。
このRPGでは、シンプルだけど拡張しやすい設計 でアイテムを実装しています。
アイテムをIDで管理する設計
まず、アイテムは列挙型で定義されています。
typedef enum {
ITEM_POTION = 0,
ITEM_HIPOTION,
ITEM_ETHER,
ITEM_ELIXIR,
ITEM_BRONZE_SWORD,
ITEM_STEEL_SWORD,
ITEM_APPRENTICE_STAFF,
ITEM_SAGE_STAFF,
ITEM_COUNT
} ItemID;この設計のポイント
- アイテムを数値IDで一意に管理
- ITEM_COUNT で総数を把握
- 配列と組み合わせやすい
RPGでは、
アイテムID=配列の添字
という考え方がとても便利です。
所持アイテムの管理方法
所持数は、GameState の配列で管理されています。
int inv[ITEM_COUNT];なぜ配列なのか
| 理由 | 内容 |
|---|---|
| 高速 | 添字アクセスですぐ取得 |
| 単純 | 個数管理が簡単 |
| 保存しやすい | セーブが楽 |
マップ探索や戦闘で増減するため、
数値管理が最も安定する設計 です。
アイテムの種類を分類する理由
アイテムには、種類があります。
typedef enum { IT_CONSUME = 0, IT_WEAPON = 1, IT_STAFF = 2 } ItemType;分類の意味
| 種類 | 内容 |
|---|---|
| IT_CONSUME | 消費アイテム |
| IT_WEAPON | 武器 |
| IT_STAFF | 杖 |
この分類によって、
- 使用処理
- 装備処理
を 同じ入口で分岐 できるようになります。
アイテム定義テーブルの役割
実際のアイテム情報は、
ItemDef 配列でまとめられています。
static const ItemDef g_items[ITEM_COUNT] = {
{"ポーション", IT_CONSUME, 30},
{"ハイポーション", IT_CONSUME, 70},
{"エーテル", IT_CONSUME, 15},
{"エリクサー", IT_CONSUME, 999},
{"ブロンズソード", IT_WEAPON, 3},
{"スチールソード", IT_WEAPON, 6},
{"見習いの杖", IT_STAFF, 3},
{"賢者の杖", IT_STAFF, 6},
};このテーブルが表すもの
| 要素 | 意味 |
|---|---|
| name | 表示名 |
| type | アイテム種別 |
| value | 回復量や補正値 |
ロジックとデータを分けることで、
数値調整だけを安全に行える設計 になっています。
アイテムを使えるかどうかの判定
戦闘中、まず確認されるのが
アイテムが1つでもあるかどうかです。
static int any_item_available(const int inv[]) {
for (int i = 0; i < ITEM_COUNT; i++)
if (inv[i] > 0) return 1;
return 0;
}このチェックの意味
- 無駄な選択肢を表示しない。
- 入力ミスを防ぐ。
プレイヤー体験を意識した、
親切なガード処理 です。
消費アイテムの使用処理
消費アイテムは、
use_consumable_on 関数で処理されます。
static void use_consumable_on(Character* c, ItemID id) {
if (id == ITEM_POTION || id == ITEM_HIPOTION) {
c->hp += g_items[id].value;
if (c->hp > c->max_hp) c->hp = c->max_hp;
}
}ポイント解説
- 回復量はテーブル参照
- 最大値を超えないよう制御
- キャラを直接更新
この関数を使うことで、
どの場面でも同じ回復処理 が使えます。
装備処理と職業制限
装備アイテムは、
equip_item 関数で処理されます。
if (g_items[id].type == IT_WEAPON) {
if (c->job == HERO || c->job == WARRIOR) {
c->weapon_atk = g_items[id].value;
}
}なぜ職業制限を入れるのか
- 職業ごとの役割を明確にする。
- 全員が万能にならない。
- RPGらしい選択を生む。
装備可能かどうかを
関数内で判断している点 が重要です。
装備は上書き方式にしている理由
装備を変更すると、
- 以前の装備は自動的に外れる。
- 補正値だけが更新される。
という設計になっています。
この方式のメリット
- 管理がシンプル
- 装備スロットを持たなくて済む。
- 学習用として分かりやすい。
複雑な装備管理は、
次のステップで拡張可能です。
戦闘中のアイテム使用フロー
戦闘中の流れは次のとおりです。
- 所持アイテム一覧を表示
- 使用・装備するアイテムを選択
- 消費か装備かを判定
- 対象キャラに反映
この一連の流れが、
1ターンの行動として完結 しています。
STEP17で押さえておきたいポイントまとめ
STEP17で理解しておきたいポイントはこちらです。
- アイテムはIDと配列で管理する。
- アイテム情報はテーブルで定義する。
- 消費と装備は種別で分岐する。
- 装備制限で職業の個性を保つ。
- 処理は関数にまとめて再利用する。
