기타

Economy System by Nick@Creation Asylum

by 백호 posted Feb 22, 2009
?

단축키

Prev이전 문서

Next다음 문서

ESC닫기

크게 작게 위로 아래로 댓글로 가기 인쇄
http://www.dubealex.com/asylum/index.php?showtopic=4885
  상점의 품목, 물품 수량, 상점생성은 이벤트 편집->스크립트에서 이루어집니다.  재고수량이 적어질수록 가격은 오르고, 역으로 수량이 늘수록 가격은 떨어집니다.  물론 재고가 소진되더라도 지정된 시간간격으로 재고가 하나씩 차게 됩니다.


#----------------------------------------------------------------------------
# Economic Shop System - by Nick
# Version 2.134 (Hell yeah)
#----------------------------------------------------------------------------
# You may delete all comments except copyright.
# How to use:
# Step 1:
# -Create a shop using $eco.add_shop("name", "trade_type", "description")
# -"name", the store name, to identify shops, cant make 2 shops with same name
# -"trade_type", Standard it is both so you dont have to enter it, use "buy"
# -Or "sell" for buy/sell only shops.
# Step 2:
# -Add items using $eco.add_item(shop, item, type, amount, time_per_unit)
# -Shop can be either shop name or id.
# -Item is just the item id in the database.
# -Type is item(0), weapon(1) or armor(2)
# -Amount is the amount of items automatic in stock and it will restock to.
# -Time_per_unit is the time for 1 item to restock.
# Step 3:
# -Use call script; $scene = Eco_Scene_Shop.new(shopname/id)
# Note:
# -You can also use step 1 and 2 in Game_Economy, def initialize if you prefer.
# -Just replace $eco.shops with just @shops.
# Extra's:
# -If you are going to add items, it might be handier to use ID instead of name
# -For quick acces to ID use @id = $eco.retrieve_id(shopname) to put it in a string
# -Use module ES to adjust quick settings.
# -If you dont like the way i used to set prices, adjust def price in Data_Shopitems
# -And def calprice in Eco_Window_ShopNumber
#----------------------------------------------------------------------------
# Made by: Nick alias "PieNick, "Paashaas", "Generaal Gek", "Ali Anthrax"
# Thanks to: Near_Fantastica for the idea and his great scripts
#----------------------------------------------------------------------------
module ES
  RESTOCK = true # Restock items?
  CT = true # In the shop menu, let the user choose item type? 
  SHOPNAME = true # Show shopname in help window when empty?
end

class Data_ShopItems
  # All data for items are stored here, and the price calculating
  attr_accessor :item
  attr_accessor :type
  attr_accessor :stock
  attr_accessor :default
  attr_accessor :time_per_unit
  attr_accessor :time_start
  #--------------------------------------------------------------------------
  def initialize(item, type, default, time_per_unit)
    @item = item
    @type = type
    @stock = default   
    @default = default
    @time_per_unit = time_per_unit
    @time_start = Graphics.frame_count
  end
  #--------------------------------------------------------------------------
  def price(sell = false)
    case type
    when 0
      base = $data_items
    when 1
      base = $data_weapons
    when 2
      base = $data_armors
    end
    @baseprice = base[@item].price.to_f
    if @default != 0
      range = @default.to_f / @stock.to_f
    else
      if sell
        range = 1.30
        for i in 0...@stock
          range -= 0.05 if range >= 0.80
        end
      else
        range = 2.16
        for i in 0...@stock
          range -= 0.16 if range >= 0.70
        end
      end
    end
    range = 1.25 if range.nan?
    if sell
      @base = @baseprice / 2
      if range == 1
        @newprice = @base
      elsif range > 1
        @newprice = @base * (range * range)     
      else
        @newprice = @base * range
      end
      @newprice = @baseprice * 3 if @newprice > @baseprice * 3
      @newprice = @baseprice / 3 if @newprice < @baseprice / 3   
    else
      @newprice = @baseprice * range
      @newprice = @baseprice * 2 if @newprice > @baseprice * 2
      @newprice = @baseprice / 2 if @newprice < @baseprice / 2
    end
    @newprice = @newprice.round
    return @newprice
  end
