mirror of
https://github.com/redstrate/Kawari.git
synced 2025-06-30 11:47:45 +00:00
Allow reloading Global.lua with the new !reload debug command
Scripts are normally loaded when they are needed, with the exception of Global.lua that's only loaded once at start-up. But now you can reload it in-game with the !reload command, which should make event and command scripting way less of a hassle.
This commit is contained in:
parent
0c967f8a56
commit
f07d16b949
7 changed files with 86 additions and 57 deletions
3
USAGE.md
3
USAGE.md
|
@ -111,7 +111,8 @@ These special debug commands start with `!` and are custom to Kawari.
|
||||||
* `!unlockaction <id>`: Unlock an action, for example: `1` for Return and `4` for Teleport.
|
* `!unlockaction <id>`: Unlock an action, for example: `1` for Return and `4` for Teleport.
|
||||||
* `!equip <name>`: Forcefully equip an item, useful for bypassing class/job and other client restrictions. This will *overwrite* any item in that slot!
|
* `!equip <name>`: Forcefully equip an item, useful for bypassing class/job and other client restrictions. This will *overwrite* any item in that slot!
|
||||||
* `!nudge <distance> <up/down (optional)>`: Teleport forward, back, up or down `distance` yalms. Specifying up or down will move the player up or down instead of forward or back. Examples: `!nudge 5 up` to move up 5 yalms, `!nudge 5` to move forward 5 yalms, `!nudge -5` to move backward 5 yalms.
|
* `!nudge <distance> <up/down (optional)>`: Teleport forward, back, up or down `distance` yalms. Specifying up or down will move the player up or down instead of forward or back. Examples: `!nudge 5 up` to move up 5 yalms, `!nudge 5` to move forward 5 yalms, `!nudge -5` to move backward 5 yalms.
|
||||||
*`!festival <id1> <id2> <id3> <id4>`: Sets the festival in the current zone. Multiple festivals can be set together to create interesting effects.
|
* `!festival <id1> <id2> <id3> <id4>`: Sets the festival in the current zone. Multiple festivals can be set together to create interesting effects.
|
||||||
|
* `!reload`: Reloads `Global.lua` that is normally only loaded once at start-up.
|
||||||
|
|
||||||
### GM commands
|
### GM commands
|
||||||
|
|
||||||
|
|
|
@ -81,3 +81,4 @@ registerCommand("setspeed", "commands/debug/SetSpeed.lua")
|
||||||
registerCommand("nudge", "commands/debug/Nudge.lua")
|
registerCommand("nudge", "commands/debug/Nudge.lua")
|
||||||
registerCommand("festival", "commands/debug/Festival.lua")
|
registerCommand("festival", "commands/debug/Festival.lua")
|
||||||
registerCommand("permtest", "commands/debug/PermissionTest.lua")
|
registerCommand("permtest", "commands/debug/PermissionTest.lua")
|
||||||
|
registerCommand("reload", "commands/debug/Reload.lua")
|
||||||
|
|
6
resources/scripts/commands/debug/Reload.lua
Normal file
6
resources/scripts/commands/debug/Reload.lua
Normal file
|
@ -0,0 +1,6 @@
|
||||||
|
required_rank = GM_RANK_DEBUG
|
||||||
|
|
||||||
|
function onCommand(args, player)
|
||||||
|
player:reload_scripts()
|
||||||
|
player:send_message("Scripts reloaded!")
|
||||||
|
end
|
|
@ -20,10 +20,10 @@ use kawari::packet::oodle::OodleNetwork;
|
||||||
use kawari::packet::{
|
use kawari::packet::{
|
||||||
ConnectionType, PacketSegment, PacketState, SegmentData, SegmentType, send_keep_alive,
|
ConnectionType, PacketSegment, PacketState, SegmentData, SegmentType, send_keep_alive,
|
||||||
};
|
};
|
||||||
use kawari::world::{ChatHandler, ExtraLuaState, Zone, ZoneConnection};
|
use kawari::world::{ChatHandler, ExtraLuaState, Zone, ZoneConnection, load_global_script};
|
||||||
use kawari::world::{
|
use kawari::world::{
|
||||||
ClientHandle, EffectsBuilder, Event, FromServer, LuaPlayer, PlayerData, ServerHandle,
|
ClientHandle, Event, FromServer, LuaPlayer, PlayerData, ServerHandle, StatusEffects, ToServer,
|
||||||
StatusEffects, ToServer, WorldDatabase, handle_custom_ipc, server_main_loop,
|
WorldDatabase, handle_custom_ipc, server_main_loop,
|
||||||
};
|
};
|
||||||
|
|
||||||
use mlua::{Function, Lua};
|
use mlua::{Function, Lua};
|
||||||
|
@ -888,58 +888,8 @@ async fn main() {
|
||||||
let game_data = Arc::new(Mutex::new(GameData::new()));
|
let game_data = Arc::new(Mutex::new(GameData::new()));
|
||||||
|
|
||||||
{
|
{
|
||||||
let lua = lua.lock().unwrap();
|
let mut lua = lua.lock().unwrap();
|
||||||
|
load_global_script(&mut lua);
|
||||||
let register_action_func = lua
|
|
||||||
.create_function(|lua, (action_id, action_script): (u32, String)| {
|
|
||||||
tracing::info!("Registering {action_id} with {action_script}!");
|
|
||||||
let mut state = lua.app_data_mut::<ExtraLuaState>().unwrap();
|
|
||||||
let _ = state.action_scripts.insert(action_id, action_script);
|
|
||||||
Ok(())
|
|
||||||
})
|
|
||||||
.unwrap();
|
|
||||||
|
|
||||||
let register_event_func = lua
|
|
||||||
.create_function(|lua, (event_id, event_script): (u32, String)| {
|
|
||||||
tracing::info!("Registering {event_id} with {event_script}!");
|
|
||||||
let mut state = lua.app_data_mut::<ExtraLuaState>().unwrap();
|
|
||||||
let _ = state.event_scripts.insert(event_id, event_script);
|
|
||||||
Ok(())
|
|
||||||
})
|
|
||||||
.unwrap();
|
|
||||||
|
|
||||||
let register_command_func = lua
|
|
||||||
.create_function(|lua, (command_name, command_script): (String, String)| {
|
|
||||||
tracing::info!("Registering {command_name} with {command_script}!");
|
|
||||||
let mut state = lua.app_data_mut::<ExtraLuaState>().unwrap();
|
|
||||||
let _ = state.command_scripts.insert(command_name, command_script);
|
|
||||||
Ok(())
|
|
||||||
})
|
|
||||||
.unwrap();
|
|
||||||
|
|
||||||
lua.set_app_data(ExtraLuaState::default());
|
|
||||||
lua.globals()
|
|
||||||
.set("registerAction", register_action_func)
|
|
||||||
.unwrap();
|
|
||||||
lua.globals()
|
|
||||||
.set("registerEvent", register_event_func)
|
|
||||||
.unwrap();
|
|
||||||
lua.globals()
|
|
||||||
.set("registerCommand", register_command_func)
|
|
||||||
.unwrap();
|
|
||||||
|
|
||||||
let effectsbuilder_constructor = lua
|
|
||||||
.create_function(|_, ()| Ok(EffectsBuilder::default()))
|
|
||||||
.unwrap();
|
|
||||||
lua.globals()
|
|
||||||
.set("EffectsBuilder", effectsbuilder_constructor)
|
|
||||||
.unwrap();
|
|
||||||
|
|
||||||
let file_name = format!("{}/Global.lua", &config.world.scripts_location);
|
|
||||||
lua.load(std::fs::read(&file_name).expect("Failed to locate scripts directory!"))
|
|
||||||
.set_name("@".to_string() + &file_name)
|
|
||||||
.exec()
|
|
||||||
.unwrap();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
let (handle, _) = spawn_main_loop();
|
let (handle, _) = spawn_main_loop();
|
||||||
|
|
|
@ -34,6 +34,7 @@ use super::{
|
||||||
Actor, CharacterData, EffectsBuilder, Event, LuaPlayer, StatusEffects, ToServer, WorldDatabase,
|
Actor, CharacterData, EffectsBuilder, Event, LuaPlayer, StatusEffects, ToServer, WorldDatabase,
|
||||||
Zone,
|
Zone,
|
||||||
common::{ClientId, ServerHandle},
|
common::{ClientId, ServerHandle},
|
||||||
|
load_global_script,
|
||||||
lua::Task,
|
lua::Task,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -591,6 +592,10 @@ impl ZoneConnection {
|
||||||
Task::WarpAetheryte { aetheryte_id } => {
|
Task::WarpAetheryte { aetheryte_id } => {
|
||||||
self.warp_aetheryte(*aetheryte_id).await;
|
self.warp_aetheryte(*aetheryte_id).await;
|
||||||
}
|
}
|
||||||
|
Task::ReloadScripts => {
|
||||||
|
let mut lua = self.lua.lock().unwrap();
|
||||||
|
load_global_script(&mut lua);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
player.queued_tasks.clear();
|
player.queued_tasks.clear();
|
||||||
|
|
|
@ -5,12 +5,14 @@ use crate::{
|
||||||
ObjectId, ObjectTypeId, Position, timestamp_secs, workdefinitions::RemakeMode,
|
ObjectId, ObjectTypeId, Position, timestamp_secs, workdefinitions::RemakeMode,
|
||||||
write_quantized_rotation,
|
write_quantized_rotation,
|
||||||
},
|
},
|
||||||
|
config::get_config,
|
||||||
ipc::zone::{
|
ipc::zone::{
|
||||||
ActionEffect, ActorControlCategory, ActorControlSelf, DamageElement, DamageKind,
|
ActionEffect, ActorControlCategory, ActorControlSelf, DamageElement, DamageKind,
|
||||||
DamageType, EffectKind, EventScene, ServerZoneIpcData, ServerZoneIpcSegment, Warp,
|
DamageType, EffectKind, EventScene, ServerZoneIpcData, ServerZoneIpcSegment, Warp,
|
||||||
},
|
},
|
||||||
opcodes::ServerZoneIpcType,
|
opcodes::ServerZoneIpcType,
|
||||||
packet::{PacketSegment, SegmentData, SegmentType},
|
packet::{PacketSegment, SegmentData, SegmentType},
|
||||||
|
world::ExtraLuaState,
|
||||||
};
|
};
|
||||||
|
|
||||||
use super::{PlayerData, StatusEffects, Zone, connection::TeleportQuery};
|
use super::{PlayerData, StatusEffects, Zone, connection::TeleportQuery};
|
||||||
|
@ -23,6 +25,7 @@ pub enum Task {
|
||||||
FinishEvent { handler_id: u32 },
|
FinishEvent { handler_id: u32 },
|
||||||
SetClassJob { classjob_id: u8 },
|
SetClassJob { classjob_id: u8 },
|
||||||
WarpAetheryte { aetheryte_id: u32 },
|
WarpAetheryte { aetheryte_id: u32 },
|
||||||
|
ReloadScripts,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Default)]
|
#[derive(Default)]
|
||||||
|
@ -156,6 +159,10 @@ impl LuaPlayer {
|
||||||
fn warp_aetheryte(&mut self, aetheryte_id: u32) {
|
fn warp_aetheryte(&mut self, aetheryte_id: u32) {
|
||||||
self.queued_tasks.push(Task::WarpAetheryte { aetheryte_id });
|
self.queued_tasks.push(Task::WarpAetheryte { aetheryte_id });
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn reload_scripts(&mut self) {
|
||||||
|
self.queued_tasks.push(Task::ReloadScripts);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl UserData for LuaPlayer {
|
impl UserData for LuaPlayer {
|
||||||
|
@ -223,6 +230,10 @@ impl UserData for LuaPlayer {
|
||||||
this.warp_aetheryte(aetheryte_id);
|
this.warp_aetheryte(aetheryte_id);
|
||||||
Ok(())
|
Ok(())
|
||||||
});
|
});
|
||||||
|
methods.add_method_mut("reload_scripts", |_, this, _: ()| {
|
||||||
|
this.reload_scripts();
|
||||||
|
Ok(())
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
fn add_fields<F: UserDataFields<Self>>(fields: &mut F) {
|
fn add_fields<F: UserDataFields<Self>>(fields: &mut F) {
|
||||||
|
@ -324,3 +335,58 @@ impl FromLua for EffectsBuilder {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Loads `Global.lua`
|
||||||
|
pub fn load_global_script(lua: &mut Lua) {
|
||||||
|
let register_action_func = lua
|
||||||
|
.create_function(|lua, (action_id, action_script): (u32, String)| {
|
||||||
|
tracing::info!("Registering {action_id} with {action_script}!");
|
||||||
|
let mut state = lua.app_data_mut::<ExtraLuaState>().unwrap();
|
||||||
|
let _ = state.action_scripts.insert(action_id, action_script);
|
||||||
|
Ok(())
|
||||||
|
})
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
|
let register_event_func = lua
|
||||||
|
.create_function(|lua, (event_id, event_script): (u32, String)| {
|
||||||
|
tracing::info!("Registering {event_id} with {event_script}!");
|
||||||
|
let mut state = lua.app_data_mut::<ExtraLuaState>().unwrap();
|
||||||
|
let _ = state.event_scripts.insert(event_id, event_script);
|
||||||
|
Ok(())
|
||||||
|
})
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
|
let register_command_func = lua
|
||||||
|
.create_function(|lua, (command_name, command_script): (String, String)| {
|
||||||
|
tracing::info!("Registering {command_name} with {command_script}!");
|
||||||
|
let mut state = lua.app_data_mut::<ExtraLuaState>().unwrap();
|
||||||
|
let _ = state.command_scripts.insert(command_name, command_script);
|
||||||
|
Ok(())
|
||||||
|
})
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
|
lua.set_app_data(ExtraLuaState::default());
|
||||||
|
lua.globals()
|
||||||
|
.set("registerAction", register_action_func)
|
||||||
|
.unwrap();
|
||||||
|
lua.globals()
|
||||||
|
.set("registerEvent", register_event_func)
|
||||||
|
.unwrap();
|
||||||
|
lua.globals()
|
||||||
|
.set("registerCommand", register_command_func)
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
|
let effectsbuilder_constructor = lua
|
||||||
|
.create_function(|_, ()| Ok(EffectsBuilder::default()))
|
||||||
|
.unwrap();
|
||||||
|
lua.globals()
|
||||||
|
.set("EffectsBuilder", effectsbuilder_constructor)
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
|
let config = get_config();
|
||||||
|
let file_name = format!("{}/Global.lua", &config.world.scripts_location);
|
||||||
|
lua.load(std::fs::read(&file_name).expect("Failed to locate scripts directory!"))
|
||||||
|
.set_name("@".to_string() + &file_name)
|
||||||
|
.exec()
|
||||||
|
.unwrap();
|
||||||
|
}
|
||||||
|
|
|
@ -11,7 +11,7 @@ mod database;
|
||||||
pub use database::{CharacterData, WorldDatabase};
|
pub use database::{CharacterData, WorldDatabase};
|
||||||
|
|
||||||
mod lua;
|
mod lua;
|
||||||
pub use lua::{EffectsBuilder, LuaPlayer};
|
pub use lua::{EffectsBuilder, LuaPlayer, load_global_script};
|
||||||
|
|
||||||
mod event;
|
mod event;
|
||||||
pub use event::Event;
|
pub use event::Event;
|
||||||
|
|
Loading…
Add table
Reference in a new issue