跳到主要内容

Lua 脚本编写:世界与环境

webapp_banner.jpg

本页面涵盖 context.worldcontext.vectorscontext.settingscontext.event 上可用的每一个方法。它们让你的 Lua 能力可以与 Minecraft 世界交互——生成实体、播放特效、查询方块等等。如果你刚接触 Lua 能力,请先从 入门 开始。

EliteMobs Boss 上下文

EliteMobs 的 Boss 能力复用了 MagmaCore 的 Lua 沙箱。Boss 的 context.world 起源于共享的 MagmaCore world 表,因此诸如 get_block_at(...)set_block_at(...)spawn_particle(...) 这类通用坐标辅助方法仍然可用。本页面聚焦于 EliteMobs Boss 专有的 context.worldcontext.vectorscontext.settingscontext.event 新增内容与覆盖实现。关于通用的 world API,请参见 MagmaCore Lua 脚本引擎

当两边存在同名方法时,以 EliteMobs 版本为准:下文记录的每个 *_at_location 方法都会覆盖共享版本,以便 Boss 脚本保留 EliteMobs 的语义(闪电绕过保护、更丰富的粒子规格、临时方块跟踪器)。

只有安装了 FreeMinecraftModels 才会出现的战利品辅助方法

当服务器上同时安装了 FreeMinecraftModels 时,它会在共享的 world 表上注册三个额外方法,因此 Boss 能力也会继承它们:world:drop_elitemobs_procedural_loot(player, level[, location])world:drop_elitemobs_random_loot(player, level[, location])world:drop_elitemobs_custom_loot(player, filename, level[, location])。每个方法都接受玩家包装器、UUID 字符串或玩家名称;当 location 被省略或无效时,会回退到该玩家自身的位置;返回值为布尔值。如果缺少其中任一插件,它们会返回 false 而不是报错。


context.world

world 表提供了用于生成实体、播放特效、修改方块以及改变世界状态的方法。所有方法都使用冒号语法调用(world:method())。


world:spawn_particle_at_location(location, particleSpec)

在某个位置生成粒子。第二个参数可以是简单的粒子名称字符串,也可以是完整的粒子规格表,以便进行更高级的控制。

参数类型说明
locationlocation 表生成粒子的位置
particleSpec字符串或表粒子名称 或粒子规格表(见下文)
示例
return {
api_version = 1,
on_enter_combat = function(context)
-- Simple particle by name
context.world:spawn_particle_at_location(context.boss:get_location(), "FLAME")

-- Full particle spec table with red dust
context.world:spawn_particle_at_location(context.boss:get_location(), {
particle = "DUST",
amount = 10,
x = 0.5,
y = 0.5,
z = 0.5,
speed = 0.02,
red = 255,
green = 0,
blue = 0,
})
end
}

粒子规格表格式

类型默认值说明
particle字符串必填粒子名称
amount整数1粒子数量
xyz数字0各轴上的扩散/偏移
speed数字0粒子速度
redgreenblue整数255用于 DUSTDUST_COLOR_TRANSITION 的 RGB 颜色
toRedtoGreentoBlue整数255DUST_COLOR_TRANSITION 的过渡目标颜色
提示

对于 DUST_COLOR_TRANSITION,你也可以使用 snake_case 形式的键:to_redto_greento_blue

注意

与 EliteScript 的 YAML 配置不同,Lua 中的粒子名称支持旧版粒子名称转换。你必须使用当前的 Spigot API 名称(例如用 FIREWORK 而不是 FIREWORKS_SPARK,用 SMOKE 而不是 SMOKE_NORMAL,用 DUST 而不是 REDSTONE)。完整的当前名称列表及其旧版对应名称,请参见 有效粒子列表


world:play_sound_at_location(location, sound, volume, pitch)

在某个位置播放声音。

参数类型默认值说明
locationlocation 表播放声音的位置
sound字符串Minecraft 声音键(例如 "entity.blaze.shoot")或 Spigot 的 Sound 枚举名称。资源包中的键同样可用。
volume数字1.0音量
pitch数字1.0音调
示例
return {
api_version = 1,
on_spawn = function(context)
context.world:play_sound_at_location(
context.boss:get_location(),
"entity.wither.spawn",
1.0,
0.5
)
end
}

