ミニゲーム:スロットマシーン



どこにでもありそうなスロットマシーンのスクリプトです。

$scene = Scene_Slot.new
にてゲーム開始。

※以下のモジュール/スクリプトが別途導入必要です。
 縁取り文字
 ミニゲーム用共通処理モジュール
 貪藻矢射妥←ダイヤモンドベースモジュール
 ボトムキーヘルプ
 VXA風SE
 Window VXA

変更点
2008:11:12
・共通部分をモジュール化

2008:11:16
・モジュール変更に伴う修正

2008:11:23
・モジュール変更に伴う修正2

2010:03:20
・微修正

2011:06:04
・画像を統一
・よりスロットマシンらしくなるように修正
・判定直後カードの表示が消えて最終的にどんなカードだったのか分からないバグを修正

2012:01:21
・エラーメッセージを共通処理モジュールへ移動

2012:03:03
・一部の共通モジュールのクラス化
・無駄部分排除

2013:06:01
・カードの配列をひとまとめに
・オーディオファイルの設定を変更

2015:10:01
・VXA風Sound対応

2020:09:03
・Window VXA対応

#==============================================================================
# ミニゲーム:スロットマシーン By 貪藻矢射妥←
#------------------------------------------------------------------------------
# いわゆるどこにでもありがちなスロットマシーンのスクリプト。
# 
# $scene = Scene_Slot.new
# にてゲームを開始できます。
# 
# 外部カスタマイズポイントについて
# シーンをスロットに移す前に以下を設定することでスロットマシーンの難易度などを
# 変更することが可能です。(設定しなくともプレイは可能です。)
# 
# EX)
# $game_system.get_rate = [3, 1]
#  →大当たり/当たり時の掛け金基本倍率
# $game_system.slot_opt = 2
#  →1列/複数列の選択を可能にするかどうか
#    (0:真ん中1列のみ, 1:3列, 2:3列+斜め)
# $game_system.get_rate_line = [1.1, 0.6, 0.3]
#  →複数列選択可能時の賭け金倍率
# $game_system.slot_wait = 3
#  →スロットマシーンの絵柄が変わるまでの時間
# 
# ※ちなみに、普通のカスタマイズポイントにしてないのは、数種類のスロットマシーン
#  を設定したい際にスクリプトをコピペして使用しなくてもいいようにとの配慮です。
#==============================================================================
# 変更履歴
# 
# 2008:11:12
# ・共通部分をモジュール化
# 
# 2008:11:16
# ・モジュール変更に伴う修正
# 
# 2008:11:23
# ・モジュール変更に伴う修正2
#
# 2010:03:20
# ・微修正
# 
# 2011:06:04
# ・画像を統一
# ・よりスロットマシンらしくなるように修正
# ・判定直後カードの表示が消えて最終的にどんなカードだったのか分からないバグを修正
# 
# 2012:01:21
# ・エラーメッセージを共通処理モジュールへ移動
# 
# 2012:03:03
# ・一部の共通モジュールのクラス化
# ・無駄部分排除
# 
# 2013:06:01
# ・カードの配列をひとまとめに
# ・オーディオファイルの設定を変更
# 
# 2015:10:01
# ・VXA風Sound対応
# 
# 2020:09:0
# ・Window VXA対応

module SLOT
  # スロットの絵柄
  CARD_ROOT="slot_set"
  # スロット一枚のサイズ
  TR_WIDTH  = 64
  TR_HEIGHT = 96
  # 外側部分の画像
  PIC_ROOT="slot_pic"
  # 一枚のサイズ
  SP_WIDTH  = 75
  SP_HEIGHT = 35
  
  #--------------------------------------------------------------------------
  # スロットセッティング
  #--------------------------------------------------------------------------
  def set_slot
    $sl_pic = []
    for i in 0...10
      $sl_pic[i] = Rect.new(i * TR_WIDTH, 0, TR_WIDTH, TR_HEIGHT)
    end
    
    $game_pic = []
    for i in 0...5
      $game_pic[i] = Rect.new(0, i * SP_HEIGHT, SP_WIDTH, SP_HEIGHT)
    end
  end
  
  # 賭け金基本レート(スロットの絵柄の数-1分設定)
  SL_RATE = [5.0 ,4.5 ,4.0 ,3.5 ,3.0 ,2.5 ,2.0 ,1.5 ,1.0]
  
  # スロットを終える時に外部カスタマイズポイントをnilに戻すか?
  SLOT_END_FLAG = true
