wesnoth/data/lua/diversion.lua
Steve Cotton e3deff8bfd Make undo work again, undeprecate on_event()
Fixes #6898. The issue is that non-WML events added through the new events API
always disable undo with no equivalent of WML's `[allow_undo]`. The long-term
fix is to add a way to do that; however until that's available then listeners
for `moveto` need to use the old `on_event` API. The old `on_event` API can't
be deprecated yet, and this is enforced by our unit tests (the build fails if
there are unexpected deprecation warnings during the tests).

Reverts most of 7e234f8833282424b3535b9c334c751748f7222b. Does not revert files
that only listen for non-undoable events such as `die` or `new turn`.

Reverts the deprecation part of #5663's 8cd133263058a5df85f64988e348d2cf54d13a48.
2022-11-19 05:23:30 +01:00

108 lines
3.3 KiB
Lua

local _ = wesnoth.textdomain 'wesnoth-help'
local T = wml.tag
local on_event = wesnoth.require("on_event")
local u_pos_filter = function(u_id)
local output = "initial"
local hex_dirs = {"n", "ne", "se", "s", "sw", "nw"}
local diversion_unit = wesnoth.units.get(u_id)
if not diversion_unit then
return nil
end
for i, dir in ipairs(hex_dirs) do
if diversion_unit:matches {
id = u_id,
T.filter_adjacent {
is_enemy = "yes",
adjacent = dir,
formula = "self.hitpoints > 0",
T.filter_adjacent {
is_enemy = "yes",
adjacent = dir,
formula = "self.hitpoints > 0"
}
}
} then
output = "diverter"
break
end
end
if output ~= "initial" then
return output
else
-- either nothing passed filter, or there was an error
return nil
end
end
local status_anim_update = function(is_undo)
local ec = wesnoth.current.event_context
local changed_something = false
if not ec.x1 or not ec.y1 then
return
end
-- find all units on map with ability = diversion but not status.diversion = true
local div_candidates = wesnoth.units.find_on_map({
ability = "diversion",
{"not", { status = "diversion" }}
})
-- for those that pass the filter now, change status and fire animation
for index, ec_unit in ipairs(div_candidates) do
local filter_result = u_pos_filter(ec_unit.id)
if filter_result then
changed_something = true
ec_unit.status.diversion = true
ec_unit:extract()
ec_unit:to_map(false)
wesnoth.wml_actions.animate_unit {
flag = "launching",
with_bars = true,
T.filter { id = ec_unit.id }
}
end
end
-- find all units on map with ability = diversion and status.diversion = true
local stop_candidates = wesnoth.units.find_on_map({
ability = "diversion",
status = "diversion"
})
-- for those that fail the filter now, change status and fire animation
for index, ec_unit in ipairs(stop_candidates) do
local filter_result = u_pos_filter(ec_unit.id)
if not filter_result then
changed_something = true
ec_unit.status.diversion = false
ec_unit:extract()
ec_unit:to_map(false)
wesnoth.wml_actions.animate_unit {
flag = "landing",
with_bars = true,
T.filter { id = ec_unit.id }
}
end
end
if changed_something and not is_undo then
wesnoth.wml_actions.on_undo {
wml.tag.on_undo_diversion {
}
}
end
end
function wesnoth.wml_actions.on_undo_diversion(cfg)
status_anim_update(true)
end
on_event("moveto, die, recruit, recall", function()
status_anim_update()
end)