価格の変動(アイテム装備)



ある装備をしていると価格が変動するスクリプトです。
(エストポリス伝記に出てくるエンゲージリングみたいな感じ。)

※以下のモジュールが別途導入必要です。
 貪藻矢射妥←ダイヤモンドベースモジュール
 TOI風最大所持数変更モジュール
 VXA風SE

※このスクリプトを導入後は最初からはじめないと(価格変動装備品を装備せずショップ画面に移った際に)
 エラーをはきます。

 (途中から導入したい場合は、どこかでショップ画面に移る前にイベントのスクリプトで
 $game_system.price_off = 1
 $game_system.premium   = 1
 を実行してください。)

※TOI風最大所持数変更に対応したため、上記以外に
 $game_system.max_hold_change(0)
 を実行しないと同じくショップ画面に移る際にエラー落ちします。

変更点
2008:12:16
・最大保持数を別モジュール化
・TOI風最大所持数変更に対応

2009:05:07
・購入項目に並んでいないものを売却しようとした際、価格が変動しないバグを修正

2009:05:08
・売却時しか価格の変動に対応していなかったバグを修正
・価格変動装飾品IDをカスタマイズポイントへ移行

2009:06:03
・ロード直後は設定が反映されないバグを修正

2010:03:27
・最大購入可能個数を計算においてTOI風最大所持数変更を導入していなかった際最大所持数が設定されない
 バグを修正

2015:10:01
・VXA風Sound対応

スクリプト本体
#==============================================================================
# ■ 価格変動 β By 貪藻矢射妥←
# 
#  ・あるアイテムを装備することで購入価格、売却価格を変動させます。
# 
#  ※このスクリプトを導入後は最初からはじめないと(価格変動装備品を装備せず
#   ショップ画面に移った際に)エラーをはきます。
#   (途中から導入したい場合は、どこかでショップ画面に移る前にイベントの
#    スクリプトで
#    $game_system.price_off = 1
#    $game_system.premium   = 1
#    を実行してください。)
# 
#  ※TOI風最大所持数変更に対応したため、上記以外に
#   $game_system.max_hold_change(0)
#   を実行しないと同じくショップ画面に移る際にエラー落ちします。
# 
#  ※if actor.○○_id == m を if actor.states.include?(n) に変更すれば
#   あるステートにかかっているアクターがいる場合価格が変動するように変更
#   できます。
# 
#==============================================================================
# 更新っぽいもの
# 
# 2008:12:16
# ・最大保持数を別モジュール化
# ・TOI風最大所持数変更に対応
# 
# 2009:05:07
# ・購入項目に並んでいないものを売却しようとした際、価格が変動しないバグを修正
# 
# 2009:05:08
# ・売却時しか価格の変動に対応していなかったバグを修正
#  (■ Window_ShopNumber)
# ・価格変動装飾品IDをカスタマイズポイントへ移行
# 
# 2010:03:27
# ・最大購入可能個数を計算においてTOI風最大所持数変更を導入していなかった際
#  最大所持数が設定されないバグを修正
# 
# 2015:10:01
# ・VXA風Sound対応
# 
# 2016:05:01
# ・価値観の違いによる価格変動の外部フラグ対応

$OuterFlgs = {} if $OuterFlgs == nil
$OuterFlgs["Price_Change_I"] = true

class Game_System
  #--------------------------------------------------------------------------
  # ● 公開インスタンス変数
  #--------------------------------------------------------------------------
  attr_accessor :price_off                # プライスオフ変数
  attr_accessor :premium                  # プレミア変数
  
  attr_reader   :max_hold_value           # 外部最大所持数
end

#==============================================================================
# ■ Game_Party
#------------------------------------------------------------------------------
#  パーティを扱うクラスです。ゴールドやアイテムなどの情報が含まれます。このク
# ラスのインスタンスは $game_party で参照されます。
#==============================================================================
class Game_Party
  #--------------------------------------------------------------------------
  # ● オブジェクト初期化
  #--------------------------------------------------------------------------
  alias diamond_initialize initialize
  def initialize
    diamond_initialize
    # 価格変動の初期化
    $game_system.price_off = 1
    $game_system.premium   = 1
  end
end