end

class Game_System
  #--------------------------------------------------------------------------
  # ● 公開インスタンス変数
  #--------------------------------------------------------------------------
  attr_accessor :get_rate                 # 賭け金倍率
  attr_accessor :slot_opt                 # ラインセレクト
  attr_accessor :get_rate_line            # ラインによる賭け金倍率
  attr_accessor :slot_wait                # スロットの回転ウェイト
end

class Scene_Slot
  include BM
  include SLOT
  include MINI_GAME
  #--------------------------------------------------------------------------
  # ● スロットマシーン初期化
  #--------------------------------------------------------------------------
  def slot_init(flg = true)
    @slot_flg = false
    @three_flg = false
    @stop_flg = [false, false, false]
    @bet_gold = 0
    @index = 0
    @slot = [[9, 9, 9], [9, 9, 9], [9, 9, 9]]
    set_slot
    if flg == true
      draw_slot
      draw_sl_pics
    end
  end
  #--------------------------------------------------------------------------
  # ● スロットマシーンの外側部分描画
  # opacity : 透明度のリスト
  #--------------------------------------------------------------------------
  def draw_sl_pics(opacity = [160, 160, 160, 160, 160])
    @slot_window2.contents.clear
    
    y_list = [130,  45, 215,  10, 250]
    
    for i in 0...$game_system.slot_opt * 2 + 1
      dest_src = Rect.new(10, y_list[i], SP_WIDTH, SP_HEIGHT)
      @slot_window2.contents.stretch_blt(dest_src, RPG::Cache.picture(PIC_ROOT), 
                                         $game_pic[i], opacity[i])
    end
    
    for i in 0...3
      fil_rect = Rect.new(20 + SP_WIDTH, y_list[i] + SP_HEIGHT / 2, 248, 2)
      @slot_window2.contents.fill_rect(fil_rect, Color.new(196, 196, 128, 200))
    end
  end
  #--------------------------------------------------------------------------
  # ● グラフィックの描画
  # 
  # card    : 表示カード
  # x       : 表示x座標
  # y       : 表示y座標
  # height  : 表示高さ倍率
  # set     : 上下カット(0:カットなし, 1:下カット, 2:上カット)
  # opacity : 透明度
  #--------------------------------------------------------------------------
  def draw_card(card, x, y, height = 100, set = 0, opacity = MAX8BIT)
    case set
    when 0
      src_rect = card.dup
    when 1
      src_rect = Rect.new(card.x, card.y + 16, card.width, card.height - 16)
    when 2
      src_rect = Rect.new(card.x, card.y, card.width, card.height - 16)
    end
    
    @slot_window.contents.stretch_blt(Rect.new(x, y, TR_WIDTH, TR_HEIGHT * height / 100), 
                                      RPG::Cache.picture(CARD_ROOT), 
                                      src_rect, opacity)
  end
  #--------------------------------------------------------------------------
  # ● スロットマシーンの絵柄表示
  #--------------------------------------------------------------------------
  def draw_slot
    @slot_window.contents.clear
    
    draw_card($sl_pic[@slot[0][0]],   0 + 124 - 17, 30, 60, 1)
    draw_card($sl_pic[@slot[1][0]],  80 + 124 - 17, 30, 60, 1)
    draw_card($sl_pic[@slot[2][0]], 160 + 124 - 17, 30, 60, 1)
    
    draw_card($sl_pic[@slot[0][1]],   0 + 124 - 17, 100)
    draw_card($sl_pic[@slot[1][1]],  80 + 124 - 17, 100)
    draw_card($sl_pic[@slot[2][1]], 160 + 124 - 17, 100)
    
    draw_card($sl_pic[@slot[0][2]],   0 + 124 - 17, 208, 60, 2)
    draw_card($sl_pic[@slot[1][2]],  80 + 124 - 17, 208, 60, 2)
    draw_card($sl_pic[@slot[2][2]], 160 + 124 - 17, 208, 60, 2)
  end
  #--------------------------------------------------------------------------
  # ● スロット絵柄
  #--------------------------------------------------------------------------
  def change_slot(id)
    if @card[id] == $game_system.slot_wait
      @slot[id].delete_at(0)
      @slot[id].push(rand(9))
      @card[id] = 0
    end
    @card[id] += 1
  end
  #--------------------------------------------------------------------------
  # ● スロットマシーン結果判定
  #--------------------------------------------------------------------------
  def judg_slot
    total_rate = 0
    opa_list = [160, 160, 160, 160, 160]
    
    if @slot[0][1] == @slot[1][1] && @slot[1][1] == @slot[2][1]
      total_rate += Integer($game_system.get_rate_line[$game_system.slot_opt] * 
                            $game_system.get_rate[0] * SL_RATE[@slot[0][1]])
      opa_list[0] = MAX8BIT
      draw_sl_pics(opa_list)
    end
    if @slot[0][1] == @slot[1][1] || @slot[1][1] == @slot[2][1]
      total_rate += Integer($game_system.get_rate_line[$game_system.slot_opt] * 
                            $game_system.get_rate[1] * SL_RATE[@slot[1][1]])
      opa_list[0] = MAX8BIT
      draw_sl_pics(opa_list)
    end
    if $game_system.slot_opt >= 1
      if @slot[0][0] == @slot[1][0] && @slot[1][0] == @slot[2][0]
        total_rate += Integer($game_system.get_rate_line[$game_system.slot_opt] * 
                              $game_system.get_rate[0] * SL_RATE[@slot[0][0]])
      opa_list[1] = MAX8BIT
      draw_sl_pics(opa_list)
      end
      if @slot[0][2] == @slot[1][2] && @slot[1][2] == @slot[2][2]
        total_rate += Integer($game_system.get_rate_line[$game_system.slot_opt] * 
                              $game_system.get_rate[0] * SL_RATE[@slot[0][2]])
      opa_list[2] = MAX8BIT
      draw_sl_pics(opa_list)
      end
      if @slot[0][0] == @slot[1][0] || @slot[1][0] == @slot[2][0]
        total_rate += Integer($game_system.get_rate_line[$game_system.slot_opt] * 
                              $game_system.get_rate[1] * SL_RATE[@slot[0][0]])
      opa_list[1] = MAX8BIT
      draw_sl_pics(opa_list)
      end
      if @slot[0][2] == @slot[1][2] || @slot[1][2] == @slot[2][2]
        total_rate += Integer($game_system.get_rate_line[$game_system.slot_opt] * 
                              $game_system.get_rate[1] * SL_RATE[@slot[0][2]])
      opa_list[2] = MAX8BIT
      draw_sl_pics(opa_list)
      end
    end
    if $game_system.slot_opt == 2
      if @slot[0][0] == @slot[1][1] && @slot[1][1] == @slot[2][2]
        total_rate += Integer($game_system.get_rate_line[$game_system.slot_opt] * 
                              $game_system.get_rate[0] * SL_RATE[@slot[1][1]])
      opa_list[3] = MAX8BIT
      draw_sl_pics(opa_list)
      end
      if @slot[0][2] == @slot[1][1] && @slot[1][1] == @slot[2][0]
        total_rate += Integer($game_system.get_rate_line[$game_system.slot_opt] * 
                              $game_system.get_rate[0] * SL_RATE[@slot[1][1]])
      opa_list[4] = MAX8BIT
      draw_sl_pics(opa_list)
      end
    end
    if total_rate == 0
      total_rate = -1
    end
    gets_gold = total_rate * @bet_gold
    if gets_gold > MAX_GOLD
      gets_gold = MAX_GOLD
    end
    
    if gets_gold > 0
      $game_party.gain_gold(gets_gold)
      text = GET_GOLD + gets_gold.to_s
      @info_window.refresh(text)
      if gets_gold > @bet_gold * $game_system.get_rate[0] * ($game_system.slot_opt + 1)
        $game_system.me_play(JACK_POT_ME4)
      else
        $game_system.me_play(JACK_POT_ME6)
      end
    else
      $game_party.lose_gold(@bet_gold)
      text = LOST_GOLD + @bet_gold.to_s
      @info_window.refresh(text)
      $game_system.se_play(LOOSE_ME)
    end
    
    @bet_gold = 0
    @bet_window.refresh(@bet_gold)
    @gold_window.refresh
  end
  
  #--------------------------------------------------------------------------
  # ○ キーヘルプを設定
  #--------------------------------------------------------------------------
  def set_keyhelp1
    @bottomkeyhelp_window.clear
    @bottomkeyhelp_window.set_bottom_help({"B"=>"キャンセル", 
                                           "A"=>"コインベット", 
                                           "C"=>"ゲームスタート"})
  end
  #--------------------------------------------------------------------------
  # ○ キーヘルプを設定 2
  #--------------------------------------------------------------------------
  def set_keyhelp2
    @bottomkeyhelp_window.clear
    @bottomkeyhelp_window.set_bottom_help({"C"=>"ストップ", 
                                           "B"=>"キャンセル"})
  end
  #--------------------------------------------------------------------------
  # ○ キーヘルプを設定 3
  #--------------------------------------------------------------------------
  def set_keyhelp3
    @bottomkeyhelp_window.clear
    @bottomkeyhelp_window.set_bottom_help({"矢印"=>"ベット", 
                                           "C"   =>"決定", 
                                           "B"   =>"キャンセル"})
  end
  #--------------------------------------------------------------------------
  # ● メイン処理
  #--------------------------------------------------------------------------
  def initialize
    @bottomkeyhelp_window = Window_BottomKeyHelp.new
    set_keyhelp1
  end
  
  def main
    @card = [0, 0, 0]
    
    # 外部カスタマイズポイントの設定(未設定の場合)
    if $game_system.get_rate == nil
      $game_system.get_rate = [2.5, 1.5]
    end
    if $game_system.slot_opt == nil
      $game_system.slot_opt = 0
    end
    if $game_system.get_rate_line == nil
      $game_system.get_rate_line = [1, 0.8, 0.6]
    end
    if $game_system.slot_wait == nil
      $game_system.slot_wait = 6
    end
    
    # ウィンドウを作成
    @title_window = Window_Title_Root.new
    
    @slot_window = Window_Base.new(0, 64, 480 - 10, 380 - 64)
    @slot_window.contents = Bitmap.new(480 - 10 - 32, 380 - 64 - 32)
    @slot_window2 = Window_Base.new(0, 64, 480 - 10, 380 - 64)
    @slot_window2.contents = Bitmap.new(480 - 10 - 32, 380 - 64 - 32)
    
    @info_window = Window_Info_Space.new
    
    @gold_info_window = Window_Info_Gold.new
    
    @gold_window = Window_Gold.new
    @gold_window.x = 480 - 8
    @gold_window.y = 128
  
    @bet_info_window = Window_Info_Bet.new  
    
    @bet_window = Window_Bet_Gold.new
    
    @value_window2 = Window_Base.new(200, 200, 240, 64)
    @value_window2.z = 1000
    @value_window = Window_InputNumber.new(MAX_DIG)
    @value_window.x = 200
    @value_window.y = 200
    
    @value_window2.hide
    @value_window.hide
    @value_window.deactivate
    
    slot_init
    
    @title_window.refresh("スロットマシーン")
    @bet_window.refresh(@bet_gold)
    
    # トランジション実行
    Graphics.transition
    # メインループ
    loop do
      
      if @slot_flg == true
        if @three_flg == false
          @slot = [[rand(9), rand(9), rand(9)], 
                   [rand(9), rand(9), rand(9)], 
                   [rand(9), rand(9), rand(9)]]
          @three_flg = true
        end
      end
      
      if @three_flg == true
        for id in 0..2
          if @stop_flg[id] == false
            change_slot(id)
          end
        end
        draw_slot
      end
      
      # ゲーム画面を更新
      Graphics.update
      # 入力情報を更新
      Input.update
      # フレーム更新
      update
      # 画面が切り替わったらループを中断
      if $scene != self
        break
      end
    end

    # トランジション準備
    Graphics.freeze
    # ウィンドウを解放
    @title_window.dispose
    @slot_window.dispose
    @slot_window2.dispose
    @gold_window.dispose
    @bet_window.dispose
    @value_window.dispose
    @value_window2.dispose
    @info_window.dispose
    @gold_info_window.dispose
    @bet_info_window.dispose
    @bottomkeyhelp_window.dispose
  end
  #--------------------------------------------------------------------------
  # ● フレーム更新
  #--------------------------------------------------------------------------
  def update
    if @slot_window.active
      update_main
      return
    end
    if @value_window.active
      @value_window.number = @bet_gold
      update_value
      return
    end
  end
  #--------------------------------------------------------------------------
  # ● フレーム更新 (メインウィンドウがアクティブの場合)
  #--------------------------------------------------------------------------
  def update_main
    # B ボタンが押された場合
    if Input.trigger?(Input::B)
      # キャンセル SE を演奏
      Sound.play_cancel
      $game_system.windowskin_name = WINDOW_SKIN_ROOT
      if SLOT_END_FLAG
        $game_system.get_rate = nil
        $game_system.slot_opt = nil
        $game_system.get_rate_line = nil
        $game_system.slot_wait = nil
      end
      $scene = Scene_Map.new
      return
    end
    # A ボタンが押された場合
    if Input.trigger?(Input::A)
      # 決定 SE を演奏
      Sound.play_ok
      # 念の為
      draw_slot
      draw_sl_pics
      @value_window.show
      @value_window.activate
      @value_window2.show
      @slot_window.deactivate
      set_keyhelp3
      return
    end
    # C ボタンが押された場合
    if Input.trigger?(Input::C)
      if @bet_gold == 0
        # エラー SE を演奏
        $game_system.se_play(ERROR_SE)
        text =  "まずは" + MG_ERR_BET_ZERO
        @info_window.refresh(text)
      else
        # 決定 SE を演奏
        Sound.play_ok
        @info_window.refresh("")
        if @slot_flg == false
          @slot_flg = true
          set_keyhelp2
        elsif @slot_flg == true
          if @stop_flg[0] == false
            @stop_flg[0] = true
          elsif @stop_flg[1] == false
            @stop_flg[1] = true
          elsif @stop_flg[2] == false
            @stop_flg[2] = true
          end
        end
        if @stop_flg[2] == true
          judg_slot
          slot_init(false)
          set_keyhelp1
        end
        return
      end
    end
  end
  #--------------------------------------------------------------------------
  # ● フレーム更新 (バリューウィンドウがアクティブの場合)
  #--------------------------------------------------------------------------
  def update_value
    # C ボタンが押された場合
    if Input.trigger?(Input::C)
      if @bet_gold > $game_party.gold
        # エラー SE を演奏
        $game_system.se_play(ERROR_SE)
        @info_window.refresh(MG_ERR_BET_UPPER)
      elsif @bet_gold == 0
        # エラー SE を演奏
        $game_system.se_play(ERROR_SE)
        @info_window.refresh(MG_ERR_BET_ZERO)
      else
        # 決定 SE を演奏
        Sound.play_ok
        @info_window.refresh("")
        @value_window.hide
        @value_window.deactivate
        @value_window2.hide
        @slot_window.activate
        @bet_window.refresh(@bet_gold)
        set_keyhelp1
      return
      end
    end
    # B ボタンが押された場合
    if Input.trigger?(Input::B)
      # キャンセル SE を演奏
      Sound.play_cancel
      @value_window.hide
      @value_window.deactivate
      @value_window2.hide
      @slot_window.activate
      set_keyhelp1
      return
    end
    # Window_InputNumberに処理を移す
    @value_window.update
    @bet_gold = @value_window.number
  end
end
こぉんな感じになります。 使用画像はこちらにありマス カスタマイズポイントの設定
外部カスタマイズポイント
変数 設定例 説明
$game_system.get_rate [3, 1] 大当たり/当たり時の掛け金基本倍率
$game_system.slot_opt 2 1列/複数列の選択を可能にするかどうか
(0:真ん中1列のみ, 1:3列, 2:3列+斜め)
$game_system.get_rate_line [1.1, 0.6, 0.3] 複数列選択可能時の賭け金倍率
$game_system.slot_wait 3 スロットマシーンの絵柄が変わるまでの時間
内部カスタマイズポイント(一部省略)
変数 設定例 説明
SL_RATE [5.0 ,4.5 ,4.0 ,3.5 ,3.0 ,2.5 ,2.0 ,1.5 ,1.0] 賭け金基本レート(スロットの絵柄の数-1分設定)
MAX_DIG 7 入力金額最高桁数
SLOT_END_FLAG true スロットを終える時に外部カスタマイズポイントをnilに戻すか?

戻る