シェルスクリプトでRPG風ゲームを作ってみる②

だしまき
2025-07-18
2025-07-18

はじめに

暑すぎて溶け始めています。
どうもだしまきです。


前回記事で作ったシェルスクリプトRPGの機能を拡張してみたいと思います!

RPGを作ってみました

改めて前回作成したRPGシェルスクリプトです。

#!/bin/bash

# プレイヤーのステータス
player_hp=100
player_max_hp=100

# 敵のステータス
enemy_hp=100

echo "========================"
echo "=== バトルスタート! ==="
echo "========================"

while [ $player_hp -gt 0 ]; do
  echo
  echo "あなたのHP: $player_hp / $player_max_hp "
  echo "モンスターのHP: $enemy_hp"
  echo "1: 攻撃  2: 回復"
  read -p "→ 行動を選んでください: " action

  if [ "$action" = "1" ]; then
    damage=$((RANDOM % 41))  # 0〜40のダメージ
    echo "あなたの攻撃!モンスターに $damage ダメージ!"
    enemy_hp=$((enemy_hp - damage))
  elif [ "$action" = "2" ]; then
    heal=$((RANDOM % 31 + 10))  # 10〜40HPを回復
    player_hp=$((player_hp + heal))
    [ "$player_hp" -gt "$player_max_hp" ] && player_hp=$player_max_hp
    echo "あなたは $heal 回復した!"
  else
    echo "無効な入力"
    continue
  fi

  # モンスターが倒された際の処理
  if [ $enemy_hp -le 0 ]; then
    echo "モンスターを倒した!"
    enemy_hp=$((RANDOM % 50 + 100))  # 新しい敵
    echo "新たなモンスターが現れた!(HP: $enemy_hp)"
    continue
  fi

  # 敵の攻撃ターン
  enemy_damage=$((RANDOM % 31))  # 0〜30のダメージ
  echo "敵の攻撃!あなたに $enemy_damage ダメージ!"
  player_hp=$((player_hp - enemy_damage))

  if [ $player_hp -le 0 ]; then
    echo "あなたは倒れた… ゲームオーバー"
    break
  fi
done

モンスターと戦ったり回復したりと一通りの行動は出来るようになっているものの、
まだまだ物足りない部分が多いので、
今回は変数を使用して以下の点を追加してみようと思います。

【1】レベルアップ要素

では早速作っていきます!

【1】レベルアップ要素の追加

RPGといえばレベルアップ要素ですよね、モンスターを倒して経験値を得て強くなる。
このシステムをまずは追加してみようと思います。

 
大きく変更したところを振り返っていきたいと思います。
# プレイヤーのステータス
player_level=1
player_exp=0
exp_to_levelup=100
player_hp=100
player_max_hp=100
player_attack_min=10
player_attack_max=30

まずプレイヤーのステータス欄を増やしました。
レベルアップに伴う変更です、初期のレベルは1で当然最初は経験値0です。
レベルアップまでの経験値を100として、プレイヤーの攻撃力の下限値と上限値を設定しています。
後ほど出てきますのでそこで解説します。

# ステータス表示関数
show_status() {
  echo "========================"
  echo "現在のステータス:"
  echo "Lv.$player_level"
  echo "HP: $player_hp / $player_max_hp"
  echo "攻撃力: ${player_attack_min}〜${player_attack_max}"
  echo "EXP: $player_exp / $exp_to_levelup"
  echo "========================"
}

この部分は完全新規追加です。
現在のステータス(プレイヤーレベル・HP・攻撃力・次のレベルアップまで)を表示するために追加しています。
複数行のechoをひとまとめにして関数show_statusとして定義しています。
何箇所か表示させたい場面があるのでそこで簡単に呼び出せるようにします。

# 経験値獲得
    gained_exp=$((RANDOM % 31 + 20))  # 20〜50EXP
    player_exp=$((player_exp + gained_exp))
    echo "経験値を $gained_exp 獲得!(現在: $player_exp / $exp_to_levelup)"

    # レベルアップ判定
    if [ $player_exp -ge $exp_to_levelup ]; then
      player_level=$((player_level + 1))
      player_exp=$((player_exp - exp_to_levelup))  # 超過分を残す処理
      exp_to_levelup=$((exp_to_levelup + 50))

      # ステータス強化
      hp_increase=$((RANDOM % 21 + 10))  # +10〜30
      atk_min_increase=$((RANDOM % 3 + 1))  # +1〜3
      atk_max_increase=$((RANDOM % 5 + 2))  # +2〜6

      player_max_hp=$((player_max_hp + hp_increase))
      player_hp=$player_max_hp
      player_attack_min=$((player_attack_min + atk_min_increase))
      player_attack_max=$((player_attack_max + atk_max_increase))

      echo "=== レベルアップ! Lv.$player_level に上がった! ==="
      echo "最大HP +$hp_increase、攻撃力強化(+${atk_min_increase}〜+${atk_max_increase})!"
      echo "HP全回復!"
    fi