end

class Data_Shop
  # All data for shops is here
  attr_accessor :name
  attr_accessor :items
  attr_accessor :trade_type
  #--------------------------------------------------------------------------
  def initialize(name, trade_type)
    @name = name
    @trade_type = trade_type
    @items = []
  end
end

class Game_Economy
  # Also known as $eco
  attr_accessor :shops
  #--------------------------------------------------------------------------
  def initialize
    @shops = []
    # After this, you can also create shops and put items in them
  end
  #--------------------------------------------------------------------------
  # Checks every shop and every item if it needs restocking, i think it could
  # Cause lag if it needs to search alot of things...
  def restock
    for shop in 0...@shops.size
      for item in 0...@shops[shop].items.size
        itemdata = @shops[shop].items[item]
        times = (Graphics.frame_count.to_f - itemdata.time_start.to_f) / itemdata.time_per_unit.to_f
        if times >= 1.00 and itemdata.time_per_unit != 0
          itemdata.time_start = Graphics.frame_count
          if itemdata.stock > itemdata.default
            itemdata.stock -= times.floor       
          elsif itemdata.stock < itemdata.default
            itemdata.stock += times.floor             
          end
        end
      end
    end
  end
  #--------------------------------------------------------------------------
  # Add shops using this
  def add_shop(name, trade_type = "both")   
    @shops.push(Data_Shop.new(name, trade_type)) unless $eco.shops.index(name)
  end
  #--------------------------------------------------------------------------
  # Add items to shops using this
  def add_item(shop, item, type, default, time_per_unit)
    if shop.is_a?(Fixnum)
      @id = shop
      @name = @shops[@id].name     
    else
      @name = shop
      @id = retrieve_id(shop)
    end
    tpu = time_per_unit * Graphics.frame_rate
    @shops[@id].items.push(Data_ShopItems.new(item, type, default, tpu))
  end
  #--------------------------------------------------------------------------
  # Quick ID
  def retrieve_id(shop)
    for i in 0...@shops.size
      if @shops[i].name == shop
        return i
      end
    end
  end
  #--------------------------------------------------------------------------
  # Created to let you use $eco.price to check price
  def price(shop, item, group, sell = false)
    if shop.is_a?(Fixnum)
      @id = shop
      @name = @shops[@id].name     
    else
      @name = shop
      @id = retrieve_id(shop)
    end
    for i in 0...@shops[@id].items.size
      @i = i
      if @shops[@id].items[i].item == item and @shops[@id].items[i].type == group
        item_id = i
        break
      end
    end
    if item_id
      return @shops[@id].items[item_id].price(sell)
    else
      case group
      when 0
        item = $data_items[item]
      when 1
        item = $data_weapons[item]
      when 2
        item = $data_armors[item]
      end
      return item.price * 3
    end
  end
end
# Addition to scene_title to set $eco
class Scene_Title
 alias eco_scene_title_cng command_new_game
  def command_new_game
    eco_scene_title_cng
    $eco = Game_Economy.new
  end
end
# Addition to scene_map to restock items
class Scene_Map
 alias eco_scene_map_update update
  def update
    if ES::RESTOCK
      $eco.restock
    end
    eco_scene_map_update
  end
end
# Addition to scene_load and scene_save to store data
class Scene_Load < Scene_File
 alias eco_scene_load_rsd read_save_data
 def read_save_data(file)
  eco_scene_load_rsd(file)
  $eco = Marshal.load(file)
 end
end

class Scene_Save < Scene_File
 alias eco_scene_save_wsd write_save_data
 def write_save_data(file)
  eco_scene_save_wsd(file)
  Marshal.dump($eco, file)
 end
end

