Scripting Lua: Primeros Pasos
Esta página te enseña a escribir tu primer script Lua para un prop o un objeto personalizado de FreeMinecraftModels, desde un archivo vacío hasta un script interactivo funcional. Al finalizar, entenderás los hooks, el context, las APIs de props y objetos, y la estructura general de cada archivo de script.
Una vez que te sientas cómodo con lo básico, continúa con las páginas complementarias:
- API de Props e Ítems -- las APIs de
context.prop,context.item,context.event,context.worldy los demás context - Ejemplos y Patrones -- scripts funcionales completos para props y objetos que puedes estudiar y adaptar
- Solución de Problemas -- errores comunes, consejos de depuración y la lista de verificación QC
Los scripts Lua de props y de objetos son actualmente experimentales. Los nombres de los hooks, los métodos auxiliares y el comportamiento aún pueden cambiar a medida que FreeMinecraftModels evoluciona, así que prueba cuidadosamente antes de usarlos en un servidor de producción.
FreeMinecraftModels usa el runtime Lua de MagmaCore. Si ya escribes poderes Lua para EliteMobs, los conceptos fundamentales -- archivos de script que devuelven una tabla, api_version, hooks, context, estado, cooldowns, programación y la sandbox -- te resultarán familiares. Los hooks exactos y los nombres de los métodos del context siguen dependiendo del plugin:
- Los scripts de EliteMobs se ejecutan en jefes y tienen hooks como
on_boss_damaged_by_player,on_enter_combat, etc. - Los scripts de props de FMM se ejecutan en props y tienen hooks como
on_right_click,on_left_click,on_zone_enter, etc. - Los scripts de objetos de FMM se ejecutan en objetos personalizados y tienen hooks como
on_equip,on_attack_entity,on_consume,on_game_tick, etc.
Las APIs context.world, context.zones, context.scheduler, context.state y context.log documentadas aquí son las versiones de FreeMinecraftModels/MagmaCore. Los scripts de NPC de EliteMobs usan las mismas tablas genéricas de MagmaCore más context.npc; los poderes de jefe de EliteMobs usan variantes específicas de jefe para varias tablas. Esta página cubre lo que es específico de los props y objetos de FMM.
Qué Son los Scripts de Props
Los scripts de props son archivos .lua independientes que se encuentran en la carpeta plugins/FreeMinecraftModels/scripts/. Se referencian desde un archivo de configuración YAML que se ubica junto al archivo del modelo, y se ejecutan cada vez que el prop aparece en el mundo.
Para Qué Son Buenos los Scripts de Props
Los scripts de props destacan cuando necesitas:
- Props interactivos que responden a los clics de los jugadores (puertas, palancas, botones)
- Props decorativos invulnerables que no pueden ser destruidos por los jugadores
- Disparadores de proximidad que detectan cuando los jugadores entran o salen de un área
- Props animados que reproducen animaciones al interactuar o con un temporizador
- Props emisores de sonido que reproducen sonidos al hacer clic o al acercarse
- Cualquier comportamiento de prop que requiera lógica más allá de la decoración estática
Si tu prop es puramente decorativo y no necesita interacción, no necesitas un script.
Qué Son los Scripts de Objetos
Los scripts de objetos usan el mismo formato de archivo .lua y la misma carpeta scripts/ que los scripts de props. La diferencia es que se adjuntan a objetos personalizados: modelos que tienen un campo material: establecido en su archivo de configuración YML. Mientras que los scripts de props se ejecutan cuando una entidad prop aparece en el mundo, los scripts de objetos se ejecutan cuando un jugador equipa el objeto personalizado (mano principal, mano secundaria o ranura de armadura) y se detienen cuando el objeto se desequipa.
Cómo Funcionan los Scripts de Objetos
- Activación: se crea una instancia de script cuando un jugador equipa un objeto personalizado de FMM. Los scripts son por jugador y por tipo de objeto: una
ScriptInstancepor par (jugador, itemId). - Desactivación: la instancia de script se destruye cuando el objeto se desequipa (se saca de la ranura activa, se tira o el jugador se desconecta).
- Identificación del objeto: los objetos personalizados se identifican por la clave PDC (PersistentDataContainer)
fmm_item_id, que es distinta delmodel_iddel prop. Para obtener un objeto correctamente etiquetado, usa/fmm giveitem <id>o el menú de administrador. - Context: los hooks de objeto reciben un
contextconcontext.player,context.item,context.world,context.state,context.scheduler,context.logy, cuando corresponde,context.event.
Para Qué Son Buenos los Scripts de Objetos
Los scripts de objetos destacan cuando necesitas:
- Armas personalizadas con habilidades especiales (espadas de escarcha, varitas mágicas)
- Herramientas con acciones únicas de clic derecho o clic con Shift
- Objetos consumibles con efectos personalizados
- Armaduras con efectos pasivos mientras se llevan puestas
- Objetos que registran su uso o tienen durabilidad limitada
- Cualquier comportamiento de objeto en mano que vaya más allá de las mecánicas vanilla
Para Quién Es Esta Página
Esta página está escrita para tres tipos de lectores:
- Alguien que ya conoce el scripting Lua de EliteMobs y quiere aprender los hooks y APIs específicos de FMM
- Alguien que es nuevo en el scripting Lua y necesita una referencia completa con nombres exactos para props
- Alguien que usa IA para redactar scripts de props y necesita suficiente detalle para saber cuándo la IA inventó algo falso
No necesitas convertirte en un desarrollador Lua completo antes de escribir scripts de props útiles. Para la mayoría de los scripts de props prácticos, lo único que realmente necesitas es:
- Cómo colocar un hook válido en la tabla devuelta
- Cómo leer valores de
context - Cómo detener la ejecución anticipadamente con
if ... then return end - Cómo llamar a algunos métodos auxiliares de forma exacta
Introducción Rápida a Lua
No necesitas ser un experto en Lua para escribir scripts de FMM. La mayoría de los scripts solo usan un puñado de conceptos: variables (local x = 5), funciones (function foo() end), comprobaciones if (if x then ... end), tablas ({key = value}) y nil (el valor "nada" de Lua). La sintaxis es ligera: sin punto y coma, sin llaves, solo end para cerrar bloques.
Para un recorrido completo con ejemplos, consulta el Motor de Scripting Lua de MagmaCore — Introducción Rápida a Lua. Esa introducción es compartida por todos los plugins de Nightbreak, así que aprenderla una vez sirve para todos.
Dónde Se Ubican los Archivos
Archivos de Script
Coloca los archivos .lua en la carpeta central de scripts:
plugins/
FreeMinecraftModels/
scripts/
invulnerable.lua
interactive_door.lua
proximity_sound.lua
FMM detecta todos los archivos .lua en plugins/FreeMinecraftModels/scripts/ al iniciar.
En la lista scripts: de un modelo, incluye la extensión .lua por claridad. FMM también acepta entradas sin la extensión y le añade .lua internamente. El archivo en disco debe seguir terminando en .lua, y los nombres siguen distinguiendo mayúsculas de minúsculas.
Archivos de Modelo y Archivos de Configuración
Cada archivo de modelo puede tener un archivo .yml de configuración asociado en el mismo directorio:
plugins/
FreeMinecraftModels/
models/
torch_01.fmmodel
torch_01.yml <-- config de script para torch_01
scripts/
invulnerable.lua <-- referenciado por torch_01.yml
El archivo .yml de configuración es lo que conecta un modelo con sus scripts.
Formato del Archivo de Configuración
El archivo de configuración YAML que se ubica junto a un archivo de modelo tiene estos campos:
isEnabled: true
voxelize: false
solidify: false
scripts:
- invulnerable.lua
Para los ítems personalizados (modelos que los jugadores pueden sostener o equipar), también estableces el campo material y, opcionalmente, name, lore y enchantments:
isEnabled: true
material: DIAMOND_SWORD
name: "&bFrost Blade"
lore:
- "&7A sword forged in eternal ice"
- "&7Slows enemies on hit"
enchantments:
- "SHARPNESS,5"
- "UNBREAKING,3"
scripts:
- frost_sword.lua
| Campo | Tipo | Predeterminado | Notas |
|---|---|---|---|
isEnabled | boolean | true | Si los scripts están activos para este prop/ítem |
scripts | lista de strings | [] | Nombres de archivos .lua en la carpeta scripts/ |
voxelize | boolean | false | Ajusta la colocación a rotaciones de 90 grados y al alineamiento con la rejilla de bloques |
solidify | boolean | false | Coloca bloques barrera solo por paquetes en la huella del prop (requiere voxelize) |
material | string | "" | Un nombre válido de Material de Bukkit (p. ej. DIAMOND_SWORD). Establecerlo convierte el modelo en un ítem personalizado que los jugadores pueden sostener o equipar, lo que activa el sistema de scripting de ítems |
name | string | "" | Nombre visible del ítem personalizado. Admite códigos de color & |
lore | lista de strings | [] | Líneas de lore mostradas en el tooltip del ítem. Admite códigos de color & |
enchantments | lista de strings | [] | Encantamientos aplicados al ítem. Formato: "ENCHANTMENT_NAME,LEVEL" (p. ej. "SHARPNESS,5") |
Puedes adjuntar múltiples scripts al mismo prop. Cada script es su propia instancia independiente.
- El ID del ítem se deriva del nombre del archivo YML sin su extensión. Por ejemplo,
frost_sword.ymlproduce un ID de ítemfrost_sword. Este es el ID que usan/fmm giveitemy la clave PDCfmm_item_id. - Los ítems vinculan solo un script de la lista
scripts:. FMM revisa las entradas en orden y usa el primer script que puede resolver, ignorando las entradas posteriores. A diferencia de los ítems, los props ejecutan todos los scripts listados que puedan resolver, cada uno como una instancia independiente. - La extensión
.luase añade automáticamente a los nombres de archivo de script si la omites, así quefrost_swordyfrost_sword.luason equivalentes en la listascripts:.
Generación Diferida de Configuración
Cuando un prop aparece y no existe un archivo .yml asociado, FMM crea automáticamente un archivo de configuración predeterminado con isEnabled: true y una lista scripts: vacía. Esto sucede de forma asíncrona, por lo que el prop no tendrá scripts en su primer spawn -- solo después de que se cree la configuración y la edites para agregar nombres de archivos de script.
Esto significa:
- Coloca tu archivo de modelo en
models/ - Genera el prop una vez (FMM crea el
.ymlautomáticamente) - Edita el
.ymlgenerado para agregar tus nombres de archivos de script - Vuelve a generar el prop o recarga (los scripts ahora están activos)
Referencia de Hooks
Cada archivo de script Lua de prop devuelve una tabla. Cada clave en esa tabla (además de api_version y priority) debe ser uno de los hooks listados a continuación. El runtime llama a la función correspondiente cada vez que se dispara el evento del juego asociado.
| Hook | Se dispara cuando | Notas |
|---|---|---|
on_spawn | El prop aparece en el mundo | Se ejecuta una vez cuando el script se vincula |
on_game_tick | Una vez por tick del servidor (50 ms) | Solo activo si el script define este hook |
on_destroy | El prop se elimina del mundo | Hook de limpieza |
on_left_click | Un jugador hace clic izquierdo (golpea) el prop | context.event es el evento de daño |
on_right_click | Un jugador hace clic derecho en el prop | context.event es el evento de interacción |
on_zone_enter | Un jugador entra en una zona vigilada | Requiere que se haya configurado una vigilancia de zona |
on_zone_leave | Un jugador sale de una zona vigilada | Requiere que se haya configurado una vigilancia de zona |
El validador de scripts actual acepta on_projectile_hit en los scripts de props, pero el runtime actual todavía no despacha impactos de proyectil a los scripts de props. Usa el on_projectile_hit de ítem para comportamientos de proyectil ligados a un ítem con script, o la API de Bukkit ModeledEntityHitByProjectileEvent para gestionar proyectiles sobre entidades modeladas desde el plugin.
Referencia de Hooks de Ítems
Los scripts de ítems devuelven una tabla igual que los scripts de props, con api_version = 1 y funciones de hook. Los siguientes hooks están disponibles para los scripts de ítems. Todos los hooks de ítems reciben context con context.player, context.item y (cuando corresponde) context.event.
La columna de notas indica la familia de eventos Bukkit subyacente. El wrapper de Lua no expone campos específicos de Bukkit sin procesar como target, block, projectile o item; usa context.player, context.event.player y las consultas auxiliares de entidades/mundo cuando necesites context adicional.
Hooks de Combate
| Hook | Se dispara cuando | Notas |
|---|---|---|
on_attack_entity | El jugador ataca a una entidad mientras sostiene el ítem | context.event es el evento de daño |
on_kill_entity | El jugador mata a una entidad mientras sostiene el ítem | context.event es el evento de muerte |
on_take_damage | El jugador recibe daño mientras el ítem está equipado | context.event es el evento de daño |
on_shield_block | El jugador bloquea daño con un escudo | context.event es el evento de daño |
on_shoot_bow | El jugador dispara un arco | context.event es el evento de disparo de arco |
on_projectile_hit | Un proyectil disparado por el jugador golpea algo | context.event es el evento de impacto de proyectil |
on_projectile_launch | El jugador lanza un proyectil | context.event es el evento de lanzamiento de proyectil |
Hooks de Interacción
| Hook | Se dispara cuando | Notas |
|---|---|---|
on_right_click | El jugador hace clic derecho mientras sostiene el ítem | context.event es el evento de interacción |
on_left_click | El jugador hace clic izquierdo mientras sostiene el ítem | context.event es el evento de interacción |
on_shift_right_click | El jugador hace shift+clic derecho mientras sostiene el ítem | context.event es el evento de interacción |
on_shift_left_click | El jugador hace shift+clic izquierdo mientras sostiene el ítem | context.event es el evento de interacción |
on_interact_entity | El jugador hace clic derecho en una entidad mientras sostiene el ítem | context.event es el evento de interacción con entidad |
Hooks de Equipamiento
| Hook | Se dispara cuando | Notas |
|---|---|---|
on_equip | El ítem se equipa (se mueve a una ranura activa) | Buen lugar para inicializar el estado |
on_unequip | El ítem se desequipa (se saca de una ranura activa) | Buen lugar para hacer limpieza |
on_swap_hands | El jugador intercambia el ítem entre la mano principal y la secundaria | context.event es el evento de intercambio |
on_drop | El jugador suelta el ítem | context.event es el evento de soltar |
Hooks de Utilidad
| Hook | Se dispara cuando | Notas |
|---|---|---|
on_break_block | El jugador rompe un bloque mientras sostiene el ítem | context.event es el evento de rotura de bloque |
on_consume | El jugador consume el ítem (comida/poción) | context.event es el evento de consumo |
on_item_damage | El ítem sufre daño de durabilidad | context.event es el evento de daño de ítem |
on_fish | El jugador usa una caña de pescar | context.event es el evento de pesca |
on_death | El jugador muere mientras el ítem está equipado | context.event es el evento de muerte |
Hook de Ciclo de Vida
| Hook | Se dispara cuando | Notas |
|---|---|---|
on_game_tick | Cada tick del servidor mientras el ítem está equipado | Úsalo con moderación -- se ejecuta 20 veces por segundo |
Contrato Mínimo del Archivo
Cada script Lua de prop debe hacer return de una tabla.
Campos de Nivel Superior Obligatorios y Opcionales
| Campo | Obligatorio | Tipo | Notas |
|---|---|---|---|
api_version | Sí | Number | Actualmente debe ser 1 |
priority | No | Number | Se valida si está presente, pero FMM actualmente no ordena los scripts por él. Los props se ejecutan en el orden de la lista scripts:; los ítems vinculan solo el primer script válido |
| claves de hook soportadas | No | Function | Debe usar uno de los nombres exactos de hook listados en la Referencia de Hooks |
Reglas de Validación
- El archivo debe devolver una tabla.
api_versiones obligatorio y actualmente debe ser1.prioritydebe ser numérico si está presente.- Cada clave de nivel superior adicional debe ser un nombre de hook soportado.
- Cada clave de hook debe apuntar a una función.
- Las claves de nivel superior desconocidas son rechazadas.
priority es útil para mantener los scripts portables entre runtimes basados en MagmaCore, pero el orden de ejecución actual de FreeMinecraftModels lo dicta la configuración. Coloca los scripts de props en el orden en que quieres que se ejecuten dentro de la lista scripts: del modelo.
Las funciones auxiliares y las constantes locales deben estar encima del return final, no dentro de la tabla devuelta.
Tu Primer Script de Prop Funcional, Paso a Paso
Antes del Paso 1: Configurar la Config
- Coloca tu archivo de modelo (ej.
my_prop.fmmodel) enplugins/FreeMinecraftModels/models/ - Genera el prop una vez para generar la configuración
.yml - Crea tu archivo de script en
plugins/FreeMinecraftModels/scripts/first_test.lua - Edita
plugins/FreeMinecraftModels/models/my_prop.yml:
isEnabled: true
scripts:
- first_test.lua
- Vuelve a generar el prop o recarga el servidor
Paso 1: Hacer que el Archivo se Cargue
return {
api_version = 1,
on_spawn = function(context)
end
}
Si esto se carga sin errores en la consola, has demostrado:
- El archivo es Lua válido
- FMM lo encontró en la carpeta
scripts/ - La configuración lo referencia correctamente
- La forma de la tabla devuelta es correcta
Paso 2: Hacer que el Prop Haga Algo Visible
return {
api_version = 1,
on_spawn = function(context)
context.log:info("Prop script loaded for: " .. (context.prop.model_id or "unknown"))
end
}
Revisa la consola del servidor. Si ves el mensaje de log, tu hook se está ejecutando.
Paso 3: Reaccionar al Clic de un Jugador
return {
api_version = 1,
on_right_click = function(context)
context.log:info("Prop was right-clicked!")
end
}
Haz clic derecho en el prop en el juego. Si la consola muestra el mensaje, el hook de clic está funcionando.
Paso 4: Cancelar el Daño para Hacer el Prop Invulnerable
return {
api_version = 1,
on_left_click = function(context)
if context.event then
context.event.cancel()
end
end
}
Este es el patrón utilizado por el script predefinido invulnerable.lua. Cancela el evento de daño para que el armor stand que respalda al prop no pueda ser destruido.
Paso 5: Reproducir una Animación al Hacer Clic
return {
api_version = 1,
on_right_click = function(context)
context.prop:play_animation("open", true, false)
end
}
Esto reproduce la animación "open" en el modelo del prop, mezclada y sin bucle.
¿Qué Es context?
Cada función de hook recibe un argumento llamado context. Piensa en él como una caja de herramientas que FMM te entrega cada vez que algo sucede -- contiene todo lo que necesitas para interactuar con el prop, el mundo, las zonas y más.
Tú no creas context -- FMM lo crea y lo pasa a tu hook. Para los detalles completos de las APIs de context compartidas (context.state, context.log, context.cooldowns, context.scheduler, context.world, context.zones), consulta la página del Motor de Scripting Lua de MagmaCore.
APIs Clave de context
Aquí tienes un resumen de lo que está disponible. Para detalles completos, consulta API de Props.
-
context.prop-- (Solo scripts de props) La entidad del prop. Proporcionamodel_id,current_location,play_animation()ystop_animation(). -
context.item-- (Solo scripts de ítems) El ítem personalizado. Proporcionaid,material(),get_amount(),set_amount(),consume(),get_uses(),set_uses(),get_name(),set_name(),get_lore(),set_lore(),get_durability(),get_durability_percentage(),use_durability()yuse_durability_percentage(). Consulta API de Props e Ítems para todos los detalles. -
context.player-- El jugador en los hooks impulsados por un jugador. Los scripts de ítems lo resuelven a partir del portador del ítem; los hooks de clic de props y los hooks genéricos de zona lo resuelven a partir del jugador que los dispara. Esnilen los hooks de ciclo de vida de props, en los callbacks programados de props y en los hooks que no involucran a un jugador. -
context.event-- Un pequeño wrapper del evento Bukkit o del actor jugador que activó este hook. Disponible en los hooks de clic, combate, interacción y zona genéricos. Proporcionaevent.player,is_cancelledy, cuando el evento Bukkit subyacente es cancelable,cancel()/uncancel(); no expone campos específicos de Bukkit comotarget,block,projectileoitem. Esnilen los hooks que no tienen evento ni actor jugador (comoon_spawn,on_game_tickyon_equip). -
context.state-- Una tabla Lua simple que persiste durante la vida de la instancia del script. Consulta context.state. -
context.cooldowns-- Auxiliares de cooldown locales y globales. Usacontext.cooldowns:check_local("key", ticks)para cooldowns normales por script. Consulta context.cooldowns. -
context.log-- Registro en consola. Consulta context.log. -
context.scheduler-- Tareas diferidas y repetitivas. Consulta context.scheduler. -
context.world-- Interacción con el mundo: partículas, sonidos, consultas de bloques, rayos, entidades cercanas. Consulta context.world. -
context.zones-- Creación y vigilancia de zonas espaciales (esferas, cilindros, cuboides). Consulta context.zones.
Sintaxis de Métodos: : vs .
Para una explicación de la sintaxis de métodos : frente a . en Lua, consulta la página del Motor de Scripting Lua de MagmaCore. La API de FMM acepta ambas formas.
Plantillas Listas para Copiar y Pegar
Script de Prop Válido Más Pequeño
return {
api_version = 1,
on_spawn = function(context)
end
}
Plantilla de Prop Invulnerable
return {
api_version = 1,
on_left_click = function(context)
if context.event then
context.event.cancel()
end
end
}
Plantilla de Prop Interactivo
return {
api_version = 1,
on_spawn = function(context)
context.state.is_active = false
end,
on_right_click = function(context)
context.state.is_active = not context.state.is_active
if context.state.is_active then
context.prop:play_animation("activate", true, true)
else
context.prop:stop_animation()
end
end
}
Script de Ítem Válido Más Pequeño
return {
api_version = 1,
on_equip = function(context)
end
}
Plantilla de Ítem con Acción de Clic Derecho
return {
api_version = 1,
on_right_click = function(context)
if not context.cooldowns:check_local("activate", 40) then return end
-- Your action here
context.player:send_message("&aItem activated!")
end
}
Disposición de Archivo Más Grande
local ANIMATION_NAME = "idle"
local function do_something(context)
context.log:info("Doing something!")
end
return {
api_version = 1,
priority = 0,
on_spawn = function(context)
context.state.task_id = nil
end,
on_right_click = function(context)
do_something(context)
end,
on_destroy = function(context)
if context.state.task_id ~= nil then
context.scheduler:cancel(context.state.task_id)
end
end
}
Primer Flujo de Trabajo Real
Al construir un script de prop completamente nuevo, usa este orden:
- Crea el archivo
.luay haz queon_spawnfuncione. - Agrega el nombre del archivo de script a la configuración
.ymldel prop. - Cambia al hook que realmente deseas (ej.
on_right_click). - Agrega un mensaje de log primero, antes de animaciones o efectos.
- Agrega un efecto real (animación, sonido, partícula).
- Solo después de eso, agrega funciones auxiliares, state, lógica de scheduler o zonas.
Ese orden facilita enormemente la depuración porque solo cambia una cosa a la vez.
Scripts Predefinidos
FMM viene con cuatro scripts Lua predefinidos:
invulnerable.lua-- Cancela los eventos de daño por clic izquierdo, haciendo el prop indestructible. Este es el script de prop útil más simple.pickupable.lua-- Permite a los jugadores recoger un prop golpeándolo tres veces. Cada golpe reproduce una animación de daño en el prop, y al tercer golpe el prop se elimina y suelta su ítem de colocación para que el jugador lo recoja.storage_double.lua-- Convierte un prop en un cofre doble (54 ranuras). El clic derecho abre una GUI de inventario persistente. Reproduce animaciones y sonidos de apertura/cierre. El contenido se guarda en el prop y sobrevive a los reinicios del servidor. Al destruirlo, todo el contenido se suelta.storage_single.lua-- Igual questorage_double, pero con 3 filas (27 ranuras) en lugar de 6.
Puedes encontrar más ejemplos en la página Ejemplos y Patrones.
Lua Sandbox
Los scripts de props y de ítems se ejecutan dentro del mismo entorno LuaJ sandboxed que EliteMobs. Las restricciones de la sandbox son idénticas. Para la lista completa de globals eliminados y funciones de la biblioteca estándar disponibles, consulta la página del Motor de Scripting Lua de MagmaCore.
Próximos Pasos
- API de Props e Ítems -- referencia completa de
context.prop,context.item,context.event,context.world,context.zonesycontext.scheduler - Ejemplos y Patrones -- scripts funcionales completos para props e ítems con explicaciones
- Solución de Problemas -- problemas comunes, consejos de depuración y una lista de verificación QC
Si también escribes poderes Lua de jefe para EliteMobs, la sandbox, api_version, la tabla de estado, los conceptos de cooldown y la estructura basada en hooks te resultarán familiares, pero el context de jefe usa nombres de métodos específicos de EliteMobs. Consulta la documentación Lua de EliteMobs para las APIs exactas de jefes.