#==============================================================================
# ■ Scene_Shop
#------------------------------------------------------------------------------
#  ショップ画面の処理を行うクラスです。
#==============================================================================
class Scene_Shop
  include BM
  #--------------------------------------------------------------------------
  # ● フレーム更新 (購入ウィンドウがアクティブの場合)
  #--------------------------------------------------------------------------
  def update_buy
    # ステータスウィンドウのアイテムを設定
    @status_window.item = @buy_window.item
    # B ボタンが押された場合
    if Input.trigger?(Input::B)
      # キャンセル SE を演奏
      Sound.play_cancel
      # ウィンドウの状態を初期モードへ
      @command_window.active = true
      @dummy_window.visible = true
      @buy_window.active = false
      @buy_window.visible = false
      @status_window.visible = false
      @status_window.item = nil
      # ヘルプテキストを消去
      @help_window.set_text("")
      return
    end
    # C ボタンが押された場合
    if Input.trigger?(Input::C)
      # アイテムを取得
      @item = @buy_window.item
      # アイテムが無効の場合、または価格が所持金より上の場合
      if @item == nil or @item.price > $game_party.gold
        # ブザー SE を演奏
        Sound.play_buzzer
        return
      end
      # アイテムの所持数を取得
      case @item
      when RPG::Item
        number = $game_party.item_number(@item.id)
      when RPG::Weapon
        number = $game_party.weapon_number(@item.id)
      when RPG::Armor
        number = $game_party.armor_number(@item.id)
      end
      # すでに BM::MAX_HOLD 個所持している場合
      if $OuterFlgs["Max_Hold_Change"]
        max_hold = MAX_HOLD[$game_system.max_hold_value]
      else
        max_hold = DEFAULT_MH
      end
      if number == max_hold
        # ブザー SE を演奏
        Sound.play_buzzer
        return
      end
      # 決定 SE を演奏
      Sound.play_ok
      # 最大購入可能個数を計算
      change_price = Integer(@item.price / $game_system.price_off)
      if $OuterFlgs["Max_Hold_Change"]
        max_hold = MAX_HOLD[$game_system.max_hold_value]
      else
        max_hold = DEFAULT_MH
      end
      max = @item.price == 0 ? max_hold : $game_party.gold / change_price
      max = [max, max_hold - number].min
      # ウィンドウの状態を個数入力モードへ
      @buy_window.active = false
      @buy_window.visible = false
      @number_window.set(@item, max, change_price)
      @number_window.active = true
      @number_window.visible = true
    end
  end
  #--------------------------------------------------------------------------
  # ● フレーム更新 (売却ウィンドウがアクティブの場合)
  #--------------------------------------------------------------------------
  def update_sell
    # B ボタンが押された場合
    if Input.trigger?(Input::B)
      # キャンセル SE を演奏
      Sound.play_cancel
      # ウィンドウの状態を初期モードへ
      @command_window.active = true
      @dummy_window.visible = true
      @sell_window.active = false
      @sell_window.visible = false
      @status_window.item = nil
      # ヘルプテキストを消去
      @help_window.set_text("")
      return
    end
    # C ボタンが押された場合
    if Input.trigger?(Input::C)
      # アイテムを取得
      @item = @sell_window.item
      # ステータスウィンドウのアイテムを設定
      @status_window.item = @item
      # アイテムが無効の場合、または価格が 0 (売却不可) の場合
      if @item == nil or @item.price == 0
        # ブザー SE を演奏
        Sound.play_buzzer
        return
      end
      # 決定 SE を演奏
      Sound.play_ok
      # アイテムの所持数を取得
      case @item
      when RPG::Item
        number = $game_party.item_number(@item.id)
      when RPG::Weapon
        number = $game_party.weapon_number(@item.id)
      when RPG::Armor
        number = $game_party.armor_number(@item.id)
      end
      # 最大売却個数 = アイテムの所持数
      max = number
      # ウィンドウの状態を個数入力モードへ
      @sell_window.active = false
      @sell_window.visible = false
      change_price = Integer(@item.price / 2 * $game_system.premium)
      @number_window.set(@item, max, change_price)
      @number_window.active = true
      @number_window.visible = true
      @status_window.visible = true
    end
  end
  include DIAMOND
  #--------------------------------------------------------------------------
  # ● フレーム更新 (個数入力ウィンドウがアクティブの場合)
  #--------------------------------------------------------------------------
  def update_number
    # B ボタンが押された場合
    if Input.trigger?(Input::B)
      # キャンセル SE を演奏
      Sound.play_cancel
      # 個数入力ウィンドウを非アクティブ・不可視に設定
      @number_window.active = false
      @number_window.visible = false
      # コマンドウィンドウのカーソル位置で分岐
      case @command_window.index
      when 0  # 購入する
        # ウィンドウの状態を購入モードへ
        @buy_window.active = true
        @buy_window.visible = true
      when 1  # 売却する
        # ウィンドウの状態を売却モードへ
        @sell_window.active = true
        @sell_window.visible = true
        @status_window.visible = false
      end
      return
    end
    # C ボタンが押された場合
    if Input.trigger?(Input::C)
      # ショップ SE を演奏
      Sound.play_shop
      # 個数入力ウィンドウを非アクティブ・不可視に設定
      @number_window.active = false
      @number_window.visible = false
      
      # 価格の変動!
      if $OuterFlgs["Price_Change_AB"]
        
        set_root_price(@item)
        
        case @item
        when RPG::Item
          if $game_switches[CH_P_FLG] && PROCEB_ITEM[@item.id] != nil
            @item.price = PROCEB_ITEM[@item.id]
          else
            @item.price = $game_system.root_price_items[@item.id]
          end
        when RPG::Weapon
          if $game_switches[CH_P_FLG] && PROCEB_WEAPON[@item.id] != nil
            @item.price = PROCEB_WEAPON[@item.id]
          else
            @item.price = $game_system.root_price_weapons[@item.id]
          end
        when RPG::Armor
          if $game_switches[CH_P_FLG] && PROCEB_ARMOR[@item.id] != nil
            @item.price = PROCEB_ARMOR[@item.id]
          else
            @item.price = $game_system.root_price_armors[@item.id]
          end
        end
        if @item.price == nil
          p "価格がエラってます・・・"
        end
      end
      
      # コマンドウィンドウのカーソル位置で分岐
      case @command_window.index
      when 0  # 購入する
        # 購入処理
        
        change_price = Integer(@item.price / $game_system.price_off)
        $game_party.lose_gold(@number_window.number * change_price)
        case @item
        when RPG::Item
          $game_party.gain_item(@item.id, @number_window.number)
        when RPG::Weapon
          $game_party.gain_weapon(@item.id, @number_window.number)
        when RPG::Armor
          $game_party.gain_armor(@item.id, @number_window.number)
        end
        # 各ウィンドウをリフレッシュ
        @gold_window.refresh
        @buy_window.refresh
        @status_window.refresh
        # ウィンドウの状態を購入モードへ
        @buy_window.active = true
        @buy_window.visible = true
      when 1  # 売却する
        # 売却処理
        
        change_price = Integer(@item.price / 2 * $game_system.premium)
        $game_party.gain_gold(@number_window.number * change_price)
        case @item
        when RPG::Item
          $game_party.lose_item(@item.id, @number_window.number)
        when RPG::Weapon
          $game_party.lose_weapon(@item.id, @number_window.number)
        when RPG::Armor
          $game_party.lose_armor(@item.id, @number_window.number)
        end
        # 各ウィンドウをリフレッシュ
        @gold_window.refresh
        @sell_window.refresh
        @status_window.refresh
        # ウィンドウの状態を売却モードへ
        @sell_window.active = true
        @sell_window.visible = true
        @status_window.visible = false
      end
      return
    end
  end