# Scene classes.. They're called Eco_*original name* so you can still use
# The default shop without my nifty system :)
class Window_ShopCommand
  def draw_item(index, color = normal_color)
    self.contents.font.color = color
    rect = Rect.new(4 + index * 160, 0, self.contents.width - 8, 32)
    self.contents.fill_rect(rect, Color.new(0, 0, 0, 0))
    self.contents.draw_text(rect, @commands[index])
  end
  #--------------------------------------------------------------------------
  def disable_item(index)   
    self.contents.clear
    for i in 0...@item_max
      if i == index
        draw_item(i, disabled_color)
      else
        draw_item(i)
      end
    end
  end 
end

class Eco_Scene_Shop
  def initialize(shop)
    if shop.is_a?(Fixnum)
      @id = shop
      @name = $eco.shops[@id].name     
    else
      @name = shop
      for i in 0...$eco.shops.size
        if $eco.shops[i].name == @name
          @id = i
          break
        end
      end
    end
    if @name != $eco.shops[@id].name
      print "Error finding shop: " + shop
    end
    main
  end
  #--------------------------------------------------------------------------
  def main
    @help_window = Window_Help.new
    if ES::SHOPNAME
      @help_window.set_text($eco.shops[@id].name)
    else
      @help_window.set_text("")
    end
    @command_window = Window_ShopCommand.new
    if $eco.shops[@id].trade_type == "sell"
      @command_window.disable_item(0)
    elsif $eco.shops[@id].trade_type == "buy"
      @command_window.disable_item(1)
    end
    @gold_window = Window_Gold.new
    @gold_window.x = 480
    @gold_window.y = 64
    @dummy_window = Window_Base.new(0, 128, 640, 352)
    @buy_window = Eco_Window_ShopBuy.new(@id)
    @buy_window.active = false
    @buy_window.visible = false
    @buy_window.help_window = @help_window
    @sell_window = Eco_Window_ShopSell.new
    @sell_window.active = false
    @sell_window.visible = false
    @sell_window.help_window = @help_window
    @number_window = Eco_Window_ShopNumber.new
    @number_window.active = false
    @number_window.visible = false
    @status_window = Window_ShopStatus.new
    @status_window.visible = false
    @select_window = Window_Command.new(160, ["All", "Items", "Weapons", "Armor"])
    @select_window.x = 240
    @select_window.y = 180
    @select_window.active = false
    @select_window.visible = false
    itemstock = false
    weaponstock = false
    armorstock = false
    for i in $eco.shops[@id].items
      itemstock = true if i.type == 0
      weaponstock = true if i.type == 1
      armorstock = true if i.type == 2
    end
    @select_window.disable_item(1) if !itemstock and !weaponstock and !armorstock 
    @select_window.disable_item(1) if !itemstock
    @select_window.disable_item(2) if !weaponstock
    @select_window.disable_item(3) if !armorstock 
    Graphics.transition
    loop do
      Graphics.update
      Input.update
      update
      if $scene != self
        break
      end
    end
    Graphics.freeze
    @help_window.dispose
    @command_window.dispose
    @gold_window.dispose
    @dummy_window.dispose
    @buy_window.dispose
    @sell_window.dispose
    @number_window.dispose
    @status_window.dispose
    @select_window.dispose
  end
  #--------------------------------------------------------------------------
  def update
    @help_window.update
    @command_window.update
    @gold_window.update
    @dummy_window.update
    @buy_window.update
    @sell_window.update
    @number_window.update
    @status_window.update
    @select_window.update
    if @command_window.active
      update_command
      return
    end
    if @sell_window.active == true or @buy_window.active == true
      itemstock = false
      weaponstock = false
      armorstock = false
      for i in $eco.shops[@id].items
        itemstock = true if i.type == 0
        weaponstock = true if i.type == 1
        armorstock = true if i.type == 2
      end
      normal_color = Color.new(255, 255, 255, 255)
      if !itemstock and !weaponstock and !armorstock
        @select_window.disable_item(0)
      else
        @select_window.draw_item(0, normal_color)
      end
      if !itemstock
        @select_window.disable_item(1)
      else
        @select_window.draw_item(1, normal_color)
      end
      if !weaponstock
        @select_window.disable_item(2)
      else
        @select_window.draw_item(2, normal_color)
      end
      if !armorstock
        @select_window.disable_item(3)
      else
        @select_window.draw_item(3, normal_color)
      end   
    end
    if @buy_window.active
      @sell_window.refresh
      update_buy
      return
    end
    if @sell_window.active
      @buy_window.refresh
      update_sell
      return
    end
    if @number_window.active
      update_number
      return
    end
    if @select_window.active
      update_select
      return
    end
  end
  #--------------------------------------------------------------------------
  def update_command
    if Input.trigger?(Input::B)
      $game_system.se_play($data_system.cancel_se)
      $scene = Scene_Map.new
      return
    end
    if Input.trigger?(Input::C)
      case @command_window.index
      when 0
        if $eco.shops[@id].trade_type != "sell"
          $game_system.se_play($data_system.decision_se)
          @command_window.active = false
          if ES::CT
            @select_window.visible = true
            @select_window.active = true
          else
            $game_system.se_play($data_system.decision_se)
            @buy_window.category = 3
            @buy_window.reset
            @buy_window.refresh
            @buy_window.help_window = @help_window
            @dummy_window.visible = false
            @buy_window.active = true
            @buy_window.visible = true
            @status_window.visible = true
          end
        else
          $game_system.se_play($data_system.buzzer_se)
        end
      when 1
        if $eco.shops[@id].trade_type != "buy"
          $game_system.se_play($data_system.decision_se)
          @command_window.active = false
          @dummy_window.visible = false
          @sell_window.active = true
          @sell_window.visible = true
        else
          $game_system.se_play($data_system.buzzer_se)
        end
      when 2
        $game_system.se_play($data_system.decision_se)
        $scene = Scene_Map.new
      end
      return
    end
  end
  #--------------------------------------------------------------------------
  def update_buy
    @status_window.item = @buy_window.item
    if Input.trigger?(Input::B)
      $game_system.se_play($data_system.cancel_se)
      @command_window.active = true
      @dummy_window.visible = true
      @buy_window.active = false
      @buy_window.visible = false
      @status_window.visible = false
      @status_window.item = nil
      if ES::SHOPNAME
        @help_window.set_text($eco.shops[@id].name)
      else
        @help_window.set_text("")
      end
      return
    end
    if Input.trigger?(Input::C)
      @item = @buy_window.item
      case @item
      when RPG::Item
        number = $game_party.item_number(@item.id)
        group = 0
      when RPG::Weapon
        number = $game_party.weapon_number(@item.id)
        group = 1
      when RPG::Armor
        number = $game_party.armor_number(@item.id)
        group = 2
      end
      for i in $eco.shops[@id].items
        @item_data = i if i.item == @item.id and i.type == group
      end
      eco_max = @item_data.stock
      if @item == nil or $eco.price(@id, @item.id, @item_data.type) > $game_party.gold or 0 >= eco_max
        $game_system.se_play($data_system.buzzer_se)
        return
      end
      if number == 99
        $game_system.se_play($data_system.buzzer_se)
        return
      end
      $game_system.se_play($data_system.decision_se)
      @buy_window.active = false
      @buy_window.visible = false
      @number_window.set(@id, @item, @item_data.type)
      @number_window.active = true
      @number_window.visible = true
    end
  end
  #--------------------------------------------------------------------------
  def update_sell
    if Input.trigger?(Input::B)
      $game_system.se_play($data_system.cancel_se)
      @sell_window.active = false
      @sell_window.visible = false
      @status_window.item = nil
      if ES::SHOPNAME
        @help_window.set_text($eco.shops[@id].name)
      else
        @help_window.set_text("")
      end
      @command_window.active = true
      @dummy_window.visible = true
      @buy_window.reset
      @buy_window.refresh
      @buy_window.help_window = @help_window
      return
    end
    if Input.trigger?(Input::C)
      @item = @sell_window.item
      @status_window.item = @item
      case @item
      when RPG::Item
        group = 0
      when RPG::Weapon
        group = 1
      when RPG::Armor
        group = 2
      end
      if @item == nil or $eco.price(@id, @item.id, group, true) == 0
        $game_system.se_play($data_system.buzzer_se)
        return
      end
      $game_system.se_play($data_system.decision_se)
      @sell_window.active = false
      @sell_window.visible = false
      @number_window.set(@id, @item, group, sell = true)
      @number_window.active = true
      @number_window.visible = true
      @status_window.visible = true
      @buy_window.reset
      @buy_window.refresh
      @buy_window.help_window = @help_window
    end
  end
  #--------------------------------------------------------------------------
  def update_number
    if Input.trigger?(Input::B)
      $game_system.se_play($data_system.cancel_se)
      @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
    if Input.trigger?(Input::C)
      $game_system.se_play($data_system.shop_se)
      @number_window.active = false
      @number_window.visible = false
      case @command_window.index
      when 0
        case @item
        when RPG::Item
          $game_party.gain_item(@item.id, @number_window.number)
          group = 0
        when RPG::Weapon
          $game_party.gain_weapon(@item.id, @number_window.number)
          group = 1
        when RPG::Armor
          $game_party.gain_armor(@item.id, @number_window.number)
          group = 2
        end
        for i in 0...$eco.shops[@id].items.size
          @item_id = i if $eco.shops[@id].items[i].item == @item.id and $eco.shops[@id].items[i].type == group
        end
        for i in 1..@number_window.number
          $eco.shops[@id].items[@item_id].stock -= 1
        end
        if $eco.shops[@id].items[@item_id].stock == 0 and $eco.shops[@id].items[@item_id].default == 0
          $eco.shops[@id].items.delete_at(@item_id)
          $eco.shops[@id].items.compact
        end
        $game_party.lose_gold(@number_window.total_price)
        @gold_window.refresh
        @buy_window.reset
        @buy_window.refresh
        @buy_window.help_window = @help_window
        @status_window.refresh
        @buy_window.active = true
        @buy_window.visible = true
      when 1
        case @item
        when RPG::Item
          $game_party.lose_item(@item.id, @number_window.number)
          group = 0
        when RPG::Weapon
          $game_party.lose_weapon(@item.id, @number_window.number)
          group = 1
        when RPG::Armor
          $game_party.lose_armor(@item.id, @number_window.number)
          group = 2
        end
        for i in 0...$eco.shops[@id].items.size
          @item_id = i if $eco.shops[@id].items[i].item == @item.id and $eco.shops[@id].items[i].type == group
        end
        for i in 0...@number_window.number
          if !@item_id
            $eco.add_item(@id, @item.id, group, 0, 0) 
            for i in 0...$eco.shops[@id].items.size
              @item_id = i if $eco.shops[@id].items[i].item == @item.id and $eco.shops[@id].items[i].type == group
            end
          end
          $eco.shops[@id].items[@item_id].stock += 1
        end
        $game_party.gain_gold(@number_window.total_price)
        @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
  #--------------------------------------------------------------------------
  def update_select
    if Input.trigger?(Input::B)
      $game_system.se_play($data_system.cancel_se)
      @select_window.visible = false
      @select_window.active = false
      @command_window.active = true
      return
    end
    if Input.trigger?(Input::C)
      itemstock = false
      weaponstock = false
      armorstock = false
      for i in $eco.shops[@id].items
        itemstock = true if i.type == 0
        weaponstock = true if i.type == 1
        armorstock = true if i.type == 2
      end
      case @select_window.index
      when 0
        $game_system.se_play($data_system.decision_se)
        @buy_window.category = 3
        @buy_window.reset
        @buy_window.refresh
        @buy_window.help_window = @help_window
        @select_window.visible = false
        @select_window.active = false
        @dummy_window.visible = false
        @buy_window.active = true
        @buy_window.visible = true
        @status_window.visible = true
      when 1
        if itemstock
          $game_system.se_play($data_system.decision_se)
          @buy_window.category = 0
          @buy_window.reset
          @buy_window.refresh
          @buy_window.help_window = @help_window
          @select_window.visible = false
          @select_window.active = false
          @dummy_window.visible = false
          @buy_window.active = true
          @buy_window.visible = true
          @status_window.visible = true
        else
          $game_system.se_play($data_system.buzzer_se)
        end
      when 2
        if weaponstock
          $game_system.se_play($data_system.decision_se)
          @buy_window.category = 1
          @buy_window.reset
          @buy_window.refresh
          @buy_window.help_window = @help_window
          @select_window.visible = false
          @select_window.active = false
          @dummy_window.visible = false
          @buy_window.active = true
          @buy_window.visible = true
          @status_window.visible = true
        else
          $game_system.se_play($data_system.buzzer_se)
        end
      when 3
        if armorstock
          $game_system.se_play($data_system.decision_se)
          @buy_window.category = 2
          @buy_window.reset
          @buy_window.refresh
          @buy_window.help_window = @help_window
          @select_window.visible = false
          @select_window.active = false
          @dummy_window.visible = false
          @buy_window.active = true
          @buy_window.visible = true
          @status_window.visible = true
        else
          $game_system.se_play($data_system.buzzer_se)
        end
      end
      return
    end
  end