少し長いですが、今回の一番のメイン部分です。
プレイヤーの攻撃後、モンスターが倒れた次の処理に追加しています。
まずモンスターを倒した際にランダムで20~50の経験値を獲得し、現在の経験値とレベルアップに必要な経験値を表示させます。
その後レベルアップに必要な経験値の値(exp_to_levelup)を(player_exp)が超えていた場合レベルアップ判定の処理を実行し、
プレイヤーのレベルを1アップさせ、経験値の超過分を持ち越して次にレベルアップまで必要な経験値を前回の数値から+50して少し上がりにくくします。
さらにその後各ステータスの強化です。
最初に出てきていた(player_attack_min)(player_attack_max)は攻撃力の下限/上限値で、
今までは攻撃がランダムで0~40のダメージを出すようになっていましたが、
レベルアップに伴い攻撃力も上がらないとつまらないので、
下限値と上限値を設定し、レベルアップすると両ステータスが上がる事で攻撃時のランダム性はそのままにダメージを上げるように変更します。
HPも同様にランダムで最大値を上昇させ、レベルアップのタイミングでHPは全回復するようにしています。

さいごに

という事で今回はレベルアップ要素とそれに伴うステータスの設定等を行いました。
これらの要素が増えると一気にRPGっぽくなりますね!次回はモンスター側の調整等を行ってみたいと思います。
最後に変更を加えた全体を載せておきます、良かったら遊んでみてください!それでは!

#!/bin/bash

# プレイヤーのステータス
player_level=1
player_exp=0
exp_to_levelup=100
player_hp=100
player_max_hp=100
player_attack_min=10
player_attack_max=30

# ステータス表示関数
show_status() {
  echo "========================"
  echo "現在のステータス:"
  echo "Lv.$player_level"
  echo "HP: $player_hp / $player_max_hp"
  echo "攻撃力: ${player_attack_min}〜${player_attack_max}"
  echo "EXP: $player_exp / $exp_to_levelup"
  echo "========================"
}

# 敵のステータス
enemy_hp=100

echo "========================"
echo "=== バトルスタート! ==="
echo "========================"
show_status

while [ $player_hp -gt 0 ]; do
  echo
  echo "あなたのHP: $player_hp / $player_max_hp "
  echo "モンスターのHP: $enemy_hp"
  echo "1: 攻撃  2: 回復"
  read -p "→ 行動を選んでください: " action

  if [ "$action" = "1" ]; then
    damage=$((RANDOM % (player_attack_max - player_attack_min + 1) + player_attack_min))
    echo "あなたの攻撃!モンスターに $damage ダメージ!"
    enemy_hp=$((enemy_hp - damage))
  elif [ "$action" = "2" ]; then
    heal=$((RANDOM % 31 + 10))  # 10〜40HPを回復
    player_hp=$((player_hp + heal))
    [ "$player_hp" -gt "$player_max_hp" ] && player_hp=$player_max_hp
    echo "あなたは $heal 回復した!"
  else
    echo "無効な入力"
    continue
  fi

  # モンスターが倒された?
  if [ $enemy_hp -le 0 ]; then
    echo "モンスターを倒した!"

    # 経験値獲得
    gained_exp=$((RANDOM % 31 + 20))  # 20〜50EXP
    player_exp=$((player_exp + gained_exp))
    echo "経験値を $gained_exp 獲得!(現在: $player_exp / $exp_to_levelup)"

    # レベルアップ判定
    if [ $player_exp -ge $exp_to_levelup ]; then
      player_level=$((player_level + 1))
      player_exp=0
      exp_to_levelup=$((exp_to_levelup + 50))  # 次は+50必要

      # ステータス強化
      hp_increase=$((RANDOM % 21 + 10))  # +10〜30
      atk_min_increase=$((RANDOM % 3 + 1))  # +1〜3
      atk_max_increase=$((RANDOM % 5 + 2))  # +2〜6

      player_max_hp=$((player_max_hp + hp_increase))
      player_hp=$player_max_hp
      player_attack_min=$((player_attack_min + atk_min_increase))
      player_attack_max=$((player_attack_max + atk_max_increase))

      echo "=== レベルアップ! Lv.$player_level に上がった! ==="
      echo "最大HP +$hp_increase、攻撃力強化(+${atk_min_increase}〜+${atk_max_increase})!"
      echo "HP全回復!"
    fi

    enemy_hp=$((RANDOM % 50 + 100))
    echo "新たなモンスターが現れた!(HP: $enemy_hp)"
    show_status
    continue
  fi

  # 敵の攻撃ターン
  enemy_damage=$((RANDOM % 11))  # 0〜10
  echo "敵の攻撃!あなたに $enemy_damage ダメージ!"
  player_hp=$((player_hp - enemy_damage))

  if [ $player_hp -le 0 ]; then
    echo "あなたは倒れた… ゲームオーバー"
    break
  fi
done