end
装飾品による価格変動部分
class Game_Actor < Game_Battler
  include DIA_PC
  #--------------------------------------------------------------------------
  # ● 装備の変更
  #     equip_type : 装備タイプ
  #     id    : 武器 or 防具 ID  (0 なら装備解除)
  #--------------------------------------------------------------------------
  def equip(equip_type, id)
    $game_system.price_off = 1
    $game_system.premium   = 1
    case equip_type
    when 0  # 武器
      if id == 0 or $game_party.weapon_number(id) > 0
        $game_party.gain_weapon(@weapon_id, 1)
        @weapon_id = id
        $game_party.lose_weapon(id, 1)
      end
    when 1  # 盾
      if id == 0 or $game_party.armor_number(id) > 0
        update_auto_state($data_armors[@armor1_id], $data_armors[id])
        $game_party.gain_armor(@armor1_id, 1)
        @armor1_id = id
        $game_party.lose_armor(id, 1)
      end
    when 2  # 頭
      if id == 0 or $game_party.armor_number(id) > 0
        update_auto_state($data_armors[@armor2_id], $data_armors[id])
        $game_party.gain_armor(@armor2_id, 1)
        @armor2_id = id
        $game_party.lose_armor(id, 1)
      end
    when 3  # 身体
      if id == 0 or $game_party.armor_number(id) > 0
        update_auto_state($data_armors[@armor3_id], $data_armors[id])
        $game_party.gain_armor(@armor3_id, 1)
        @armor3_id = id
        $game_party.lose_armor(id, 1)
      end
    when 4  # 装飾品
      if id == 0 or $game_party.armor_number(id) > 0
        update_auto_state($data_armors[@armor4_id], $data_armors[id])
        $game_party.gain_armor(@armor4_id, 1)
        @armor4_id = id
        $game_party.lose_armor(id, 1)
      end
    end
    
    for actor in $game_party.actors
      next if actor.id == @actor.id
      if actor.armor4_id == PC_ACC
        $game_system.price_off = 2
      end
    end
    
    $game_map.refresh
  end