world:strike_lightning_at_location(location)

在某个位置降下闪电(既有视觉效果也会造成伤害)。

参数类型说明
locationlocation 表降下闪电的位置
示例
return {
api_version = 1,
on_boss_damaged_by_player = function(context)
if context.player == nil then return end
if not context.cooldowns:check_local("lightning", 100) then return end
context.world:strike_lightning_at_location(context.player:get_location())
context.player:send_message("&eA bolt of lightning strikes you!")
end
}

world:spawn_entity_at_location(entityType, location, options)

生成一个原版 Minecraft 实体。

参数类型说明
entityType字符串实体类型名称(例如 "FIREBALL""ARROW"
locationlocation 表生成位置
options表(可选)生成选项(见下文)

实体生成选项

类型默认值说明
velocityvector 表nil初始速度 {x, y, z}
effect字符串nil生成时播放的 EntityEffect
duration整数0经过这么多游戏刻后自动移除(0 = 永不移除)
on_land函数nil实体落地时的回调
max_ticks整数6000强制触发 on_land 回调前最多监视的游戏刻数

返回一个实体包装器表。非生物实体(FIREBALLARROWTNT 等)返回的是 非生物引用包装器,其中 is_valid() 是一个方法。 生物实体类型(ZOMBIEGIANT 等)返回的则是完整的 生物实体包装器,其中 is_valid 是一个布尔字段——对这类包装器调用 entity:is_valid() 会抛出 attempt to call a boolean value

示例
return {
api_version = 1,
on_boss_damaged_by_player = function(context)
if context.player == nil then return end
if not context.cooldowns:check_local("fireball_spawn", 100) then return end
-- Spawn a fireball aimed at the player
local boss_loc = context.boss:get_location()
local dir = context.vectors.get_vector_between_locations(boss_loc, context.player:get_location())
dir = context.vectors.normalize_vector(dir)

context.world:spawn_entity_at_location("FIREBALL", boss_loc, {
velocity = { x = dir.x * 2, y = dir.y * 2, z = dir.z * 2 },
duration = 100,
})
end
}
示例
return {
api_version = 1,
on_enter_combat = function(context)
-- Spawn a primed TNT with a landing callback
context.world:spawn_entity_at_location("TNT", context.boss:get_location(), {
velocity = { x = 0, y = 1.5, z = 0 },
on_land = function(land_location, entity_ref)
context.world:spawn_particle_at_location(land_location, {
particle = "EXPLOSION_EMITTER",
amount = 1,
})
end,
})
end
}

world:spawn_falling_block_at_location(location, material, options)

生成一个下落的方块实体。

参数类型说明
locationlocation 表生成位置
material字符串材料名称(例如 "STONE""MAGMA_BLOCK"
options表(可选)生成选项(见下文)

下落方块选项

类型默认值说明
velocityvector 表nil初始速度 {x, y, z}
drop_item布尔值false该方块是否作为物品掉落
hurt_entities布尔值false该方块是否对它砸中的实体造成伤害
on_land函数nil方块落地时的回调 function(land_location, entity_ref)

返回一个实体引用表。

示例
return {
api_version = 1,
on_enter_combat = function(context)
-- Rain magma blocks from above
local loc = context.boss:get_location()
for i = 1, 5 do
local offset_loc = {
x = loc.x + math.random(-3, 3),
y = loc.y + 10,
z = loc.z + math.random(-3, 3),
world = loc.world
}
context.world:spawn_falling_block_at_location(offset_loc, "MAGMA_BLOCK", {
velocity = { x = 0, y = -0.5, z = 0 },
hurt_entities = true,
on_land = function(land_location, entity_ref)
context.world:spawn_particle_at_location(land_location, { particle = "LAVA", amount = 8 })
end,
})
end
end
}

world:spawn_custom_boss_at_location(filename, location, options)

根据配置文件生成一个 EliteMobs 自定义 Boss。

参数类型说明
filename字符串Boss 配置文件名(例如 "my_boss.yml"
locationlocation 表生成位置
options表(可选)生成选项(见下文)

自定义 Boss 生成选项

类型默认值说明
level整数Boss 等级覆盖生成出来的 Boss 等级
silent布尔值false抑制生成消息
velocityvector 表nil初始速度
add_as_reinforcement布尔值false注册为当前 Boss 的增援

返回一个实体包装器表;如果无法创建该 Boss,则返回 nil

示例
return {
api_version = 1,
on_enter_combat = function(context)
local minion = context.world:spawn_custom_boss_at_location(
"skeleton_minion.yml",
context.boss:get_location(),
{ level = 10, add_as_reinforcement = true }
)
if minion ~= nil then
context.boss:send_message("&cMinions, arise!")
end
end
}

world:spawn_boss_at_location(filename, location, level)

一个更简单的 Boss 生成方法。在某个位置生成自定义 Boss,等级可选。

参数类型默认值说明
filename字符串Boss 配置文件名
locationlocation 表Boss 位置生成位置(可选,默认为 Boss 所在位置)
level整数Boss 等级覆盖生成等级(可选)

返回一个实体包装器表,或 nil

示例
return {
api_version = 1,
on_enter_combat = function(context)
context.world:spawn_boss_at_location("zombie_guard.yml", context.boss:get_location(), 5)
context.boss:send_message("&cGuards, defend me!")
end
}

world:spawn_reinforcement_at_location(filename, location, level, velocity)

生成一个由 EliteMobs 增援系统跟踪的增援怪。

参数类型默认值说明
filename字符串Boss 配置文件名
locationlocation 表生成位置
level整数0增援等级。设为 0 时由召唤辅助逻辑决定其默认等级行为。
velocityvector 表nil初始速度(可选)

返回一个实体包装器表,或 nil

示例
return {
api_version = 1,
on_enter_combat = function(context)
context.world:spawn_reinforcement_at_location(
"necro_skeleton.yml",
context.boss:get_location(),
0,
{ x = 0, y = 0.5, z = 0 }
)
context.boss:send_message("&5Rise, my servant!")
end
}

world:spawn_fireworks_at_location(location, spec)

生成一个烟花实体,并可完全控制其效果。

参数类型说明
locationlocation 表生成位置
spec烟花规格(见下文)

烟花规格表

类型默认值说明
power整数1飞行力度(高度)
velocityvector 表nil初始速度
shot_at_angle布尔值true烟花是否以一定角度射出(设置了 velocity 时使用)
effects表的数组nil烟花效果规格的数组。如果省略,则把顶层规格当作单个效果处理。

烟花效果规格

类型默认值说明
type字符串"BALL_LARGE""BALL""BALL_LARGE""STAR""BURST""CREEPER"
flicker布尔值true闪烁效果
trail布尔值true拖尾效果
colorsnil颜色名称或 {red, green, blue} 表的数组
fade_colorsnil渐隐颜色名称或 {red, green, blue} 表的数组

颜色名称:"WHITE""SILVER""GRAY""BLACK""RED""MAROON""YELLOW""OLIVE""LIME""GREEN""AQUA""TEAL""BLUE""NAVY""FUCHSIA""PURPLE""ORANGE"

返回一个实体引用表。你可以对它调用 :detonate() 来强制立即引爆。

示例
return {
api_version = 1,
on_spawn = function(context)
local fw = context.world:spawn_fireworks_at_location(context.boss:get_location(), {
power = 0,
effects = {
{
type = "STAR",
flicker = true,
trail = true,
colors = { "RED", "ORANGE", { red = 255, green = 200, blue = 0 } },
fade_colors = { "YELLOW" },
},
},
})

-- Detonate immediately for a visual burst
context.scheduler:run_after(1, function()
fw:detonate()
end)
end
}

world:spawn_splash_potion_at_location(location, spec)

生成一个被投掷出去的喷溅药水实体。

参数类型说明
locationlocation 表生成位置
spec药水规格(见下文)

喷溅药水规格表

类型说明
velocityvector 表被投掷药水的初始速度
effects表的数组药水效果规格的数组

药水效果规格

类型默认值说明
type字符串必填药水效果类型名称(例如 "SLOWNESS""POISON"
duration整数0持续时间,单位为游戏刻
amplifier整数0效果等级增幅(0 = I 级)
overwrite布尔值true是否覆盖同类型的已有效果

返回一个实体引用表,或 nil

示例
return {
api_version = 1,
on_boss_damaged_by_player = function(context)
if context.player == nil then return end
if not context.cooldowns:check_local("potion_throw", 200) then return end

local dir = context.vectors.get_vector_between_locations(
context.boss:get_location(),
context.player:get_location()
)
dir = context.vectors.normalize_vector(dir)

context.world:spawn_splash_potion_at_location(context.boss:get_location(), {
velocity = { x = dir.x * 1.5, y = 0.5, z = dir.z * 1.5 },
effects = {
{ type = "SLOWNESS", duration = 100, amplifier = 1 },
{ type = "WEAKNESS", duration = 60, amplifier = 0 },
},
})
end
}

world:place_temporary_block_at_location(location, material, duration, requireAir)

放置一个临时方块,它会在指定时长后自动还原。

参数类型默认值说明
locationlocation 表放置位置
material字符串材料名称
duration整数0方块还原前的游戏刻数(0 = 永久保留)
requireAir布尔值false若为 true,则仅在该处当前为空气时才放置
示例
return {
api_version = 1,
on_enter_combat = function(context)
-- Create a temporary ice floor under the boss
local loc = context.boss:get_location()
for dx = -2, 2 do
for dz = -2, 2 do
context.world:place_temporary_block_at_location(
{ x = loc.x + dx, y = loc.y - 1, z = loc.z + dz, world = loc.world },
"PACKED_ICE",
100,
false
)
end
end
end
}

world:set_block_at_location(location, material, requireAir)

永久性地设置一个方块。如果你希望它能还原,请使用 place_temporary_block_at_location

参数类型默认值说明
locationlocation 表放置位置
material字符串材料名称
requireAir布尔值false若为 true,则仅在该处当前为空气时才放置
示例
return {
api_version = 1,
on_enter_combat = function(context)
-- Place fire at the boss's location
context.world:set_block_at_location(context.boss:get_location(), "FIRE", true)
end
}

world:get_block_type_at_location(location)

以字符串形式返回某个位置方块的材料名称。

参数类型说明
locationlocation 表要查询的位置
示例
return {
api_version = 1,
on_enter_combat = function(context)
local block_type = context.world:get_block_type_at_location(context.boss:get_location())
if block_type == "WATER" then
context.boss:send_message("&bThe boss is empowered by water!")
context.boss:apply_potion_effect("SPEED", 200, 1)
end
end
}

world:get_highest_block_y_at_location(location)

返回给定 X/Z 位置上最高的非空气方块的 Y 坐标。

参数类型说明
locationlocation 表要查询的位置(只使用 X 和 Z)
示例
return {
api_version = 1,
on_boss_damaged_by_player = function(context)
if context.player == nil then return end
if not context.cooldowns:check_local("skyport", 200) then return end
local loc = context.player:get_location()
local ground_y = context.world:get_highest_block_y_at_location(loc)
-- Teleport the player to the surface
context.player:teleport_to_location({
x = loc.x, y = ground_y + 1, z = loc.z, world = loc.world
})
context.player:send_message("&eYou are teleported to the surface!")
end
}

world:get_blast_resistance_at_location(location)

以数字形式返回某个位置方块的爆炸抗性。

参数类型说明
locationlocation 表要查询的位置
示例
return {
api_version = 1,
on_enter_combat = function(context)
local resistance = context.world:get_blast_resistance_at_location(context.boss:get_location())
context.log:info("Blast resistance at boss: " .. resistance)
end
}

world:is_air_at_location(location)

如果该位置的方块是空气,则返回 true

参数类型说明
locationlocation 表要查询的位置
示例
return {
api_version = 1,
on_enter_combat = function(context)
local loc = context.boss:get_location()
local above = { x = loc.x, y = loc.y + 2, z = loc.z, world = loc.world }
if context.world:is_air_at_location(above) then
-- There is space above the boss, launch upward
context.boss:set_velocity_vector({ x = 0, y = 1.5, z = 0 })
end
end
}

world:is_passable_at_location(location)

如果该位置的方块可以穿过(实体能够从中走过),则返回 true

参数类型说明
locationlocation 表要查询的位置
示例
return {
api_version = 1,
on_enter_combat = function(context)
if context.world:is_passable_at_location(context.boss:get_location()) then
context.log:info("Boss is in a passable block")
end
end
}

world:is_passthrough_at_location(location)

如果该位置的方块不是实心方块,则返回 true(与 passable 类似,但基于实心判定)。

参数类型说明
locationlocation 表要查询的位置
示例
return {
api_version = 1,
on_enter_combat = function(context)
local loc = context.boss:get_location()
local above = { x = loc.x, y = loc.y + 1, z = loc.z, world = loc.world }
if context.world:is_passthrough_at_location(above) then
context.log:info("Boss can move upward")
end
end
}

world:is_on_floor_at_location(location)

如果该位置的方块不是实心方块,并且其下方的方块是实心方块(即该位置“站在地面上”),则返回 true

参数类型说明
locationlocation 表要查询的位置
示例
return {
api_version = 1,
on_enter_combat = function(context)
if context.world:is_on_floor_at_location(context.boss:get_location()) then
context.boss:send_message("&aThe boss slams the ground!")
context.world:spawn_particle_at_location(context.boss:get_location(), {
particle = "CLOUD",
amount = 30,
})
end
end
}

world:is_standing_on_material(location, material)

如果该位置正下方的方块与给定材料相符,则返回 true

参数类型说明
locationlocation 表要查询的位置
material字符串要检查的 材料名称
示例
return {
api_version = 1,
on_boss_damaged_by_player = function(context)
if context.player == nil then return end
if context.world:is_standing_on_material(context.player:get_location(), "SOUL_SAND") then
context.player:send_message("&8The soul sand saps your strength!")
context.player:apply_potion_effect("SLOWNESS", 60, 2)
end
end
}

world:set_world_time(time) / world:set_world_time(location, time)

设置世界时间。你也可以传入一个位置来指定作用于哪个世界。

参数类型说明
locationlocation 表(可选)要影响的世界。默认为 Boss 所在的世界。
time整数以游戏刻表示的世界时间(0 = 黎明,6000 = 正午,13000 = 夜晚,18000 = 午夜)
示例
return {
api_version = 1,
on_enter_combat = function(context)
-- Set to midnight when combat starts
context.world:set_world_time(18000)
context.boss:send_message("&8Darkness falls...")
end
}

world:set_world_weather(weather, duration) / world:set_world_weather(location, weather, duration)

设置 Boss 所在世界的天气。

参数类型默认值说明
locationlocation 表(可选)Boss 所在世界要影响的世界
weather字符串"CLEAR""RAIN"(或 "PRECIPITATION")、"THUNDER"
duration整数6000天气持续时间,单位为游戏刻
示例
return {
api_version = 1,
on_enter_combat = function(context)
-- Start a thunderstorm for 200 ticks
context.world:set_world_weather("THUNDER", 200)
context.boss:send_message("&eA storm gathers!")
end
}

world:generate_fake_explosion(blockLocations, sourceLocation)

使用 EliteMobs 的爆炸恢复系统制造一次假爆炸的视觉效果(方块会被炸毁并随后恢复)。

参数类型说明
blockLocationslocation 表的数组要“炸毁”的方块位置数组
sourceLocationlocation 表(可选)用于方向计算的爆炸源位置
示例
return {
api_version = 1,
on_enter_combat = function(context)
local loc = context.boss:get_location()
local blocks = {}
for dx = -1, 1 do
for dz = -1, 1 do
table.insert(blocks, { x = loc.x + dx, y = loc.y, z = loc.z + dz, world = loc.world })
end
end
context.world:generate_fake_explosion(blocks, loc)
end
}

world:run_console_command(command)

以服务器身份执行一条控制台命令。

参数类型说明
command字符串要执行的命令(不带开头的 /
示例
return {
api_version = 1,
on_enter_combat = function(context)
context.world:run_console_command("say The boss has entered phase 2!")
end
}

world:run_empowered_lightning_task_at_location(location)

运行强化闪电的视觉任务(由末影龙相关能力使用)。它会制造更具戏剧性的闪电打击,并附带额外特效。

参数类型说明
locationlocation 表降下闪电的位置
示例
return {
api_version = 1,
on_enter_combat = function(context)
context.world:run_empowered_lightning_task_at_location(context.boss:get_location())
context.boss:send_message("&eFeel the power of the storm!")
end
}

world:spawn_fake_gold_nugget_at_location(location, velocity, hasGravity)

生成一枚假的金粒弹射物,由弹幕系统使用。

参数类型默认值说明
locationlocation 表生成位置
velocityvector 表初始速度
hasGravity布尔值false该弹射物是否受重力影响

返回一个假弹射物表,包含以下方法:get_location()set_gravity(bool)remove()is_removed()

示例
return {
api_version = 1,
on_boss_damaged_by_player = function(context)
if context.player == nil then return end
if not context.cooldowns:check_local("nugget", 60) then return end

local dir = context.vectors.get_vector_between_locations(
context.boss:get_location(),
context.player:get_location()
)
dir = context.vectors.normalize_vector(dir)

context.world:spawn_fake_gold_nugget_at_location(
context.boss:get_location(),
{ x = dir.x, y = dir.y, z = dir.z }
)
end
}

world:run_fake_gold_nugget_damage(projectiles)

对一组假金粒弹射物执行针对附近实体的伤害处理。

参数类型说明
projectilesspawn_fake_gold_nugget_at_location 返回的假弹射物表的数组
示例
return {
api_version = 1,
on_enter_combat = function(context)
-- Spawn some projectiles and store them
context.state.active_projectiles = {}
local loc = context.boss:get_location()
for i = 1, 5 do
local angle = (i / 5) * math.pi * 2
local nugget = context.world:spawn_fake_gold_nugget_at_location(
loc,
{ x = math.cos(angle) * 0.5, y = 0.3, z = math.sin(angle) * 0.5 }
)
table.insert(context.state.active_projectiles, nugget)
end

-- Process damage each tick for 3 seconds
local task_id
task_id = context.scheduler:run_every(1, function(tick_context)
tick_context.world:run_fake_gold_nugget_damage(tick_context.state.active_projectiles)
end)
context.scheduler:run_after(60, function(later_context)
later_context.scheduler:cancel_task(task_id)
end)
end
}

world:generate_player_loot(times)

为对该 Boss 造成过伤害的玩家生成战利品。

参数类型默认值说明
times整数1战利品掷取次数
示例
return {
api_version = 1,
on_boss_damaged_by_player = function(context)
local pct = context.boss:get_health() / context.boss:get_maximum_health()
if pct < 0.5 and not context.boss:has_tag("bonus_loot") then
context.boss:add_tag("bonus_loot")
context.world:generate_player_loot(2)
context.boss:send_message("&6Bonus loot drops!")
end
end
}

world:drop_bonus_coins(multiplier)

为所有参与伤害该 Boss 的玩家掉落额外金币。

参数类型默认值说明
multiplier数字2.0金币数量倍率
示例
return {
api_version = 1,
on_boss_damaged_by_player = function(context)
local pct = context.boss:get_health() / context.boss:get_maximum_health()
if pct < 0.25 and not context.boss:has_tag("bonus_coins") then
context.boss:add_tag("bonus_coins")
context.world:drop_bonus_coins(3.0)
context.boss:send_message("&6Gold spills everywhere!")
end
end
}

context.vectors

向量数学辅助工具。它们以普通函数的方式调用(点号语法),而不是方法。

方法返回值说明
vectors.get_vector_between_locations(loc1, loc2[, options])vector 表loc1 指向 loc2 的方向
vectors.normalize_vector(vec)vector 表返回一个单位长度的向量
vectors.rotate_vector(vec, pitch, yaw)vector 表按 pitch 和 yaw 的角度旋转向量

所有 vector 表都包含 xyz 字段。

vectors.get_vector_between_locations(loc1, loc2, options)

参数类型说明
loc1location 表起点
loc2location 表终点
options表(可选)后处理选项(见下文)

向量选项

类型默认值说明
normalize布尔值false对结果向量做归一化
multiplier数字1.0缩放该向量
offsetvector 表nil加上一个偏移向量
示例
return {
api_version = 1,
on_boss_damaged_by_player = function(context)
if context.player == nil then return end
if not context.cooldowns:check_local("dash", 100) then return end
-- Compute a normalized direction from boss to player, scaled to speed 2
local dir = context.vectors.get_vector_between_locations(
context.boss:get_location(),
context.player:get_location(),
{ normalize = true, multiplier = 2.0 }
)
-- Launch the boss toward the player
context.boss:set_velocity_vector(dir)
end
}

vectors.normalize_vector(vec)

参数类型说明
vecvector 表输入向量
示例
return {
api_version = 1,
on_boss_damaged_by_player = function(context)
if context.player == nil then return end
local raw = context.vectors.get_vector_between_locations(
context.boss:get_location(),
context.player:get_location()
)
local unit = context.vectors.normalize_vector(raw)
context.log:info("Direction: " .. unit.x .. ", " .. unit.y .. ", " .. unit.z)
end
}

vectors.rotate_vector(vec, pitch, yaw)

参数类型说明
vecvector 表输入向量
pitch数字绕 X 轴旋转的角度
yaw数字绕 Y 轴旋转的角度
示例
return {
api_version = 1,
on_boss_damaged_by_player = function(context)
if context.player == nil then return end
if not context.cooldowns:check_local("spread_shot", 100) then return end
local forward = context.vectors.normalize_vector(
context.vectors.get_vector_between_locations(
context.boss:get_location(),
context.player:get_location()
)
)
-- Fire three fireballs in a spread pattern
for _, yaw_offset in ipairs({ -30, 0, 30 }) do
local dir = context.vectors.rotate_vector(forward, 0, yaw_offset)
context.boss:summon_projectile(
"FIREBALL",
context.boss:get_eye_location(),
{
x = context.boss:get_location().x + dir.x * 10,
y = context.boss:get_location().y + dir.y * 10,
z = context.boss:get_location().z + dir.z * 10,
world = context.boss:get_location().world
},
1.0
)
end
end
}
提示

你可以在循环中旋转一个基准向量,从而构建出一组扩散方向:

local base = context.vectors.normalize_vector(
context.vectors.get_vector_between_locations(boss_loc, target_loc)
)
for angle = 0, 360, 30 do
local dir = context.vectors.rotate_vector(base, 0, angle)
-- Use dir for spawning projectiles in a ring
end

context.settings

以只读方式访问与能力相关的配置值。

方法返回值说明
settings:warning_visual_effects_enabled()布尔值怪物战斗设置中是否启用了警示视觉特效
示例
return {
api_version = 1,
on_enter_combat = function(context)
if context.settings:warning_visual_effects_enabled() then
context.world:spawn_particle_at_location(context.boss:get_location(), {
particle = "DUST",
amount = 20,
red = 255, green = 0, blue = 0,
})
end
end
}

context.event

当前钩子的事件数据。可用字段取决于是哪个钩子触发了本次调用。

字段或方法可用时机说明
event.damage_amount伤害类钩子当前的伤害数值(调用时刻的快照)
event.damage_cause伤害类钩子Bukkit DamageCause 枚举名称(例如 "ENTITY_ATTACK"
event.cancel_event()可取消的事件取消该事件
event.set_damage_amount(value)基于 EliteDamageEvent 的钩子直接设置伤害值
event.multiply_damage_amount(multiplier)基于 EliteDamageEvent 的钩子对当前伤害做乘法
event.damager带有伤害来源实体的伤害事件伤害来源的实体引用包装器
event.projectile伤害来源是弹射物的伤害事件弹射物的实体引用包装器
event.spawn_reasonon_spawn生成原因的枚举名称
event.entityon_death、区域事件相关的实体包装器

示例:把受到的伤害减半

示例
return {
api_version = 1,
on_boss_damaged_by_player = function(context)
if context.event ~= nil then
local dmg = context.event.damage_amount
context.log:info("Boss took " .. dmg .. " damage, halving it")
context.event.multiply_damage_amount(0.5)
end
end
}

示例:取消来自弹射物的伤害

示例
return {
api_version = 1,
on_boss_damaged_by_player = function(context)
if context.event ~= nil and context.event.damage_cause == "PROJECTILE" then
context.event.cancel_event()
if context.player ~= nil then
context.player:send_message("&cThe boss deflects your projectile!")
end
end
end
}

示例:读取伤害来源

示例
return {
api_version = 1,
on_player_damaged_by_boss = function(context)
if context.event ~= nil then
context.log:info("Damage cause: " .. (context.event.damage_cause or "unknown"))
end
end
}
备注
  • damage_amount 是一个快照。在调用 set_damage_amount()multiply_damage_amount() 之后,它不会自动刷新。
  • 在计划任务的回调内部,context.eventnil。请在事件钩子中修改事件。

下一步