end

class Eco_Window_ShopBuy < Window_Selectable
  attr_accessor :category
  #--------------------------------------------------------------------------
  def initialize(shop) 
    @id = shop
    @name = $eco.shops[@id].name
    @data = []
    @data_type = []
    @category = 3
    super(0, 128, 368, 352)
    refresh
    self.index = 0
  end
  #--------------------------------------------------------------------------
  def reset
    @data = []
    @data_type = []
    @ecoitem = nil
    self.index = 0
    return
  end
  #--------------------------------------------------------------------------
  def item
    data = @data[self.index]
    case @data_type[self.index]
    when 0
      item = $data_items[data]
    when 1
      item = $data_weapons[data]
    when 2
      item = $data_armors[data]
    end
    return item
  end
  #--------------------------------------------------------------------------
  def refresh
    if self.contents != nil
      self.contents.dispose
      self.contents = nil
    end
    @compitable = []
    for i in $eco.shops[@id].items
      @compitable.push(i.item) if i.type == @category or @category == 3
    end
    @item_max = @compitable.length
    self.contents = Bitmap.new(width - 32, row_max * 32 + 32)
    self.contents.font.name = $fontface
    self.contents.font.size = $fontsize
    for i in 0...$eco.shops[@id].items.size
      pie = $eco.shops[@id].items[i]
      if pie.type == @category or @category == 3
        draw_item(i)
        @data.push(pie.item)
        @data_type.push(pie.type)
      end
    end
  end
  #--------------------------------------------------------------------------
  def draw_item(index)
    item = $eco.shops[@id].items[index]
    number = $game_party.item_number(index)
    if item.type == 0
      @ecoitem = $data_items[item.item]
    elsif item.type == 1
      @ecoitem = $data_weapons[item.item]
    elsif item.type == 2
      @ecoitem = $data_armors[item.item]
    end
    self.contents.font.size = $fontsize
    if $eco.price(@id, item.item, item.type) <= $game_party.gold and number < 99 and item.stock != 0
      self.contents.font.color = normal_color
    else
      self.contents.font.color = disabled_color
    end
    x = 4
    y = @data.length * 32
    rect = Rect.new(x, y, self.width - 32, 32)
    self.contents.fill_rect(rect, Color.new(0, 0, 0, 0))
    bitmap = RPG::Cache.icon(@ecoitem.icon_name)
    opacity = self.contents.font.color == normal_color ? 255 : 128
    self.contents.blt(x, y + 4, bitmap, Rect.new(0, 0, 24, 24), opacity)
    self.contents.draw_text(x + 28, y, 212, 32, @ecoitem.name, 0)
    self.contents.draw_text(x + 240, y, 88, 32, $eco.price(@id, item.item, item.type).to_s, 2)
    ax = contents.text_size(@ecoitem.name).width + 36
    self.contents.font.size = 18
    self.contents.draw_text(ax, y - 6, 212, 32, "* " + item.stock.to_s, 0)
  end
  #--------------------------------------------------------------------------
  def update_help
    if self.item
      @help_window.set_text(self.item == nil ? @name : self.item.description)
    elsif self.item and !ES::SHOPNAME
      @help_window.set_text(self.item == nil ? "" : self.item.description)
    end
  end
