Allow defining commands in Lua, and executing them.
This commit is contained in:
parent
fae004f76c
commit
c2bd680299
@ -4,6 +4,15 @@ use crate::{
|
||||
echo_to_term_frame, lua_state::LuaState, parsing::parse_commands, GlobalCell, TermFrame,
|
||||
};
|
||||
|
||||
fn debrace(inp: &str) -> &str {
|
||||
let v = inp.trim();
|
||||
if v.starts_with("{") && v.ends_with("}") {
|
||||
&v[1..(v.len() - 1)]
|
||||
} else {
|
||||
v
|
||||
}
|
||||
}
|
||||
|
||||
fn reentrant_command_handler(
|
||||
lua_state: &mut LuaState,
|
||||
globals: &GlobalCell,
|
||||
@ -16,14 +25,25 @@ fn reentrant_command_handler(
|
||||
match command.split_out_command() {
|
||||
None => (),
|
||||
Some((cmd, rest)) => {
|
||||
if cmd.starts_with('#') {
|
||||
if cmd == "##" {
|
||||
match lua_state.execute(&join(rest.arguments.iter(), " ")) {
|
||||
match lua_state.execute(debrace(&join(rest.arguments.iter(), " "))) {
|
||||
Ok(()) => (),
|
||||
Err(msg) => {
|
||||
echo_to_term_frame(globals, term_frame, &format!("{}\r\n", msg))
|
||||
.unwrap_or(())
|
||||
}
|
||||
}
|
||||
} else {
|
||||
let cmd = &cmd[1..];
|
||||
match lua_state.execute_command(cmd, &rest.arguments) {
|
||||
Ok(()) => (),
|
||||
Err(msg) => {
|
||||
echo_to_term_frame(globals, term_frame, &format!("{}\r\n", msg))
|
||||
.unwrap_or(())
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1,11 +1,11 @@
|
||||
use anyhow::Error;
|
||||
use piccolo::{
|
||||
Callback, Closure, Context, Executor, FromValue, Function, IntoValue, Lua, StashedExecutor,
|
||||
StaticError, Table,
|
||||
StaticError, Table, Value, Variadic,
|
||||
};
|
||||
|
||||
use crate::{echo_to_term_frame, GlobalCell, TermFrame};
|
||||
use std::str;
|
||||
use std::{collections::VecDeque, str};
|
||||
|
||||
pub struct LuaState {
|
||||
pub interp: Lua,
|
||||
@ -48,6 +48,35 @@ impl LuaState {
|
||||
.execute::<()>(&self.exec)
|
||||
.map_err(|err| format!("{}", err))
|
||||
}
|
||||
|
||||
pub fn execute_command(
|
||||
&mut self,
|
||||
command: &str,
|
||||
arguments: &VecDeque<&str>,
|
||||
) -> Result<(), String> {
|
||||
self.interp
|
||||
.try_enter(|ctx| {
|
||||
let commands =
|
||||
Table::from_value(ctx, ctx.get_global(ctx.intern_static(b"commands")))?;
|
||||
let command_fn =
|
||||
Function::from_value(ctx, commands.get(ctx, ctx.intern(command.as_bytes())))?;
|
||||
ctx.fetch(&self.exec).restart(
|
||||
ctx,
|
||||
command_fn,
|
||||
Variadic(
|
||||
arguments
|
||||
.iter()
|
||||
.map(|s| ctx.intern(s.as_bytes()).into())
|
||||
.collect::<Vec<Value>>(),
|
||||
),
|
||||
);
|
||||
Ok(())
|
||||
})
|
||||
.map_err(|err| format!("{}", err))?;
|
||||
self.interp
|
||||
.execute::<()>(&self.exec)
|
||||
.map_err(|err| format!("{}", err))
|
||||
}
|
||||
}
|
||||
|
||||
pub fn install_lua_globals(global: &GlobalCell) -> Result<(), String> {
|
||||
@ -105,8 +134,14 @@ fn echo_frame<'gc>(ctx: Context<'gc>, _global: GlobalCell) -> Callback<'gc> {
|
||||
let commands: Table<'gc> =
|
||||
Table::from_value(ctx, ctx.get_global(ctx.intern_static(b"commands")))?;
|
||||
let function = Function::from_value(ctx, commands.get(ctx, "echo_frame_raw"))?;
|
||||
let message: piccolo::Value = stack.from_back(ctx)?;
|
||||
let message = ctx.intern(&format!("{}\r\n", message).as_bytes());
|
||||
let frame_no: Value = stack.pop_front();
|
||||
let all_parts: Vec<String> = stack
|
||||
.consume::<Variadic<Vec<Value>>>(ctx)?
|
||||
.into_iter()
|
||||
.map(|v| format!("{}", v))
|
||||
.collect();
|
||||
stack.push_front(frame_no);
|
||||
let message = ctx.intern((all_parts.join(" ") + "\r\n").as_bytes());
|
||||
stack.push_back(message.into());
|
||||
Ok(piccolo::CallbackReturn::Call {
|
||||
function,
|
||||
|
@ -121,8 +121,7 @@ fn get_or_make_term_frame<'a>(
|
||||
)
|
||||
}),
|
||||
initial_size,
|
||||
)
|
||||
.into(),
|
||||
),
|
||||
retained_closures: None,
|
||||
};
|
||||
|
||||
@ -207,7 +206,7 @@ pub fn echo_to_term_frame(
|
||||
.frame_registry
|
||||
.borrow()
|
||||
.get(frame_id)
|
||||
.ok_or_else(|| "Attempt to echo to frame that doesn't exist.")?
|
||||
.ok_or("Attempt to echo to frame that doesn't exist.")?
|
||||
.term
|
||||
.write(message);
|
||||
Ok(())
|
||||
|
Loading…
Reference in New Issue
Block a user