设为首页收藏本站同能贴吧 切换语言 繁体中文
开启辅助访问 切换到窄版
扫描二维码关注官方公众号
返回列表
+ 发新帖
查看: 123|回复: 0

[转载发布] Database Extender

[复制链接]
累计送礼:
0 个
累计收礼:
1 个
  • TA的每日心情
    开心
    2026-7-12 04:10
  • 签到天数: 209 天

    连续签到: 2 天

    [LV.7]常住居民III

    9071

    主题

    864

    回帖

    6万

    积分

    管理员

    Rank: 9Rank: 9Rank: 9

    VIP
    7
    卡币
    58883
    OK点
    16
    推广点
    0
    同能卷
    50
    积分
    68848

    灌水之王

    发表于 2026-7-23 19:02:30 | 显示全部楼层 |阅读模式
    Database Extender

    Thanks Hiino for the translation  


    I think that the RPG Maker database is a bit of a pain since we cannot extend it. Hence, I am obligated to stay in the quite restrictive base system, and, in order to obtain cooler (and more specific) things I have to abuse of the database's commentary/note fields (and why not complete with the Typed Entities script, which isn't adapted to this kind of things... IN MY OPINION!)

    So I plagiarized Avygeil who had already been plagiarized by Grim and recoded a database system for RM.

     

    Concept

    This system is based on the same idea as the one Grim used in his "Expressive Database", except it's a bit better (and more cleverly) coded. So firstly we are going to create tables in a blank script on top of Main. To achieve this, simply write:

     

    class Swords < Database::Table  # Here we will define our table's fieldsendTo add fields that characterize our table, we have to set their type and their name.

    The script accepts the following types: 


    • :string   - Represents text data
    • :integer   - Represents an integer number
    • :float   - Represents a floating point number 
    • :boolean   - Represents either true or false (a switch)

    • olymorphic   - Represents any RM data type

    Here is an example with swords and Pokemon:

     

                    Code:       
    1. class Swords < Database::Table  integer :id  string  :name  string  :description   float   :cost  integer :powerendclass Pokemon < Database::Table  integer :id  string  :name  string  :description  string  :type  integer :powerend
    复制代码


    The goal is to describe every attribute of our tables. Of course, these exaples are quite naive and not finished.

    How to fill our database

    There are two ways of filling our database.

    The first one is the most economic: after having defined our fields, we can use the "insert" command and pass it arguments. If said arguments aren't the right type the script will try to convert them, else it will set them a default value according to their type. Here is an example:

     

    class Swords < Database::Table  # Design of the table  integer :id  string  :name  string  :description   float   :cost  integer
    ower  # Filling   insert 0, "Excalibur", "A rare sword", 150.50, 120  insert 1, "Durendal", "A very rare sword", 200.20, 200  insert 2, "Dard", "Bilbon's, then Frodon's sword", 30.0, 50endclass Pokemon < Database::Table  # Design of the table  integer :id  string  :name  string  :description  string  :type  integer
    ower  # Filling  insert 0, "Pikachu", "Ugly green mouse", "Electric", 10  insert 1, "Pichu", "Same as above", "Electric", 5  insert 2, "Doraemon", "thing", "Fire", 100  insert 3, "Sangoku", "Legendary Pokemon", "Rare", 1000 endAlso, it is possible to instantiate objects this way:

                    Code:       
    1. Pokemon.new(id: 4, name: "Mew", description: "Blue monkey", type: "Plant", power: 999)Pokemon.new(id: 5, name: "Magicalichigo", description: "Looks like an Evoli", type: "Psy", power: 1)
    复制代码

    Personally, I prefer this way of doing, which allows me to separate my "design" and my filling. But it's possible to mix both techniques.

    Access a table

    We just have to write
    atabase.tables[:Table_Name] or Database.Table_Name


    For example: Database.Pokemon or Database.tables[
    okemon]


    Then Database.Pokemon[0] will return the first record (Pikachu), but since the fields are stored inside an array, it is possible to use all the methods concerning arrays. However this part only addresses scripters, kind of like this whole script actually  


     

    Process the initial RPG Maker database

    Since this script is modern and cool, it also allows for handling the RPG Maker database with the same primitives.

    For example, to access the Actors table of the database, we will write: Database.VXACE_Actors, which returns the array of all the database's actors.

    The accessible tables:



    • VXACE_Actors
    • VXACE_Classes
    • VXACE_Skills
    • VXACE_Items
    • VXACE_Weapons
    • VXACE_Armors
    • VXACE_Enemies
    • VXACE_States
    • VXACE_Animations
    • VXACE_Tilesets
    • VXACE_CommonEvents
    • VXACE_MapInfos
    This append allows us to manipulate the initial database in a transparent manner with the script.

    Associating with the Event Extender

    If the Event Extender is already appended to your project, you have to place this script below it, so that its database overrides the Event Extender's.

    The Design/Filling works the ame way as detailed above.

    To access the database, it works as usual or as documented in the Event Extender (for example T[
    okemon] or T[:VXACE_Actors]).


    Thanks to Hiino for his proofreading and translation!

     

    Code

    Spoiler# Extend Database ~ Der Botaniker (Nuki)# http://www.biloucorp.com# Idea : Avygeil, Grim # Thanks to Hiino, Zangther (sexual motivation)# And special thanks to larabdubled#==============================================================================# ** Object#------------------------------------------------------------------------------#  Generic behaviour#==============================================================================class Object  #--------------------------------------------------------------------------  # * Bool casting  #--------------------------------------------------------------------------  if defined?(Command)    remove_const
    Database)    def to_bool; (self != nil || self != false) end   end  #--------------------------------------------------------------------------  # * Polymorphic casting  #--------------------------------------------------------------------------  def nothing; self; end  #--------------------------------------------------------------------------  # * Get Instance values  #--------------------------------------------------------------------------  def instance_values    instances = Array.new    instance_variables.each do |i|      instances << instance_variable_get(i)    end    instances  endend#==============================================================================# ** Database#------------------------------------------------------------------------------# Representation of an Abstract Database#==============================================================================module Database    #==============================================================================  # ** Types  #------------------------------------------------------------------------------  # Implements the Type System  #==============================================================================    RPGDatas = [    "Actors",     "Classes",    "Skills",    "Items",    "Weapons",    "Armors",    "Enemies",    "States",    "Animations",    "Tilesets",    "CommonEvents",    "MapInfos"  ]    module Type    #--------------------------------------------------------------------------    # * Type Enum    #--------------------------------------------------------------------------    Types = {      string:       [:to_s, ""],      integer:      [:to_i, 0],      float:        [:to_f, 0.0],      boolean:      [:to_bool, true],      polymorphic:  [:nothing, ""]    }    #--------------------------------------------------------------------------    # * String representation    #--------------------------------------------------------------------------    def string(field_name)      handle_field
    string, field_name.to_sym)    end    alias :text :string    #--------------------------------------------------------------------------    # * Integer representation    #--------------------------------------------------------------------------    def integer(field_name)      handle_field
    integer, field_name.to_sym)    end    alias :int :integer    #--------------------------------------------------------------------------    # * Floating point number representation    #--------------------------------------------------------------------------    def float(field_name)      handle_field
    float, field_name.to_sym)    end    #--------------------------------------------------------------------------    # * Boolean representation    #--------------------------------------------------------------------------    def boolean(field_name)      handle_field
    boolean, field_name.to_sym)    end    alias :bool :boolean    #--------------------------------------------------------------------------    # * Polymorphic type representation    #--------------------------------------------------------------------------    def polymorphic(field_name)      handle_field
    polymorphic, field_name.to_sym)    end    alias :free
    olymorphic    #--------------------------------------------------------------------------    # * Type Coercion    #--------------------------------------------------------------------------    def self.coercion(className)      return :integer if className == Fixnum      return :string if className == String      return :float if className == Float      return :boolean if className == TrueClass || className == FalseClass      
    olymorphic    end  end    #==============================================================================  # ** Table  #------------------------------------------------------------------------------  # Representation of an Abstract Table  #==============================================================================      class Table    #--------------------------------------------------------------------------    # * Appends Type handler    #--------------------------------------------------------------------------    extend Type    Types = Type::Types    #--------------------------------------------------------------------------    # * Singleton of Table    #--------------------------------------------------------------------------    class << self      #--------------------------------------------------------------------------      # * Public instance variables      #--------------------------------------------------------------------------      attr_accessor :fields      attr_accessor :classname      #--------------------------------------------------------------------------      # * Field handling      #--------------------------------------------------------------------------      def handle_field(type, name)        @classname ||= self.to_s.to_sym        @fields ||= Hash.new        @fields[name] = type        instance_variable_set("@#{name}".to_sym, Types[type][1])        send
    attr_accessor, name)      end      #--------------------------------------------------------------------------      # * Inline insertion      #--------------------------------------------------------------------------      def insert(*args)        keys = @fields.keys        hash = Hash[keys.zip(args)]        self.new(hash)      end    end    #--------------------------------------------------------------------------    # * Object initialization    #--------------------------------------------------------------------------    def initialize(hash)      hash.each do |key, value|        type = self.class.fields[key]        insertion = Types[type][1]        insertion = value.send(Types[type][0]) if value.respond_to?(Types[type][0])        instance_variable_set("@#{key}".to_sym, insertion)      end      Database.tables[self.class.classname] ||= Array.new      Database.tables[self.class.classname] << self    end  end  #--------------------------------------------------------------------------  # * Singleton of Database  #--------------------------------------------------------------------------  class << self    #--------------------------------------------------------------------------    # * Public instance variables    #--------------------------------------------------------------------------    attr_accessor :tables    #--------------------------------------------------------------------------    # * API for tables    #--------------------------------------------------------------------------    Database.tables = Hash.new    #--------------------------------------------------------------------------    # * Method Missing    #--------------------------------------------------------------------------    def method_missing(method, *args)      tables[method] || (raise(NoMethodError))    end  endend#==============================================================================# ** Junction with the Event Extender 4#==============================================================================if defined?(Command)  #==============================================================================  # ** T  #------------------------------------------------------------------------------  #  Database handling API  #==============================================================================    module T    #--------------------------------------------------------------------------    # * Get a table    #--------------------------------------------------------------------------    def [](name); Database.tables[name.to_sym]; end  endend#==============================================================================# ** RPG::Module Mapping#------------------------------------------------------------------------------#  Initial Database Mapping#==============================================================================Database::RPGDatas.each do |data|  rpgStruct = load_data("Data/#{data}.rvdata2")  instance = rpgStruct.find{|i| !i.nil?}  instance = instance[1] if instance.is_a?(Array)  Object.const_set(    "VXACE_#{data}".to_sym,     Class.new(Database::Table) do       self.classname = "VXACE_#{data}".to_sym      instance.instance_variables.each do |attr|        classData = instance.send
    instance_variable_get, attr).class        type = Database::Type.coercion(classData)        self.send(type, attr.to_s[1..-1].to_sym)      end      rpgStruct.each do |rpgData|        rpgData = rpgData[1] if rpgData.is_a?(Hash)        self.insert(*rpgData.instance_values)      end    end  )end




     

    Permalink

    If I update the script, it will usually be on this page: https://github.com/Funkywork/Scripts-rm/blob/master/VXAce/Extend-Database.rb

    And the official Page : http://www.biloucorp.com/index.php?page=article&id_article=4


    本贴来自国际rpgmaker官方论坛作者:Der Botaniker处,因国际论坛即将永久关站,为了存档多年珍贵资料,署名转载到本论坛存档,由于官方帖子为英文原帖,需要中文翻译请点击论坛顶部切换语言为中文就可以将帖子翻译成中文浏览,方便大家随时查看,原文地址:https://forums.rpgmakerweb.com/threads/database-extender.10693/

    本帖子中包含更多资源

    您需要 登录 才可以下载或查看,没有账号?立即注册

    x
    天天去同能,天天有童年!
    回复 送礼论坛版权

    使用道具 举报

    文明发言,和谐互动
    文明发言,和谐互动
    高级模式
    您需要登录后才可以回帖 登录 | 立即注册

    本版积分规则

    简体中文
    繁體中文
    English(英语)
    日本語(日语)
    Deutsch(德语)
    Русский язык(俄语)
    بالعربية(阿拉伯语)
    Türkçe(土耳其语)
    Português(葡萄牙语)
    ภาษาไทย(泰国语)
    한어(朝鲜语/韩语)
    Français(法语)
    关闭

    幸运抽奖

    社区每日抽奖来袭,快来试试你是欧皇还是非酋~

    立即查看

    聊天机器人
    Loading...

    QQ|Archiver|手机版|小黑屋|同能RPG制作大师 ( 沪ICP备12027754号-3 )

    GMT+8, 2026-8-17 14:17 , Processed in 0.144025 second(s), 53 queries .

    Powered by Discuz! X3.4

    Copyright © 2001-2020, Tencent Cloud.

    快速回复 返回顶部 返回列表