end

class Eco_Window_ShopSell < Window_Selectable
  #--------------------------------------------------------------------------
  def initialize
    super(0, 128, 640, 352)
    @column_max = 2
    refresh
    self.index = 0
  end 
  #--------------------------------------------------------------------------
  def item
    return @data[self.index]
  end
  #--------------------------------------------------------------------------
  def refresh
    if self.contents != nil
      self.contents.dispose
      self.contents = nil
    end
    @data = []
    for i in 1...$data_items.size
      if $game_party.item_number(i) > 0
        @data.push($data_items[i])
      end
    end
    for i in 1...$data_weapons.size
      if $game_party.weapon_number(i) > 0
        @data.push($data_weapons[i])
      end
    end
    for i in 1...$data_armors.size
      if $game_party.armor_number(i) > 0
        @data.push($data_armors[i])
      end
    end
    @item_max = @data.size
    if @item_max > 0
      self.contents = Bitmap.new(width - 32, row_max * 32)
      self.contents.font.name = $fontface
      self.contents.font.size = $fontsize
      for i in 0...@item_max
        draw_item(i)
      end
    end
  end
  #--------------------------------------------------------------------------
  def draw_item(index)
    item = @data[index]
    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
    if item.price > 0
      self.contents.font.color = normal_color
    else
      self.contents.font.color = disabled_color
    end
    x = 4 + index % 2 * (288 + 32)
    y = index / 2 * 32
    rect = Rect.new(x, y, self.width / @column_max - 32, 32)
    self.contents.fill_rect(rect, Color.new(0, 0, 0, 0))
    bitmap = RPG::Cache.icon(item.icon_name)
    opacity = self.contents.font.color == normal_color ? 255 : 128
    self.contents.blt(x, y + 4, bitmap, Rect.new(0, 0, 24, 24), opacity)
    self.contents.draw_text(x + 28, y, 212, 32, item.name, 0)
    self.contents.draw_text(x + 240, y, 16, 32, ":", 1)
    self.contents.draw_text(x + 256, y, 24, 32, number.to_s, 2)
  end
  #--------------------------------------------------------------------------
  def update_help
    if self.item
      @help_window.set_text(self.item == nil ? @name : self.item.description)
    elsif self.item and !ES::SHOPNAME
      @help_window.set_text(self.item == nil ? "" : self.item.description)
    end
  end
