事件
事件其实是包含“事件”与“触发器”2个部分。你可以在任意对象上以某个事件名注册触发器,当该对象以该事件发起出事件时,便会被触发器接收到。发起事件时可以传入N个自定义参数,这些参数会被触发器接收到。你可以给同一个对象的某个事件名下注册多个触发器,当发起事件时,这些触发器会按照注册顺序反序执行。在这些触发器依次执行的过程中,删除一个还在排队等待执行的触发器 ,那么它将不会执行;新建该事件名的触发器,那么它本次也不会执行。
-- 发起一个事件,自定义参数为...
base.event_notify(obj, name, ...)
-- 也可以用这个方法来发起事件,区别之后再讲
base.event_dispatch(obj, name, ...)
-- 这个事件会被该触发器接收到
base.event_register(obj, name, function (trigger, ...)
-- 接收到的自定义参数为...
end)
为了方便起见,我们将一些常用对象做了封装
全局事件。
-- 发起
base.game:event_notify(name, ...)
base.game:event_dispatch(name, ...)
-- 接收
base.game:event(name, function (trigger, ...)
end)
玩家事件,玩家事件发起完毕后会使用同样的参数再发起一次全局事件。
-- 发起
player:event_notify(name, ...)
player:event_dispatch(name, ...)
-- 接收
player:event(name, function (trigger, ...)
end)
base.game:event(name, function (trigger, ...)
end)
单位事件,玩家事件发起完毕后会使用同样的参数再发起一次玩家事件和一次全局事件,发起玩家事件时玩家为单位的控制者。
-- 发起
unit:event_notify(name, ...)
unit:event_dispatch(name, ...)
-- 接收
unit:event(name, function (trigger, ...)
end)
unit:get_owner():event(name, function (trigger, ...)
end)
base.game:event(name, function (trigger, ...)
end)
event_notify与event_dispatch的区别在于,event_dispatch
可以获取到触发器的返回值:当接收事件的触发器返回了一个非nil
的值后,当前事件将被终止,并将返回值返回给event_dispatch
的调用方。而event_notify
的事件则无法被终止,也不关心返回值。
base.game:event('加法', function (trigger, a, b)
return a + b
end)
local result = base.game:event_dispatch('加法', 1, 2)
print(result) --> 3
方法
event_register
注册事件
- 参数
- object (table/userdata) - 对象
- name (string) - 事件名
- callback (function) - 回调函数
- 返回
- trigger (trigger) - 触发器对象
- 回调参数
- trigger (trigger) - 触发器对象
- ... (...) - 自定义数据
- 回调返回
- ... (...) - 自定义返回值(只有使用event_dispatch时有意义)
event_dispatch
发起事件(关心返回值)
- 参数
- name (string) - 事件名
- obj (table/userdata) - 对象
- ... (...) - 自定义数据
event_notify
发起事件(不关心返回值)
- 参数
- name (string) - 事件名
- obj (table/userdata) - 对象
- ... (...) - 自定义数据
内置事件
框架内置了许多事件,有些事件是通过event_dispatch发起的,意味着你可以给他设置返回值,这些事件会特别说明。
单位-初始化
- 参数
- unit (unit) - 创建的单位
此时单位还未添加技能,在这个事件中给单位添加技能可以阻止 HeroSkill 与 HideSkill 中的同槽位技能。
注意,此事件触发时该单位刚被创建,他会在当帧的后半阶段被同步给能看见他的玩家(包括自己)的客户端,因此,不要在初始化事件中立即该单位的id同步给客户端(包括使用player:set_hero也是一样效果),或者客户端拿到了不要立即使用(下一帧使用即可) 。因为此时客户端还没有收到该单位出现在视野的协议,立即使用可能会有些问题。
base.game:event('单位-初始化', function (trg, unit)
end)
单位-创建
- 参数
- unit (unit) - 创建的单位
此时技能已经添加完毕,如果是镜像的话单位属性也已经复制完毕。
和
单位-初始化
事件一样,单位本身此时还没有本同步给客户端。因此,不要在客户端立即使用该单位。下一帧再使用是可以的。
base.game:event('单位-创建', function (trg, unit)
end)
单位-即将死亡
- 参数
- damage (damage) - 即将杀死单位的伤害
当单位即将因为受到伤害而死亡时会触发此事件,返回 false
可以阻止单位被杀死。
unit:event('单位-即将死亡', function (trg, damage)
return false
end)
单位-死亡
- 参数
- dead (unit) - 死者
- killer (unit) - 凶手
此时单位已经死亡。
unit:event('单位-死亡', function (trg, unit, killer)
end)
单位-复活
- 参数
- unit (unit) - 复活的单位
此时单位已经复活。
unit:event('单位-复活', function (trg, unit)
end)
单位-升级
- 参数
- unit (unit) - 升级的单位
此时单位已经升级。
unit:event('单位-升级', function (trg, unit)
end)