Project1
标题:
关于挨打动作制作的问题
[打印本页]
作者:
546936326
时间:
2014-2-11 12:56
标题:
关于挨打动作制作的问题
本帖最后由 546936326 于 2014-2-15 13:18 编辑
在战斗中角色挨打时改变角色战斗图从而实现挨打动作。。在柳大的教程里是将这个判定放在scene-battle4里的显示挨打方动画的地方,可是这样一来当攻击动画比较长时就会出现还没打中时就换成了挨打动作的bug。。请问如何制作成当挨打方开始闪烁时才变成挨打动作。。?
作者:
天地有正气
时间:
2014-2-11 19:46
尝试一下在播放时加个case?
作者:
546936326
时间:
2014-2-13 19:07
天地有正气 发表于 2014-2-11 19:46
尝试一下在播放时加个case?
然后怎么判断闪光呢………………orz
作者:
落雪无温
时间:
2014-2-14 17:16
(。・`ω′・)话说LZ看的是哪个教程?我最近也想学这个功能,
(。・`ω′・)我倒是不需要太细节,开始播放动画就改挨打战斗图就行了。
(。・`ω′・)倒是没搜到类似教程呢……
(。・`ω′・)因为我不是那么需要细节所以全动画脚本需要的素材也太麻烦了……只要单帧的挨打战斗图呢……
作者:
546936326
时间:
2014-2-14 19:52
#
#修改战斗界面的教程。
#
前言:
本教学难度并不高,但是比较繁琐。看完之后,你会完全理解战斗的动作系统怎么去制作,而且改造于你手,无冲突无卡机。请保持耐心并跟着制作。
--------------------------------------------------------------------------------
首先先看这几个教学:
1、shownews.asp?id=131,45度战斗 + 横版战斗制作方法,这个是不带特殊素材效果的。如果你的素材紧缺,不用看了,看到这个教学基本就OK了。
对于原创度很高的游戏,可能基本到这一步就差不多了。此录像为本教学的基础,诸如设置动画、坐标等内容在本教学不再赘述。
2、shownews.asp?id=258,这个是添加了待机动画。改用行走图而已,bug很少。用于三国凡人传等游戏的制作方法,可以参考。
3、shownews.asp?id=201 + shownews.asp?id=210,超级横版战斗。所有下面有的效果里面都有,但是使用起来比较困难。
--------------------------------------------------------------------------------
好了,既然以上几个教学不能满足你,那么我来告诉你怎么打造自己的战斗吧。很多人自己会做,但是不会有我讲得这么清楚,所以我再讲一遍,希望不会再讲第N遍了哦!
0、一个变量的公开:
class Game_Battler中,attr_reader :battler_name改为attr_accessor :battler_name
否则这个变量不能随意修改。
1、待机动画
原理:常规战斗的情况下,有两种让图像动起来的方法。一种是使用循环动画,另一种是不断更改角色的战斗图。
怎样给角色添加循环动画呢?你可以设置一个状态名为“正常”,然后在这个状态附带循环动画里面制作上角色的待机动画。如果需要,可以附带这个脚本:shownews.asp?id=381,会防止挨打动画丢失。这种方法的特点是可以制作复杂的待机动作,缺点是占用了循环动画,导致一些状态动画不能显示了。
另一种方法是更改角色战斗图,这个方法没有副作用,但是需要一些脚本知识。为了方便,我们将待机动画的4个动作放在一张战斗图里面,横着排列。(你如果脚本知识牢靠,可以不使用本教学的方法,本教学仅做统一范例而已)
这张图片的名字是li.png,将作为角色的战斗图。
角色战斗图的刷新是在Sprite_Battler里面。所以,现在修改一下这个脚本。
初始化的部分:
def initialize(viewport, battler = nil)
super(viewport)
[url=home.php?mod=space&uid=133701]@battler[/url] = battler
@battler_visible = false
end
添加两个属性:
def initialize(viewport, battler = nil)
super(viewport)
@battler = battler
@battler_visible = false
#★★★★★★★★★★★★
@nx = 0
@xbit = 0
#★★★★★★★★★★★★
end
@nx表示当前的帧数,@xbit表示当前的图像。刚开始的时候都是0值。
刷新的部分def update,找到这段
# 文件名和色相与当前情况有差异的情况下
if @battler.battler_name != @battler_name or
@battler.battler_hue != @battler_hue
# 获取、设置位图
@battler_name = @battler.battler_name
@battler_hue = @battler.battler_hue
self.bitmap = RPG::Cache.battler(@battler_name, @battler_hue)
@width = bitmap.width
[url=home.php?mod=space&uid=291977]@height[/url] = bitmap.height
self.ox = @width / 2
self.oy = @height
# 如果是战斗不能或者是隐藏状态就把透明度设置成 0
if @battler.dead? or @battler.hidden
self.opacity = 0
end
end
这段表示如果战斗中角色战斗图更换则重新换图片。在此下面添加一个刷新效果:
# 文件名和色相与当前情况有差异的情况下
if @battler.battler_name != @battler_name or
@battler.battler_hue != @battler_hue
# 获取、设置位图
@battler_name = @battler.battler_name
@battler_hue = @battler.battler_hue
self.bitmap = RPG::Cache.battler(@battler_name, @battler_hue)
@width = bitmap.width
@height = bitmap.height
self.ox = @width / 2
self.oy = @height
# 如果是战斗不能或者是隐藏状态就把透明度设置成 0
if @battler.dead? or @battler.hidden
self.opacity = 0
end
end
if @battler.is_a?(Game_Actor)
@nx += 1
@nx %= 40 #每帧+1,40帧一个循环
@xbit = @nx / 10 * self.bitmap.width/4 #获得当前的图像坐标
self.src_rect.set(@xbit, 0, self.bitmap.width/4, self.bitmap.height) #设置当前战斗图的图像
end
这段就是表示,如果这个battler是角色的时候,每隔10帧角色的动画更新一次。好了。你把上面的图像和脚本放到自己的游戏中,就已经是具有待机动画的了。坐标可能不是很好,自己调一下即可。
--------------------------------------------------------------------------------
2、挨打,防御,受伤(hp小于一半)的动画
现在我们另有这么几张图片:
这张图片的名字是li★2.png
这张图片的名字是li★3.png
这张图片的名字是li★4.png
这张图片的名字是li★5.png
那么,我们怎么制作角色的防御动作和挨打动作呢?(注:我为了偷懒,上面的4张图其实上几乎没有动态,你换为自己的素材即可)
首先我们先找到脚本中控制挨打和显示伤害的部分。如果脚本比较熟你应该知道是在Scene_Battle 4中(齐时战斗的设置中讲到过了):
#--------------------------------------------------------------------------
# ● 刷新画面 (主回合步骤 4 : 对像方动画)
#--------------------------------------------------------------------------
def update_phase4_step4
# 对像方动画
for target in @target_battlers
target.animation_id = @animation2_id
target.animation_hit = (target.damage != "Miss")
end
# 限制动画长度、最低 8 帧
@wait_count = 8
# 移至步骤 5
@phase4_step = 5
end
#--------------------------------------------------------------------------
# ● 刷新画面 (主回合步骤 5 : 显示伤害)
#--------------------------------------------------------------------------
def update_phase4_step5
# 隐藏帮助窗口
@help_window.visible = false
# 刷新状态窗口
@status_window.refresh
# 显示伤害
for target in @target_battlers
if target.damage != nil
target.damage_pop = true
end
end
# 移至步骤 6
@phase4_step = 6
end
下面修改一下这段。我们在显示“对象方动画(update_phase4_step4)”的地方将角色的战斗图改为“防御”或者“挨打”的样子,“显示伤害(update_phase4_step5)”的时候再改回来。
修改如下:
#--------------------------------------------------------------------------
# ● 刷新画面 (主回合步骤 4 : 对像方动画) ★
#--------------------------------------------------------------------------
def update_phase4_step4
# 对像方动画
for target in @target_battlers
target.animation_id = @animation2_id
target.animation_hit = (target.damage != "Miss")
if target.is_a?(Game_Actor)
target.battler_name = target.battler_name.split(/★/)[0]
if (target.current_action.kind == 0 and target.current_action.basic == 1) or target.damage == "Miss" or target.damage.to_i <= 0
target.battler_name = target.battler_name + "★3"
else
target.battler_name = target.battler_name + "★4"
end
end
end
# 限制动画长度、最低 8 帧
@wait_count = 8
# 移至步骤 5
@phase4_step = 5
end
#--------------------------------------------------------------------------
# ● 刷新画面 (主回合步骤 5 : 显示伤害)
#--------------------------------------------------------------------------
def update_phase4_step5
# 隐藏帮助窗口
@help_window.visible = false
# 刷新状态窗口
@status_window.refresh
# 显示伤害
for target in @target_battlers
if target.damage != nil
target.damage_pop = true
end
if target.is_a?(Game_Actor)
target.battler_name = target.battler_name.split(/★/)[0]
if target.hp < target.maxhp/2
target.battler_name = target.battler_name + "★5"
end
end
end
# 移至步骤 6
@phase4_step = 6
end
我来解释一下红字的部分。
if target.is_a?(Game_Actor) #如果挨打的是角色的时候
target.battler_name = target.battler_name.split(/★/)[0] #先把角色的战斗图文件名改为默认的战斗图文件名(也就是忽略现在文件名中★后面的部分),防止出一些意外。也就是说,如果现在处于“受伤”的情况,则本来数据库设置战斗图为“li”,此刻却是“li★5”
if (target.current_action.kind == 0 and target.current_action.basic == 1) or target.damage <= 0 #如果角色的行动是“防御”的时候或者伤害<0的时候(当然,这个防御你可以自己修改功能,比如“防御回气”或者“召唤宠物”等。那你就自己修改一下触发条件即可)
target.battler_name = target.battler_name + "★3" #挨打者的文件名改为原名+★3。比如原来文件名是“li”,现在就变成了“li★3”
else #除此以外,也就是没“防御”的时候
target.battler_name = target.battler_name + "★4" #挨打者文件名改为原名+★4。原名“li”,现在变成了“li★4”
end
下面再来看后面显示伤害的时候。有了上面的基础,应该很简单了吧:
if target.is_a?(Game_Actor) #当是角色的时候
target.battler_name = target.battler_name.split(/★/)[0] #文件名还原
if target.hp < target.maxhp/2 #如果角色生命小于一半
target.battler_name = target.battler_name + "★5" #把战斗图改为受伤图
end
end
这样角色就有防御和挨打的图了。不过我并不推荐这种方法制作受伤动画,因为如果你用了★5的受伤动画,则你需要在Game_Battler 3的def item_effect中增加战斗图的更改。否则角色在战场被打个半死,在地图上吃药补满血后,回到战场还是使用的受伤战斗图。此外还需要在公共事件的增减HP的地方增加战斗图更改的脚本——总之,自己改吧。原理掌握了就什么都不怕了。
--------------------------------------------------------------------------------
3、死亡图
死亡图相对麻烦一点。注意到Sprite_Battler中如下几个地方:
# 如果是战斗不能或者是隐藏状态就把透明度设置成 0
if @battler.dead? or @battler.hidden
self.opacity = 0
end
以及:
if @battler.damage == nil and @battler.dead?
if @battler.is_a?(Game_Enemy)
$game_system.se_play($data_system.enemy_collapse_se)
else
$game_system.se_play($data_system.actor_collapse_se)
end
collapse
@battler_visible = false
end
以及:
if not @battler.hidden and not @battler.dead? and
(@battler.damage == nil or @battler.damage_pop)
appear
@battler_visible = true
end
修改一下吧:
# 如果是战斗不能或者是隐藏状态就把透明度设置成 0
if @battler.is_a?(Game_Enemy)
if @battler.dead? or @battler.hidden
self.opacity = 0
end
end
这个就是改为只有敌人死的时候才让敌人消失。
if @battler.damage == nil and @battler.dead?
if @battler.is_a?(Game_Enemy)
$game_system.se_play($data_system.enemy_collapse_se)
collapse
else
$game_system.se_play($data_system.actor_collapse_se)
@battler.battler_name = @battler.battler_name.split(/★/)[0]
@battler.battler_name = @battler.battler_name + "★2"
end
@battler_visible = false
end
当我方死亡的时候修改战斗图。
unless @battler_visible
# 出现
if not @battler.hidden and not @battler.dead? and
(@battler.damage == nil or @battler.damage_pop)
if @battler.is_a?(Game_Enemy)
appear
else
@battler.battler_name = @battler.battler_name.split(/★/)[0]
end
@battler_visible = true
end
end
当我方复活的时候修改战斗图
行了。完成了~~
--------------------------------------------------------------------------------
Final、调整位置
把默认没有写出来的脚本修改一下(这个脚本在RMXP的帮助中搜索damage可以获得):
module RPG
class Sprite < ::Sprite
def damage(value, critical)
dispose_damage
if value.is_a?(Numeric)
damage_string = value.abs.to_s
else
damage_string = value.to_s
end
bitmap = Bitmap.new(160, 48)
bitmap.font.name = "Arial Black"
bitmap.font.size = 32
bitmap.font.color.set(0, 0, 0)
bitmap.draw_text(-1, 12-1, 160, 36, damage_string, 1)
bitmap.draw_text(+1, 12-1, 160, 36, damage_string, 1)
bitmap.draw_text(-1, 12+1, 160, 36, damage_string, 1)
bitmap.draw_text(+1, 12+1, 160, 36, damage_string, 1)
if value.is_a?(Numeric) and value < 0
bitmap.font.color.set(176, 255, 144)
else
bitmap.font.color.set(255, 255, 255)
end
bitmap.draw_text(0, 12, 160, 36, damage_string, 1)
if critical
bitmap.font.size = 20
bitmap.font.color.set(0, 0, 0)
bitmap.draw_text(-1, -1, 160, 20, "CRITICAL", 1)
bitmap.draw_text(+1, -1, 160, 20, "CRITICAL", 1)
bitmap.draw_text(-1, +1, 160, 20, "CRITICAL", 1)
bitmap.draw_text(+1, +1, 160, 20, "CRITICAL", 1)
bitmap.font.color.set(255, 255, 255)
bitmap.draw_text(0, 0, 160, 20, "CRITICAL", 1)
end
@_damage_sprite = ::Sprite.new(self.viewport)
@_damage_sprite.bitmap = bitmap
@_damage_sprite.ox = 80
@_damage_sprite.oy = 20
@_damage_sprite.x = self.x
@_damage_sprite.x -= self.bitmap.width/2 if @battler.is_a?(Game_Actor)
@_damage_sprite.y = self.y - self.oy / 2
@_damage_sprite.z = 3000
@_damage_duration = 40
end
end
end
修改一下挨打的时候文字的位置。
再修改一下指针位置:
class Arrow_Actor < Arrow_Base中的
self.x = self.actor.screen_x改为
self.x = self.actor.screen_x - 100
就算全部完成了。
如果你的敌人也要待机动画和挨打、防御动画,上面素有的.is_a?(Game_Actor)和.is_a?(Game_Enemy)这种区别对待的东西全部去掉即可。Happy~
复制代码
作者:
落雪无温
时间:
2014-2-15 14:54
546936326 发表于 2014-2-14 19:52
(。・`ω′・)哦哦哦thankyou,话说是在哪里看到的?没搜到的说,比如这里面还提到了些别的几个教程该去哪找呢?
欢迎光临 Project1 (https://rpg.blue/)
Powered by Discuz! X3.1