# @taroxd metadata 1.0
# @require taroxd_core
# @require global
# @id route
# @display 多路线系统
# @help
# 游戏中的变量和开关是所有路线共有的。
# 该脚本可以进行路线的切换。
# 游戏开始时,路线 id 为 0。
#
# 进入空路线时,队伍无成员,不持有任何物品。玩家的位置不变。
# 建议用以下方式来初始化一条路线:
# 淡出画面 - route.id = id - 初始化路线 - 淡入画面
#
# -- 用法 -- 在事件脚本中输入 --
# route.id:获取当前路线的 id。
# route.id = id:
# 切换到第 id 号路线,无淡入淡出效果。
# set_route(id):
# 切换到第 id 号路线,有淡入淡出效果。
# route << id:将第 id 号路线合并入当前路线,并清除第 id 号路线。
# route.clear(id):清除第 id 号路线。
# 路线类,保存了路线 id 和数据。该类的实例会存入存档。
class Taroxd::Route
# 数据
class Contents
attr_reader :party, :map_id, :x, :y, :d
def initialize
@party = $game_party
@map_id = $game_map.map_id
@x = $game_player.x
@y = $game_player.y
@d = $game_player.direction
end
def restore
$game_party = @party
$game_player.reserve_transfer(@map_id, @x, @y, @d)
end
end
def self.current
Taroxd::Global[:route] ||= new
end
attr_reader :id
def initialize
@id = 0
@data = [] # Contents 实例的数组
end
def id=(id)
return if @id == id
@data[@id] = Contents.new
@id = id
contents = @data[id]
contents ? contents.restore : init_route
on_change
end
# 合并路线
def <<(id)
if @id != id && @data[id]
$game_party.merge_party(@data[id].party)
clear(id)
on_change
end
self
end
def clear(id = nil)
id ? @data[id] = nil : @data.clear
end
def on_change
$game_player.refresh
$game_map.need_refresh = true
end
private
# 进入一条新路线时执行的内容
def init_route
$game_party = Game_Party.new
end
end
class Game_Interpreter
def route
Taroxd::Route.current
end
# 设置路线并淡入淡出
def set_route(id)
return if $game_party.in_battle
command_221 # 淡出画面
route.id = id
Fiber.yield while $game_player.transfer?
command_222 # 淡入画面
end
end
class Game_Party < Game_Unit
# 合并金钱、角色、物品
def merge_party(other)
gold, actors, items, weapons, armors = other.merge_contents
gain_gold(gold)
@actors |= actors
merge_item @items, items, $data_items
merge_item @weapons, weapons, $data_weapons
merge_item @armors, armors, $data_armors
end
protected
def merge_contents
[@gold, @actors, @items, @weapons, @armors]
end
private
def merge_item(to, from, database)
to.merge!(from) do |id, v1, v2|
[v1 + v2, max_item_number(database[id])].min
end
end
end
多路线系统
动态值槽
# @taroxd metadata 1.0
# @display 动态值槽
# @require taroxd_core
# @id roll_gauge
# @help 给值槽增加动态的滚动效果
class Taroxd::Transition
# value: 当前值。changing: 当前是否正在变化
attr_reader :value, :changing
# get_target.call 获取到变化的数据。可以使用 block 代替 get_target。
def initialize(duration, get_target = nil, &block)
@duration = duration
@get_target = get_target || block
@value = @target = @get_target.call
@d = 0
end
# 更新值槽的值。如果值槽发生变化,返回 true。
def update
@target = @get_target.call
@changing = @value != @target
update_transition if @changing
@changing
end
private
def update_transition
@d = @duration if @d.zero?
@d -= 1
@value = if @d.zero?
@target
else
(@value * @d + @target).fdiv(@d + 1)
end
end
end
# include 之后,可用 @gauge_transitions[actor][:hp] 等
# 获取 Taroxd::Transition 的实例。
module Taroxd::RollGauge
Transition = Taroxd::Transition
def initialize(*)
@gauge_transitions = make_gauge_transitions
@gauge_roll_count = 0
super
end
def update
super
if (@gauge_roll_count += 1) >= gauge_roll_interval
roll_all_gauge if update_gauge_transitions && visible
@gauge_roll_count = 0
end
end
def draw_actor_hp(actor, x, y, width = 124)
hp = @gauge_transitions[actor][:hp].value
rate = hp.fdiv(actor.mhp)
draw_gauge(x, y, width, rate, hp_gauge_color1, hp_gauge_color2)
change_color(system_color)
draw_text(x, y, 30, line_height, Vocab::hp_a)
draw_current_and_max_values(x, y, width, hp.to_i, actor.mhp,
hp_color(actor), normal_color)
end
def draw_actor_mp(actor, x, y, width = 124)
mp = @gauge_transitions[actor][:mp].value
mmp = actor.mmp
rate = mmp.zero? ? 0 : mp.fdiv(actor.mmp)
draw_gauge(x, y, width, rate, mp_gauge_color1, mp_gauge_color2)
change_color(system_color)
draw_text(x, y, 30, line_height, Vocab::mp_a)
draw_current_and_max_values(x, y, width, mp.to_i, actor.mmp,
mp_color(actor), normal_color)
end
def draw_actor_tp(actor, x, y, width = 124)
tp = @gauge_transitions[actor][:tp].value
rate = tp.fdiv(actor.max_tp)
draw_gauge(x, y, width, rate, tp_gauge_color1, tp_gauge_color2)
change_color(system_color)
draw_text(x, y, 30, line_height, Vocab::tp_a)
change_color(tp_color(actor))
draw_text(x + width - 42, y, 42, line_height, tp.to_i, 2)
end
private
# 获取 make_gauge_transitions 生成的对象
attr_reader :gauge_transitions
# 值槽滚动所需的帧数
def gauge_roll_frame
30
end
# 每隔多少帧更新一次值槽
def gauge_roll_interval
1
end
# 生成值槽变化的数据。可在子类重定义。
# 默认的定义中,可以通过 gauge_transitions[actor][:hp] 等方式获取数据。
def make_gauge_transitions
Hash.new { |hash, actor|
hash[actor] = Hash.new do |h, k|
h[k] = Transition.new(gauge_roll_times, actor.method(k))
end
}.compare_by_identity
end
# 更新渐变的值。
# 返回真值则触发一次刷新。
# 每 gauge_roll_interval 帧调用一次。
def update_gauge_transitions
need_roll = false
gauge_transitions.each_value do |hash|
hash.each_value do |t|
need_roll = true if t.update
end
end
need_roll
end
# 值槽滚动所需的次数。
def gauge_roll_times
gauge_roll_frame / gauge_roll_interval
end
# 滚动所有值槽。可在子类重定义。
def roll_all_gauge
refresh
end
end
class Window_BattleStatus
include Taroxd::RollGauge
end
class Window_MenuStatus < Window_Selectable
include Taroxd::RollGauge
def roll_all_gauge
item_max.times do |i|
actor = $game_party.members[i]
rect = item_rect(i)
rect.x += 108
rect.y += line_height / 2
contents.clear_rect(rect)
draw_actor_simple_status(actor, rect.x, rect.y)
end
end
end
修复 bug
# @taroxd metadata 1.0
# @display 修复 bug
# @desciption 修复默认系统的一些 bug。详见下方的注释
# @id rgss_bugfix
module Taroxd
module BugFix
# Plane#visible 永远返回 true 的 bug。需要主动 include。
module PlaneVisible
def initialize(_)
super
@__visible = true
end
def visible
@__visible
end
def visible=(v)
@__visible = v
super
end
end
end
end
class Game_BattlerBase
# max_tp 不为 100 时,以下两方法返回值错误的 bug
def tp_rate
@tp.fdiv(max_tp)
end
def regenerate_tp
self.tp += max_tp * trg
end
end
class Game_Interpreter
# 震动画面后等待时间不正确的 bug
def command_225
screen.start_shake(@params[0], @params[1], @params[2])
wait(@params[2]) if @params[3]
end
end