end
Game_Party
class Game_Party
  include DIA_MM
  #--------------------------------------------------------------------------
  # ● パーティメンバーのリフレッシュ
  #--------------------------------------------------------------------------
  def refresh
    # ゲームデータをロードした直後はアクターオブジェクトが
    # $game_actors から分離してしまっている。
    # ロードのたびにアクターを再設定することで問題を回避する。
    new_actors = []
    for i in 0...@actors.size
      if $data_actors[@actors[i].id] != nil
        new_actors.push($game_actors[@actors[i].id])
      end
    end
    
    for actor in $game_party.actors
      next if actor.id == @actor.id
      if actor.armor4_id == PC_ACC
        $game_system.price_off = 2
      end
    end
    
    @actors = new_actors
  end
end
Window_ShopNumber
class Game_System
  #--------------------------------------------------------------------------
  # ● 公開インスタンス変数
  #--------------------------------------------------------------------------
  attr_accessor :shop_value               # 購入/売却用外部変数
end

#==============================================================================
# ■ Scene_Shop
#------------------------------------------------------------------------------
#  ショップ画面の処理を行うクラスです。
#==============================================================================

class Scene_Shop
  #--------------------------------------------------------------------------
  # ● フレーム更新
  #--------------------------------------------------------------------------
  alias update_diamond update
  def update
    $game_system.shop_value = @command_window.index
    
    # 元の処理を行う
    update_diamond
  end
end

#==============================================================================
# ■ Window_ShopNumber
#------------------------------------------------------------------------------
#  ショップ画面で、購入または売却するアイテムの個数を入力するウィンドウです。
#==============================================================================

class Window_ShopNumber < Window_Base
  include DIAMOND
  #--------------------------------------------------------------------------
  # ● リフレッシュ
  #--------------------------------------------------------------------------
  def refresh
    self.contents.clear
    draw_item_name(@item, 4, 96)
    rectr  = [272, 96, 32, 32]
    rectr2 = [308, 96, 24, 32]
    draw_shadow_text(rectr, "×")
    draw_shadow_text(rectr2, @number.to_s, normal_color, 2)
    self.cursor_rect.set(304, 96, 32, 32)
    # 合計価格と通貨単位を描画
    
    if $OuterFlgs["Price_Change_AB"]
      
      set_root_price(item)
      
      case @item
      when RPG::Item
        if $game_switches[CH_P_FLG] && PROCEB_ITEM[@item.id] != nil
          @price = PROCEB_ITEM[@item.id]
        else
          @price = $game_system.root_price_items[@item.id]
        end
      when RPG::Weapon
        if $game_switches[CH_P_FLG] && PROCEB_WEAPON[@item.id] != nil
          @price = PROCEB_WEAPON[@item.id]
        else
          @price = $game_system.root_price_weapons[@item.id]
        end
      when RPG::Armor
        if $game_switches[CH_P_FLG] && PROCEB_ARMOR[@item.id] != nil
          @price = PROCEB_ARMOR[@item.id]
        else
          @price = $game_system.root_price_armors[@item.id]
        end
      end
      if @price == nil
        p "価格がエラってます・・・"
      end
    end
    
    # 購入か売却かによって変更
    if $OuterFlgs["Price_Change_I"]
      if $game_system.shop_value == 0
        @price /= $game_system.price_off
      else
        @price *= $game_system.premium
      end
    end
    
    if $OuterFlgs["Price_Change_AB"]
      total_price = Integer(@price) * @number
    else
      total_price = @price * @number
    end
    if !KGC::ICMP_HIDE_ZERO_COST || total_price > 0
      domination = Vocab::gold
      cx = contents.text_size(domination).width
      rectr3 = [4, 160, 328-cx-2, 32]
      rectr4 = [332-cx, 160, cx, 32]
      draw_shadow_text(rectr3, total_price.to_s, normal_color, 2)
      draw_shadow_text(rectr4, domination, system_color, 2)
    end
  end
end
薄緑色の部分にて設定を行います。 (例では防具ID388(装飾品)を装備している場合、半額になるという設定になってます。) ・変数の使い方 price_off :購入時の値段の変動(大きくなるほど安くなる) premium  :売却時の値段の変動(大きくなるほど高くなる) ※実はカスタマイズポイントで値段の半減とかを行ってないので使い勝手が悪いという・・・

戻る