end

class Window_Command
  def enable_item(index)
    draw_item(index, normal_color)
  end
end

class Eco_Window_ShopNumber < Window_Base
  attr_reader :number
  attr_reader :total_price
  #--------------------------------------------------------------------------
  def initialize
    super(0, 128, 368, 352)
    self.contents = Bitmap.new(width - 32, height - 32)
    self.contents.font.name = $fontface
    self.contents.font.size = $fontsize
    @item = nil
    @max = 1
    @number = 1
  end
  #--------------------------------------------------------------------------
  def set(shop, item, group, sell = false)
    @shop = shop
    @item = item
    @group = group
    @sell = sell
    @number = 1
    @item_id = nil
    for i in 0...$eco.shops[@shop].items.size
      if $eco.shops[@shop].items[i].item == @item.id and $eco.shops[@shop].items[i].type == @group
        @item_id = i
        break
      end
    end
    refresh
  end
  #--------------------------------------------------------------------------
  def refresh
    self.contents.clear
    draw_item_name(@item, 4, 96)
    self.contents.font.color = normal_color
    self.contents.draw_text(272, 96, 32, 32, "×")
    self.contents.draw_text(308, 96, 24, 32, @number.to_s, 2)
    self.cursor_rect.set(304, 96, 32, 32)
    domination = $data_system.words.gold
    cx = contents.text_size(domination).width
    @total_price = 0
    @fake_price = 0
    if @item_id
      @fake_stock = $eco.shops[@shop].items[@item_id].stock
    else
      @fake_stock = 0
    end
    if @sell
      case @group
      when 0
        @stock = $game_party.item_number(@item.id)
      when 1
        @stock = $game_party.weapon_number(@item.id)
      when 2
        @stock = $game_party.armor_number(@item.id)
      end
      for i in 0...@number
        @total_price += calprice(true)
        @fake_stock += 1
      end     
    else
      @stock = $eco.shops[@shop].items[@item_id].stock
      for i in 0...@stock
        @fake_price += calprice
        @fake_stock -= 1
        @mstock = $eco.shops[@shop].items[@item_id].stock - @fake_stock
        @mprice = @fake_price + calprice
        if @mprice >= $game_party.gold or @fake_stock <= 0
          @max = @mstock
          break 
        end
      end
      for i in 0...@number
        @fake_stock = $eco.shops[@shop].items[@item_id].stock - i
        @total_price += calprice
      end   
    end
    self.contents.font.color = normal_color
    self.contents.draw_text(4, 160, 328-cx-2, 32, @total_price.to_s, 2)
    self.contents.font.color = system_color
    self.contents.draw_text(332-cx, 160, cx, 32, domination, 2)
  end
  #--------------------------------------------------------------------------
  def update
    super
    if self.active
      if @sell
        @max = @stock
      end
      if Input.repeat?(Input::RIGHT) and @number < @max
        $game_system.se_play($data_system.cursor_se)
        @number += 1
        refresh
      end
      if Input.repeat?(Input::LEFT) and @number > 1
        $game_system.se_play($data_system.cursor_se)
        @number -= 1
        refresh
      end
      if Input.repeat?(Input::UP) and @number < @max
        $game_system.se_play($data_system.cursor_se)
        @number = [@number + 10, @max].min
        refresh
      end
      if Input.repeat?(Input::DOWN) and @number > 1
        $game_system.se_play($data_system.cursor_se)
        @number = [@number - 10, 1].max
        refresh
      end
    end
  end
  #--------------------------------------------------------------------------
  def calprice(sell = false)
    @baseprice = @item.price.to_f
    if @item_id
      if $eco.shops[@shop].items[@item_id].default != 0
        range = $eco.shops[@shop].items[@item_id].default.to_f / @fake_stock.to_f
        none = false
      else
        none = true
      end
    else
      none = true
    end
    if none
      if sell
        range = 1.30
        for i in 0...@fake_stock
          range -= 0.05 if range >= 0.80
        end
      else
        range = 2.16
        for i in 0...@fake_stock
          range -= 0.16 if range >= 0.70
        end
      end
    end
    range = 1.25 if range.nan?
    if sell == true
      @base = @baseprice / 2
      if range == 1
        @newprice = @base
      elsif range > 1
        @newprice = @base * (range * range)     
      else
        @newprice = @base * range
      end
      @newprice = @baseprice * 3 if @newprice > @baseprice * 3
      @newprice = @baseprice / 3 if @newprice < @baseprice / 3     
    else
      @newprice = @baseprice * range
      @newprice = @baseprice * 2 if @newprice > @baseprice * 2
      @newprice = @baseprice / 2 if @newprice < @baseprice / 2
    end
    @newprice = @newprice.round
    return @newprice
  end
end
# EoF, Last edit 09/11/2005 21:57 GMT, 1070 lines total.


**이 스크립트는 일반상점과 함께 사용가능합니다.  사용법은 이벤트 편집->스크립트에서:
상점생성: $eco.add_shop("name"(ID또는 상점이름), "trade_type"(buy/sell/both))
판매품목 추가: $eco.add_item(shop(ID또는 이름), item(아이템ID), type(item(0)/ weapon(1)/ armor(2)), amount(판매할 수량), time_per_unit(재고가 차는 시간간격))
상점호출: $scene = Eco_Scene_Shop.new(ID또는 이름)


**첨부된 데모를 참조하세요.