From eb0f3b02856f279f44ca54de8ba0f5f2dec6a017 Mon Sep 17 00:00:00 2001 From: Brooks J Rady Date: Tue, 5 Jan 2021 22:41:23 +0000 Subject: [PATCH] Very borken --- Cargo.toml | 13 +- src/errors.rs | 13 +- src/layout.rs | 23 +- src/main.rs | 81 ++---- src/pty_bus.rs | 2 +- src/screen.rs | 7 +- src/tab.rs | 249 ++++++++++-------- src/terminal_pane/mod.rs | 2 + src/terminal_pane/plugin_pane.rs | 168 ++++++++++++ src/terminal_pane/terminal_pane.rs | 24 +- .../fixtures/layouts/panes-with-plugins.yaml | 3 +- src/wasm_vm.rs | 5 +- 12 files changed, 373 insertions(+), 217 deletions(-) create mode 100644 src/terminal_pane/plugin_pane.rs diff --git a/Cargo.toml b/Cargo.toml index 792792e0..3becb4da 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -21,21 +21,12 @@ termios = "0.3" unicode-truncate = "0.1.1" unicode-width = "0.1.8" vte = "0.8.0" +wasmer = "1.0.0-rc" +wasmer-wasi = "1.0.0-rc" [dependencies.async-std] version = "1.3.0" features = ["unstable"] -[dependencies.wasmer] -version = "1.0.0-rc" -optional = true - -[dependencies.wasmer-wasi] -version = "1.0.0-rc" -optional = true - -[features] -wasm-wip = ["wasmer", "wasmer-wasi"] - [dev-dependencies] insta = "0.16.1" diff --git a/src/errors.rs b/src/errors.rs index e4788e20..148d7119 100644 --- a/src/errors.rs +++ b/src/errors.rs @@ -101,7 +101,7 @@ impl Display for ErrorContext { pub enum ContextType { Screen(ScreenContext), Pty(PtyContext), - #[cfg(feature = "wasm-wip")] + Plugin(PluginContext), App(AppContext), IPCServer, @@ -117,7 +117,7 @@ impl Display for ContextType { match *self { ContextType::Screen(c) => write!(f, "{}screen_thread: {}{:?}", purple, green, c), ContextType::Pty(c) => write!(f, "{}pty_thread: {}{:?}", purple, green, c), - #[cfg(feature = "wasm-wip")] + ContextType::Plugin(c) => write!(f, "{}plugin_thread: {}{:?}", purple, green, c), ContextType::App(c) => write!(f, "{}main_thread: {}{:?}", purple, green, c), ContextType::IPCServer => write!(f, "{}ipc_server: {}AcceptInput", purple, green), @@ -225,21 +225,22 @@ impl From<&PtyInstruction> for PtyContext { } // FIXME: This whole pattern *needs* a macro eventually, it's soul-crushing to write -#[cfg(feature = "wasm-wip")] + use crate::wasm_vm::PluginInstruction; -#[cfg(feature = "wasm-wip")] + #[derive(Debug, Clone, Copy, PartialEq)] pub enum PluginContext { Load, + Draw, Unload, Quit, } -#[cfg(feature = "wasm-wip")] impl From<&PluginInstruction> for PluginContext { fn from(plugin_instruction: &PluginInstruction) -> Self { match *plugin_instruction { - PluginInstruction::Load(_) => PluginContext::Load, + PluginInstruction::Load(..) => PluginContext::Load, + PluginInstruction::Draw(..) => PluginContext::Draw, PluginInstruction::Unload(_) => PluginContext::Unload, PluginInstruction::Quit => PluginContext::Quit, } diff --git a/src/layout.rs b/src/layout.rs index 03a1cf1f..efe7bae6 100644 --- a/src/layout.rs +++ b/src/layout.rs @@ -61,8 +61,11 @@ fn split_space_to_parts_horizontally( split_parts } -fn split_space(space_to_split: &PositionAndSize, layout: &Layout) -> Vec { - let mut pane_positions: Vec = vec![]; +fn split_space( + space_to_split: &PositionAndSize, + layout: &Layout, +) -> Vec<(Layout, PositionAndSize)> { + let mut pane_positions = Vec::new(); let percentages: Vec = layout .parts .iter() @@ -88,7 +91,7 @@ fn split_space(space_to_split: &PositionAndSize, layout: &Layout) -> Vec usize { + + pub fn total_terminal_panes(&self) -> usize { let mut total_panes = 0; total_panes += self.parts.len(); for part in self.parts.iter() { - total_panes += part.total_panes(); + if part.plugin.is_none() { + total_panes += part.total_terminal_panes(); + } } total_panes } // FIXME: I probably shouldn't exist, much less with PathBuf (use &Path) - #[cfg(feature = "wasm-wip")] + pub fn list_plugins(&self) -> Vec<&PathBuf> { let mut plugins: Vec<_> = self.parts.iter().flat_map(Layout::list_plugins).collect(); if let Some(path) = &self.plugin { @@ -184,7 +190,10 @@ impl Layout { plugins } - pub fn position_panes_in_space(&self, space: &PositionAndSize) -> Vec { + pub fn position_panes_in_space( + &self, + space: &PositionAndSize, + ) -> Vec<(Layout, PositionAndSize)> { split_space(space, &self) } } diff --git a/src/main.rs b/src/main.rs index bff2f701..77d3fc5f 100644 --- a/src/main.rs +++ b/src/main.rs @@ -12,7 +12,7 @@ mod screen; mod tab; mod terminal_pane; mod utils; -#[cfg(feature = "wasm-wip")] + mod wasm_vm; use std::io::Write; @@ -160,14 +160,13 @@ pub fn start(mut os_input: Box, opts: Opt) { let mut send_pty_instructions = SenderWithContext::new(err_ctx, SenderType::Sender(send_pty_instructions)); - #[cfg(feature = "wasm-wip")] use crate::wasm_vm::PluginInstruction; - #[cfg(feature = "wasm-wip")] + let (send_plugin_instructions, receive_plugin_instructions): ( Sender<(PluginInstruction, ErrorContext)>, Receiver<(PluginInstruction, ErrorContext)>, ) = channel(); - #[cfg(feature = "wasm-wip")] + let send_plugin_instructions = SenderWithContext::new(err_ctx, SenderType::Sender(send_plugin_instructions)); @@ -200,17 +199,8 @@ pub fn start(mut os_input: Box, opts: Opt) { .name("pty".to_string()) .spawn({ let mut command_is_executing = command_is_executing.clone(); - #[cfg(feature = "wasm-wip")] - let send_plugin_instructions = send_plugin_instructions.clone(); move || { if let Some(layout) = maybe_layout { - #[cfg(feature = "wasm-wip")] - for plugin_path in layout.list_plugins() { - dbg!(send_plugin_instructions - .send(PluginInstruction::Load(plugin_path.clone()))) - .unwrap(); - } - pty_bus.spawn_terminals_for_layout(layout); } else { let pid = pty_bus.spawn_terminal(None); @@ -281,6 +271,7 @@ pub fn start(mut os_input: Box, opts: Opt) { let mut command_is_executing = command_is_executing.clone(); let os_input = os_input.clone(); let send_pty_instructions = send_pty_instructions.clone(); + let send_plugin_instructions = send_plugin_instructions.clone(); let send_app_instructions = send_app_instructions.clone(); let max_panes = opts.max_panes; @@ -288,6 +279,7 @@ pub fn start(mut os_input: Box, opts: Opt) { let mut screen = Screen::new( receive_screen_instructions, send_pty_instructions, + send_plugin_instructions, send_app_instructions, &full_screen_ws, os_input, @@ -411,14 +403,13 @@ pub fn start(mut os_input: Box, opts: Opt) { // Here be dragons! This is very much a work in progress, and isn't quite functional // yet. It's being left out of the tests because is slows them down massively (by // recompiling a WASM module for every single test). Stay tuned for more updates! - #[cfg(feature = "wasm-wip")] active_threads.push( thread::Builder::new() .name("wasm".to_string()) .spawn(move || { use crate::errors::PluginContext; use crate::wasm_vm::{mosaic_imports, wasi_stdout}; - use std::{io, collections::HashMap}; + use std::collections::HashMap; use wasmer::{ChainableNamedResolver, Instance, Module, Store, Value}; use wasmer_wasi::{Pipe, WasiState}; @@ -436,7 +427,7 @@ pub fn start(mut os_input: Box, opts: Opt) { // screen.send_app_instructions.update(err_ctx); // screen.send_pty_instructions.update(err_ctx); match event { - PluginInstruction::Load(path) => { + PluginInstruction::Load(pid_tx, path) => { // FIXME: Cache this compiled module on disk. I could use `(de)serialize_to_file()` for that let module = Module::from_file(&store, &path).unwrap(); @@ -459,50 +450,30 @@ pub fn start(mut os_input: Box, opts: Opt) { let mosaic = mosaic_imports(&store, &wasi_env); let instance = Instance::new(&module, &mosaic.chain_back(wasi)).unwrap(); - debug_log_to_file(format!("Loaded {}({}) from {}", instance.module().name().unwrap(), plugin_id, path.display())).unwrap(); - plugin_map.insert(plugin_id, instance); - plugin_id += 1; - - // FIXME: End the loading block here - - // FIXME: Yucky line - let instance = plugin_map.get(&(plugin_id - 1)).unwrap(); - let start = instance.exports.get_function("_start").unwrap(); - let handle_key = instance.exports.get_function("handle_key").unwrap(); - let draw = instance.exports.get_function("draw").unwrap(); // This eventually calls the `.init()` method start.call(&[]).unwrap(); - #[warn(clippy::never_loop)] - loop { - let (cols, rows) = (80, 24); //terminal::size()?; - draw.call(&[Value::I32(rows), Value::I32(cols)]).unwrap(); + debug_log_to_file(format!("Loaded {}({}) from {}", instance.module().name().unwrap(), plugin_id, path.display())).unwrap(); + plugin_map.insert(plugin_id, (instance, wasi_env)); + pid_tx.send(plugin_id).unwrap(); + plugin_id += 1; + } + PluginInstruction::Draw(buf_tx, pid, rows, cols) => { + let (instance, wasi_env) = plugin_map.get(&pid).unwrap(); - // Needed because raw mode doesn't implicitly return to the start of the line - write!( - io::stdout(), - "{}\n\r", - wasi_stdout(&wasi_env) - .lines() - .collect::>() - .join("\n\r") - ).unwrap(); + let draw = instance.exports.get_function("draw").unwrap(); - /* match event::read().unwrap() { - Event::Key(KeyEvent { - code: KeyCode::Char('q'), - .. - }) => break, - Event::Key(e) => { - wasi_write_string(&wasi_env, serde_json::to_string(&e).unwrap()); - handle_key.call(&[])?; - } - _ => (), - } */ - break; - } + draw.call(&[Value::I32(rows as i32), Value::I32(cols as i32)]).unwrap(); + + buf_tx.send(format!( + "{}\n\r", + wasi_stdout(&wasi_env) + .lines() + .collect::>() + .join("\n\r") + )).unwrap(); } PluginInstruction::Quit => break, i => panic!("Yo, dawg, nice job calling the wasm thread!\n {:?} is defo not implemented yet...", i), @@ -603,14 +574,14 @@ pub fn start(mut os_input: Box, opts: Opt) { AppInstruction::Exit => { let _ = send_screen_instructions.send(ScreenInstruction::Quit); let _ = send_pty_instructions.send(PtyInstruction::Quit); - #[cfg(feature = "wasm-wip")] + let _ = send_plugin_instructions.send(PluginInstruction::Quit); break; } AppInstruction::Error(backtrace) => { let _ = send_screen_instructions.send(ScreenInstruction::Quit); let _ = send_pty_instructions.send(PtyInstruction::Quit); - #[cfg(feature = "wasm-wip")] + let _ = send_plugin_instructions.send(PluginInstruction::Quit); os_input.unset_raw_mode(0); let goto_start_of_last_line = format!("\u{1b}[{};{}H", full_screen_ws.rows, 1); diff --git a/src/pty_bus.rs b/src/pty_bus.rs index 6eed4b25..4d9607d2 100644 --- a/src/pty_bus.rs +++ b/src/pty_bus.rs @@ -265,7 +265,7 @@ impl PtyBus { pid_primary } pub fn spawn_terminals_for_layout(&mut self, layout: Layout) { - let total_panes = layout.total_panes(); + let total_panes = layout.total_terminal_panes(); let mut new_pane_pids = vec![]; for _ in 0..total_panes { let (pid_primary, pid_secondary): (RawFd, RawFd) = self.os_input.spawn_terminal(None); diff --git a/src/screen.rs b/src/screen.rs index b8249a5b..a91b6811 100644 --- a/src/screen.rs +++ b/src/screen.rs @@ -2,12 +2,12 @@ use std::collections::BTreeMap; use std::os::unix::io::RawFd; use std::sync::mpsc::Receiver; -use crate::errors::ErrorContext; use crate::layout::Layout; use crate::os_input_output::OsApi; use crate::pty_bus::{PtyInstruction, VteEvent}; use crate::tab::Tab; use crate::terminal_pane::PositionAndSize; +use crate::{errors::ErrorContext, wasm_vm::PluginInstruction}; use crate::{AppInstruction, SenderWithContext}; /* @@ -55,6 +55,7 @@ pub struct Screen { max_panes: Option, tabs: BTreeMap, pub send_pty_instructions: SenderWithContext, + pub send_plugin_instructions: SenderWithContext, pub send_app_instructions: SenderWithContext, full_screen_ws: PositionAndSize, active_tab_index: Option, @@ -65,6 +66,7 @@ impl Screen { pub fn new( receive_screen_instructions: Receiver<(ScreenInstruction, ErrorContext)>, send_pty_instructions: SenderWithContext, + send_plugin_instructions: SenderWithContext, send_app_instructions: SenderWithContext, full_screen_ws: &PositionAndSize, os_api: Box, @@ -74,6 +76,7 @@ impl Screen { receiver: receive_screen_instructions, max_panes, send_pty_instructions, + send_plugin_instructions, send_app_instructions, full_screen_ws: *full_screen_ws, active_tab_index: None, @@ -88,6 +91,7 @@ impl Screen { &self.full_screen_ws, self.os_api.clone(), self.send_pty_instructions.clone(), + self.send_plugin_instructions.clone(), self.send_app_instructions.clone(), self.max_panes, Some(pane_id), @@ -181,6 +185,7 @@ impl Screen { &self.full_screen_ws, self.os_api.clone(), self.send_pty_instructions.clone(), + self.send_plugin_instructions.clone(), self.send_app_instructions.clone(), self.max_panes, None, diff --git a/src/tab.rs b/src/tab.rs index e647c8d7..02b32492 100644 --- a/src/tab.rs +++ b/src/tab.rs @@ -1,13 +1,12 @@ -use std::collections::{BTreeMap, HashSet}; -use std::io::Write; -use std::os::unix::io::RawFd; - -use crate::boundaries::Boundaries; -use crate::layout::Layout; use crate::os_input_output::OsApi; use crate::pty_bus::{PtyInstruction, VteEvent}; use crate::terminal_pane::{PositionAndSize, TerminalPane}; +use crate::{boundaries::Boundaries, terminal_pane::PluginPane}; +use crate::{layout::Layout, wasm_vm::PluginInstruction}; use crate::{AppInstruction, SenderWithContext}; +use std::collections::{BTreeMap, HashSet}; +use std::os::unix::io::RawFd; +use std::{io::Write, sync::mpsc::channel}; /* * Tab @@ -51,6 +50,7 @@ fn split_horizontally_with_gap(rect: &PositionAndSize) -> (PositionAndSize, Posi #[derive(PartialEq, Eq, Ord, PartialOrd, Hash, Clone, Copy)] enum PaneKind { Terminal(RawFd), + PluginPane(u32), // FIXME: Drop the trait object, make this a wrapper for the struct? BuiltInPane(u32), } pub struct Tab { @@ -63,6 +63,7 @@ pub struct Tab { fullscreen_is_active: bool, os_api: Box, pub send_pty_instructions: SenderWithContext, + pub send_plugin_instructions: SenderWithContext, pub send_app_instructions: SenderWithContext, } @@ -72,10 +73,7 @@ pub trait Pane { fn rows(&self) -> usize; fn columns(&self) -> usize; fn reset_size_and_position_override(&mut self); - fn change_size_p(&mut self, position_and_size: &PositionAndSize); - fn get_rows(&self) -> usize; - fn get_columns(&self) -> usize; - fn change_size(&mut self, ws: &PositionAndSize); + fn change_pos_and_size(&mut self, position_and_size: &PositionAndSize); fn override_size_and_position(&mut self, x: usize, y: usize, size: &PositionAndSize); fn handle_event(&mut self, event: VteEvent); fn cursor_coordinates(&self) -> Option<(usize, usize)>; @@ -84,7 +82,7 @@ pub trait Pane { fn position_and_size_override(&self) -> Option; fn should_render(&self) -> bool; fn set_should_render(&mut self, should_render: bool); - fn buffer_as_vte_output(&mut self) -> Option; + fn render(&mut self) -> Option; fn pid(&self) -> RawFd; fn reduce_height_down(&mut self, count: usize); fn increase_height_down(&mut self, count: usize); @@ -148,6 +146,7 @@ impl Tab { full_screen_ws: &PositionAndSize, mut os_api: Box, send_pty_instructions: SenderWithContext, + send_plugin_instructions: SenderWithContext, send_app_instructions: SenderWithContext, max_panes: Option, pane_id: Option, @@ -156,8 +155,8 @@ impl Tab { let new_terminal = TerminalPane::new(pid, *full_screen_ws, 0, 0); os_api.set_terminal_size_using_fd( new_terminal.pid, - new_terminal.get_columns() as u16, - new_terminal.get_rows() as u16, + new_terminal.columns() as u16, + new_terminal.rows() as u16, ); let mut panes: BTreeMap> = BTreeMap::new(); panes.insert(PaneKind::Terminal(pid), Box::new(new_terminal)); @@ -176,6 +175,7 @@ impl Tab { os_api, send_app_instructions, send_pty_instructions, + send_plugin_instructions, } } @@ -194,9 +194,9 @@ impl Tab { // for now the layout only supports terminal panes if let PaneKind::Terminal(pid) = pane_kind { match positions_and_size.next() { - Some(position_and_size) => { + Some((_, position_and_size)) => { terminal_pane.reset_size_and_position_override(); - terminal_pane.change_size_p(&position_and_size); + terminal_pane.change_pos_and_size(&position_and_size); self.os_api.set_terminal_size_using_fd( *pid, position_and_size.columns as u16, @@ -212,23 +212,42 @@ impl Tab { } } let mut new_pids = new_pids.iter(); - for position_and_size in positions_and_size { - // there are still panes left to fill, use the pids we received in this method - let pid = new_pids.next().unwrap(); // if this crashes it means we got less pids than there are panes in this layout - let mut new_terminal = TerminalPane::new( - *pid, - self.full_screen_ws, - position_and_size.x, - position_and_size.y, - ); - new_terminal.change_size_p(position_and_size); - self.os_api.set_terminal_size_using_fd( - new_terminal.pid, - new_terminal.get_columns() as u16, - new_terminal.get_rows() as u16, - ); - self.panes - .insert(PaneKind::Terminal(*pid), Box::new(new_terminal)); + for (layout, position_and_size) in positions_and_size { + dbg!("Loopy", &layout.plugin, position_and_size); + // Just a regular terminal + if let Some(plugin) = &layout.plugin { + dbg!("Starting here!"); + let (pid_tx, pid_rx) = channel(); + self.send_plugin_instructions + .send(PluginInstruction::Load(pid_tx, plugin.clone())) + .unwrap(); + let pid = pid_rx.recv().unwrap(); + let new_plugin = PluginPane::new( + pid, + *position_and_size, + self.send_plugin_instructions.clone(), + ); + dbg!(pid, position_and_size, plugin); + self.panes + .insert(PaneKind::PluginPane(pid), Box::new(new_plugin)); + } else { + // there are still panes left to fill, use the pids we received in this method + let pid = new_pids.next().unwrap(); // if this crashes it means we got less pids than there are panes in this layout + let mut new_terminal = TerminalPane::new( + *pid, + self.full_screen_ws, + position_and_size.x, + position_and_size.y, + ); + new_terminal.change_pos_and_size(position_and_size); + self.os_api.set_terminal_size_using_fd( + new_terminal.pid, + new_terminal.columns() as u16, + new_terminal.rows() as u16, + ); + self.panes + .insert(PaneKind::Terminal(*pid), Box::new(new_terminal)); + } } for unused_pid in new_pids { // this is a bit of a hack and happens because we don't have any central location that @@ -259,8 +278,8 @@ impl Tab { let new_terminal = TerminalPane::new(pid, self.full_screen_ws, x, y); self.os_api.set_terminal_size_using_fd( new_terminal.pid, - new_terminal.get_columns() as u16, - new_terminal.get_rows() as u16, + new_terminal.columns() as u16, + new_terminal.rows() as u16, ); self.panes .insert(PaneKind::Terminal(pid), Box::new(new_terminal)); @@ -272,8 +291,8 @@ impl Tab { (0, 0), |(current_longest_edge, current_terminal_id_to_split), id_and_terminal_to_check| { let (id_of_terminal_to_check, terminal_to_check) = id_and_terminal_to_check; - let terminal_size = (terminal_to_check.get_rows() * CURSOR_HEIGHT_WIDTH_RATIO) - * terminal_to_check.get_columns(); + let terminal_size = (terminal_to_check.rows() * CURSOR_HEIGHT_WIDTH_RATIO) + * terminal_to_check.columns(); if terminal_size > current_longest_edge { (terminal_size, id_of_terminal_to_check) } else { @@ -286,14 +305,12 @@ impl Tab { .get_mut(&PaneKind::Terminal(terminal_id_to_split)) .unwrap(); let terminal_ws = PositionAndSize { - rows: terminal_to_split.get_rows(), - columns: terminal_to_split.get_columns(), + rows: terminal_to_split.rows(), + columns: terminal_to_split.columns(), x: terminal_to_split.x(), y: terminal_to_split.y(), }; - if terminal_to_split.get_rows() * CURSOR_HEIGHT_WIDTH_RATIO - > terminal_to_split.get_columns() - { + if terminal_to_split.rows() * CURSOR_HEIGHT_WIDTH_RATIO > terminal_to_split.columns() { let (top_winsize, bottom_winsize) = split_horizontally_with_gap(&terminal_ws); let bottom_half_y = terminal_ws.y + top_winsize.rows + 1; let new_terminal = @@ -303,7 +320,7 @@ impl Tab { bottom_winsize.columns as u16, bottom_winsize.rows as u16, ); - terminal_to_split.change_size(&top_winsize); + terminal_to_split.change_pos_and_size(&top_winsize); self.panes .insert(PaneKind::Terminal(pid), Box::new(new_terminal)); self.os_api.set_terminal_size_using_fd( @@ -322,7 +339,7 @@ impl Tab { right_winsize.columns as u16, right_winsize.rows as u16, ); - terminal_to_split.change_size(&left_winszie); + terminal_to_split.change_pos_and_size(&left_winszie); self.panes .insert(PaneKind::Terminal(pid), Box::new(new_terminal)); self.os_api.set_terminal_size_using_fd( @@ -346,8 +363,8 @@ impl Tab { let new_terminal = TerminalPane::new(pid, self.full_screen_ws, x, y); self.os_api.set_terminal_size_using_fd( new_terminal.pid, - new_terminal.get_columns() as u16, - new_terminal.get_rows() as u16, + new_terminal.columns() as u16, + new_terminal.rows() as u16, ); self.panes .insert(PaneKind::Terminal(pid), Box::new(new_terminal)); @@ -358,8 +375,8 @@ impl Tab { let active_terminal = &self.get_active_terminal().unwrap(); ( PositionAndSize { - rows: active_terminal.get_rows(), - columns: active_terminal.get_columns(), + rows: active_terminal.rows(), + columns: active_terminal.columns(), x: 0, y: 0, }, @@ -383,7 +400,7 @@ impl Tab { .panes .get_mut(&PaneKind::Terminal(*active_terminal_id)) .unwrap(); - active_terminal.change_size(&top_winsize); + active_terminal.change_pos_and_size(&top_winsize); } self.panes @@ -409,8 +426,8 @@ impl Tab { let new_terminal = TerminalPane::new(pid, self.full_screen_ws, x, y); self.os_api.set_terminal_size_using_fd( new_terminal.pid, - new_terminal.get_columns() as u16, - new_terminal.get_rows() as u16, + new_terminal.columns() as u16, + new_terminal.rows() as u16, ); self.panes .insert(PaneKind::Terminal(pid), Box::new(new_terminal)); @@ -421,8 +438,8 @@ impl Tab { let active_terminal = &self.get_active_terminal().unwrap(); ( PositionAndSize { - rows: active_terminal.get_rows(), - columns: active_terminal.get_columns(), + rows: active_terminal.rows(), + columns: active_terminal.columns(), x: 0, y: 0, }, @@ -446,7 +463,7 @@ impl Tab { .panes .get_mut(&PaneKind::Terminal(*active_terminal_id)) .unwrap(); - active_terminal.change_size(&left_winszie); + active_terminal.change_pos_and_size(&left_winszie); } self.panes @@ -545,8 +562,8 @@ impl Tab { .unwrap(); self.os_api.set_terminal_size_using_fd( active_terminal_id, - active_terminal.get_columns() as u16, - active_terminal.get_rows() as u16, + active_terminal.columns() as u16, + active_terminal.rows() as u16, ); self.render(); self.toggle_fullscreen_is_active(); @@ -571,7 +588,7 @@ impl Tab { PaneKind::Terminal(pid) => { if !self.panes_to_hide.contains(pid) { boundaries.add_rect(&terminal); - if let Some(vte_output) = terminal.buffer_as_vte_output() { + if let Some(vte_output) = terminal.render() { stdout .write_all(&vte_output.as_bytes()) .expect("cannot write to stdout"); @@ -581,6 +598,16 @@ impl Tab { PaneKind::BuiltInPane(builtin_id) => { // TBD } + PaneKind::PluginPane(_) => { + if let Some(output) = terminal.render() { + write!( + stdout, + "{}\n\r", + output.lines().collect::>().join("\n\r") + ) + .unwrap(); + } + } } } @@ -634,7 +661,7 @@ impl Tab { return None; } for (pid, terminal) in self.get_terminals() { - if terminal.x() + terminal.get_columns() == terminal_to_check.x() - 1 { + if terminal.x() + terminal.columns() == terminal_to_check.x() - 1 { ids.push(pid); } } @@ -648,7 +675,7 @@ impl Tab { let mut ids = vec![]; let terminal_to_check = self.panes.get(&PaneKind::Terminal(*id)).unwrap(); for (pid, terminal) in self.get_terminals() { - if terminal.x() == terminal_to_check.x() + terminal_to_check.get_columns() + 1 { + if terminal.x() == terminal_to_check.x() + terminal_to_check.columns() + 1 { ids.push(pid); } } @@ -662,7 +689,7 @@ impl Tab { let mut ids = vec![]; let terminal_to_check = self.panes.get(&PaneKind::Terminal(*id)).unwrap(); for (pid, terminal) in self.get_terminals() { - if terminal.y() == terminal_to_check.y() + terminal_to_check.get_rows() + 1 { + if terminal.y() == terminal_to_check.y() + terminal_to_check.rows() + 1 { ids.push(pid); } } @@ -676,7 +703,7 @@ impl Tab { let mut ids = vec![]; let terminal_to_check = self.panes.get(&PaneKind::Terminal(*id)).unwrap(); for (pid, terminal) in self.get_terminals() { - if terminal.y() + terminal.get_rows() + 1 == terminal_to_check.y() { + if terminal.y() + terminal.rows() + 1 == terminal_to_check.y() { ids.push(pid); } } @@ -699,7 +726,7 @@ impl Tab { .map(|t_id| self.panes.get(&t_id).unwrap()) .filter(|terminal| { terminal.pid() != pane.pid() - && terminal.y() + terminal.get_rows() == pane.y() + pane.get_rows() + && terminal.y() + terminal.rows() == pane.y() + pane.rows() }) .collect() } @@ -709,7 +736,7 @@ impl Tab { .map(|t_id| self.panes.get(&t_id).unwrap()) .filter(|terminal| { terminal.pid() != pane.pid() - && terminal.x() + terminal.get_columns() == pane.x() + pane.get_columns() + && terminal.x() + terminal.columns() == pane.x() + pane.columns() }) .collect() } @@ -735,14 +762,14 @@ impl Tab { right_aligned_terminals.sort_by(|a, b| b.y().cmp(&a.y())); for terminal in right_aligned_terminals { let terminal_to_check = terminals.last().unwrap_or(&terminal_to_check); - if terminal.y() + terminal.get_rows() + 1 == terminal_to_check.y() { + if terminal.y() + terminal.rows() + 1 == terminal_to_check.y() { terminals.push(terminal); } } // top-most border aligned with a pane border to the right let mut top_resize_border = 0; for terminal in &terminals { - let bottom_terminal_boundary = terminal.y() + terminal.get_rows(); + let bottom_terminal_boundary = terminal.y() + terminal.rows(); if terminal_borders_to_the_right .get(&(bottom_terminal_boundary + 1)) .is_some() @@ -777,7 +804,7 @@ impl Tab { right_aligned_terminals.sort_by(|a, b| a.y().cmp(&b.y())); for terminal in right_aligned_terminals { let terminal_to_check = terminals.last().unwrap_or(&terminal_to_check); - if terminal.y() == terminal_to_check.y() + terminal_to_check.get_rows() + 1 { + if terminal.y() == terminal_to_check.y() + terminal_to_check.rows() + 1 { terminals.push(terminal); } } @@ -793,11 +820,11 @@ impl Tab { bottom_resize_border = top_terminal_boundary; } } - terminals.retain(|terminal| terminal.y() + terminal.get_rows() <= bottom_resize_border); + terminals.retain(|terminal| terminal.y() + terminal.rows() <= bottom_resize_border); // if there are no adjacent panes to resize, we use the border of the main pane we're // resizing let bottom_resize_border = if terminals.is_empty() { - terminal_to_check.y() + terminal_to_check.get_rows() + terminal_to_check.y() + terminal_to_check.rows() } else { bottom_resize_border }; @@ -819,14 +846,14 @@ impl Tab { left_aligned_terminals.sort_by(|a, b| b.y().cmp(&a.y())); for terminal in left_aligned_terminals { let terminal_to_check = terminals.last().unwrap_or(&terminal_to_check); - if terminal.y() + terminal.get_rows() + 1 == terminal_to_check.y() { + if terminal.y() + terminal.rows() + 1 == terminal_to_check.y() { terminals.push(terminal); } } // top-most border aligned with a pane border to the right let mut top_resize_border = 0; for terminal in &terminals { - let bottom_terminal_boundary = terminal.y() + terminal.get_rows(); + let bottom_terminal_boundary = terminal.y() + terminal.rows(); if terminal_borders_to_the_left .get(&(bottom_terminal_boundary + 1)) .is_some() @@ -861,7 +888,7 @@ impl Tab { left_aligned_terminals.sort_by(|a, b| a.y().cmp(&b.y())); for terminal in left_aligned_terminals { let terminal_to_check = terminals.last().unwrap_or(&terminal_to_check); - if terminal.y() == terminal_to_check.y() + terminal_to_check.get_rows() + 1 { + if terminal.y() == terminal_to_check.y() + terminal_to_check.rows() + 1 { terminals.push(terminal); } } @@ -878,13 +905,13 @@ impl Tab { } } terminals.retain(|terminal| { - // terminal.y() + terminal.get_rows() < bottom_resize_border - terminal.y() + terminal.get_rows() <= bottom_resize_border + // terminal.y() + terminal.rows() < bottom_resize_border + terminal.y() + terminal.rows() <= bottom_resize_border }); // if there are no adjacent panes to resize, we use the border of the main pane we're // resizing let bottom_resize_border = if terminals.is_empty() { - terminal_to_check.y() + terminal_to_check.get_rows() + terminal_to_check.y() + terminal_to_check.rows() } else { bottom_resize_border }; @@ -906,14 +933,14 @@ impl Tab { top_aligned_terminals.sort_by(|a, b| b.x().cmp(&a.x())); for terminal in top_aligned_terminals { let terminal_to_check = terminals.last().unwrap_or(&terminal_to_check); - if terminal.x() + terminal.get_columns() + 1 == terminal_to_check.x() { + if terminal.x() + terminal.columns() + 1 == terminal_to_check.x() { terminals.push(terminal); } } // leftmost border aligned with a pane border above let mut left_resize_border = 0; for terminal in &terminals { - let right_terminal_boundary = terminal.x() + terminal.get_columns(); + let right_terminal_boundary = terminal.x() + terminal.columns(); if terminal_borders_above .get(&(right_terminal_boundary + 1)) .is_some() @@ -945,7 +972,7 @@ impl Tab { top_aligned_terminals.sort_by(|a, b| a.x().cmp(&b.x())); for terminal in top_aligned_terminals { let terminal_to_check = terminals.last().unwrap_or(&terminal_to_check); - if terminal.x() == terminal_to_check.x() + terminal_to_check.get_columns() + 1 { + if terminal.x() == terminal_to_check.x() + terminal_to_check.columns() + 1 { terminals.push(terminal); } } @@ -961,11 +988,11 @@ impl Tab { right_resize_border = left_terminal_boundary; } } - terminals.retain(|terminal| terminal.x() + terminal.get_columns() <= right_resize_border); + terminals.retain(|terminal| terminal.x() + terminal.columns() <= right_resize_border); // if there are no adjacent panes to resize, we use the border of the main pane we're // resizing let right_resize_border = if terminals.is_empty() { - terminal_to_check.x() + terminal_to_check.get_columns() + terminal_to_check.x() + terminal_to_check.columns() } else { right_resize_border }; @@ -984,14 +1011,14 @@ impl Tab { // terminals that are next to each other up to current for terminal in bottom_aligned_terminals { let terminal_to_check = terminals.last().unwrap_or(&terminal_to_check); - if terminal.x() + terminal.get_columns() + 1 == terminal_to_check.x() { + if terminal.x() + terminal.columns() + 1 == terminal_to_check.x() { terminals.push(terminal); } } // leftmost border aligned with a pane border above let mut left_resize_border = 0; for terminal in &terminals { - let right_terminal_boundary = terminal.x() + terminal.get_columns(); + let right_terminal_boundary = terminal.x() + terminal.columns(); if terminal_borders_below .get(&(right_terminal_boundary + 1)) .is_some() @@ -1023,7 +1050,7 @@ impl Tab { // terminals that are next to each other up to current for terminal in bottom_aligned_terminals { let terminal_to_check = terminals.last().unwrap_or(&terminal_to_check); - if terminal.x() == terminal_to_check.x() + terminal_to_check.get_columns() + 1 { + if terminal.x() == terminal_to_check.x() + terminal_to_check.columns() + 1 { terminals.push(terminal); } } @@ -1039,9 +1066,9 @@ impl Tab { right_resize_border = left_terminal_boundary; } } - terminals.retain(|terminal| terminal.x() + terminal.get_columns() <= right_resize_border); + terminals.retain(|terminal| terminal.x() + terminal.columns() <= right_resize_border); let right_resize_border = if terminals.is_empty() { - terminal_to_check.x() + terminal_to_check.get_columns() + terminal_to_check.x() + terminal_to_check.columns() } else { right_resize_border }; @@ -1053,8 +1080,8 @@ impl Tab { terminal.reduce_height_down(count); self.os_api.set_terminal_size_using_fd( *id, - terminal.get_columns() as u16, - terminal.get_rows() as u16, + terminal.columns() as u16, + terminal.rows() as u16, ); } fn reduce_pane_height_up(&mut self, id: &RawFd, count: usize) { @@ -1062,8 +1089,8 @@ impl Tab { terminal.reduce_height_up(count); self.os_api.set_terminal_size_using_fd( *id, - terminal.get_columns() as u16, - terminal.get_rows() as u16, + terminal.columns() as u16, + terminal.rows() as u16, ); } fn increase_pane_height_down(&mut self, id: &RawFd, count: usize) { @@ -1071,8 +1098,8 @@ impl Tab { terminal.increase_height_down(count); self.os_api.set_terminal_size_using_fd( terminal.pid(), - terminal.get_columns() as u16, - terminal.get_rows() as u16, + terminal.columns() as u16, + terminal.rows() as u16, ); } fn increase_pane_height_up(&mut self, id: &RawFd, count: usize) { @@ -1080,8 +1107,8 @@ impl Tab { terminal.increase_height_up(count); self.os_api.set_terminal_size_using_fd( terminal.pid(), - terminal.get_columns() as u16, - terminal.get_rows() as u16, + terminal.columns() as u16, + terminal.rows() as u16, ); } fn increase_pane_width_right(&mut self, id: &RawFd, count: usize) { @@ -1089,8 +1116,8 @@ impl Tab { terminal.increase_width_right(count); self.os_api.set_terminal_size_using_fd( terminal.pid(), - terminal.get_columns() as u16, - terminal.get_rows() as u16, + terminal.columns() as u16, + terminal.rows() as u16, ); } fn increase_pane_width_left(&mut self, id: &RawFd, count: usize) { @@ -1098,8 +1125,8 @@ impl Tab { terminal.increase_width_left(count); self.os_api.set_terminal_size_using_fd( terminal.pid(), - terminal.get_columns() as u16, - terminal.get_rows() as u16, + terminal.columns() as u16, + terminal.rows() as u16, ); } fn reduce_pane_width_right(&mut self, id: &RawFd, count: usize) { @@ -1107,8 +1134,8 @@ impl Tab { terminal.reduce_width_right(count); self.os_api.set_terminal_size_using_fd( terminal.pid(), - terminal.get_columns() as u16, - terminal.get_rows() as u16, + terminal.columns() as u16, + terminal.rows() as u16, ); } fn reduce_pane_width_left(&mut self, id: &RawFd, count: usize) { @@ -1116,8 +1143,8 @@ impl Tab { terminal.reduce_width_left(count); self.os_api.set_terminal_size_using_fd( terminal.pid(), - terminal.get_columns() as u16, - terminal.get_rows() as u16, + terminal.columns() as u16, + terminal.rows() as u16, ); } fn pane_is_between_vertical_borders( @@ -1130,7 +1157,7 @@ impl Tab { .panes .get(&PaneKind::Terminal(*id)) .expect("could not find terminal to check between borders"); - terminal.x() >= left_border_x && terminal.x() + terminal.get_columns() <= right_border_x + terminal.x() >= left_border_x && terminal.x() + terminal.columns() <= right_border_x } fn pane_is_between_horizontal_borders( &self, @@ -1142,7 +1169,7 @@ impl Tab { .panes .get(&PaneKind::Terminal(*id)) .expect("could not find terminal to check between borders"); - terminal.y() >= top_border_y && terminal.y() + terminal.get_rows() <= bottom_border_y + terminal.y() >= top_border_y && terminal.y() + terminal.rows() <= bottom_border_y } fn reduce_pane_and_surroundings_up(&mut self, id: &RawFd, count: usize) { let mut terminals_below = self @@ -1352,14 +1379,14 @@ impl Tab { .panes .get(&PaneKind::Terminal(*pane_id)) .expect("pane does not exist"); - pane.y() + pane.get_rows() < self.full_screen_ws.rows + pane.y() + pane.rows() < self.full_screen_ws.rows } fn panes_exist_to_the_right(&self, pane_id: &RawFd) -> bool { let pane = self .panes .get(&PaneKind::Terminal(*pane_id)) .expect("pane does not exist"); - pane.x() + pane.get_columns() < self.full_screen_ws.columns + pane.x() + pane.columns() < self.full_screen_ws.columns } fn panes_exist_to_the_left(&self, pane_id: &RawFd) -> bool { let pane = self @@ -1564,7 +1591,7 @@ impl Tab { terminals.iter().fold(HashSet::new(), |mut borders, t| { let terminal = self.panes.get(&PaneKind::Terminal(*t)).unwrap(); borders.insert(terminal.y()); - borders.insert(terminal.y() + terminal.get_rows() + 1); // 1 for the border width + borders.insert(terminal.y() + terminal.rows() + 1); // 1 for the border width borders }) } @@ -1572,14 +1599,14 @@ impl Tab { terminals.iter().fold(HashSet::new(), |mut borders, t| { let terminal = self.panes.get(&PaneKind::Terminal(*t)).unwrap(); borders.insert(terminal.x()); - borders.insert(terminal.x() + terminal.get_columns() + 1); // 1 for the border width + borders.insert(terminal.x() + terminal.columns() + 1); // 1 for the border width borders }) } fn terminals_to_the_left_between_aligning_borders(&self, id: RawFd) -> Option> { if let Some(terminal) = &self.panes.get(&PaneKind::Terminal(id)) { let upper_close_border = terminal.y(); - let lower_close_border = terminal.y() + terminal.get_rows() + 1; + let lower_close_border = terminal.y() + terminal.rows() + 1; if let Some(mut terminals_to_the_left) = self.terminal_ids_directly_left_of(&id) { let terminal_borders_to_the_left = self.horizontal_borders(&terminals_to_the_left); @@ -1602,7 +1629,7 @@ impl Tab { fn terminals_to_the_right_between_aligning_borders(&self, id: RawFd) -> Option> { if let Some(terminal) = &self.panes.get(&PaneKind::Terminal(id)) { let upper_close_border = terminal.y(); - let lower_close_border = terminal.y() + terminal.get_rows() + 1; + let lower_close_border = terminal.y() + terminal.rows() + 1; if let Some(mut terminals_to_the_right) = self.terminal_ids_directly_right_of(&id) { let terminal_borders_to_the_right = @@ -1626,7 +1653,7 @@ impl Tab { fn terminals_above_between_aligning_borders(&self, id: RawFd) -> Option> { if let Some(terminal) = &self.panes.get(&PaneKind::Terminal(id)) { let left_close_border = terminal.x(); - let right_close_border = terminal.x() + terminal.get_columns() + 1; + let right_close_border = terminal.x() + terminal.columns() + 1; if let Some(mut terminals_above) = self.terminal_ids_directly_above(&id) { let terminal_borders_above = self.vertical_borders(&terminals_above); @@ -1649,7 +1676,7 @@ impl Tab { fn terminals_below_between_aligning_borders(&self, id: RawFd) -> Option> { if let Some(terminal) = &self.panes.get(&PaneKind::Terminal(id)) { let left_close_border = terminal.x(); - let right_close_border = terminal.x() + terminal.get_columns() + 1; + let right_close_border = terminal.x() + terminal.columns() + 1; if let Some(mut terminals_below) = self.terminal_ids_directly_below(&id) { let terminal_borders_below = self.vertical_borders(&terminals_below); @@ -1692,8 +1719,8 @@ impl Tab { } pub fn close_pane_without_rerender(&mut self, id: RawFd) { if let Some(terminal_to_close) = &self.panes.get(&PaneKind::Terminal(id)) { - let terminal_to_close_width = terminal_to_close.get_columns(); - let terminal_to_close_height = terminal_to_close.get_rows(); + let terminal_to_close_width = terminal_to_close.columns(); + let terminal_to_close_height = terminal_to_close.rows(); if let Some(terminals) = self.terminals_to_the_left_between_aligning_borders(id) { for terminal_id in terminals.iter() { self.increase_pane_width_right(&terminal_id, terminal_to_close_width + 1); diff --git a/src/terminal_pane/mod.rs b/src/terminal_pane/mod.rs index c6c10be2..7d478886 100644 --- a/src/terminal_pane/mod.rs +++ b/src/terminal_pane/mod.rs @@ -1,7 +1,9 @@ +mod plugin_pane; mod scroll; mod terminal_character; mod terminal_pane; +pub use plugin_pane::*; pub use scroll::*; pub use terminal_character::*; pub use terminal_pane::*; diff --git a/src/terminal_pane/plugin_pane.rs b/src/terminal_pane/plugin_pane.rs new file mode 100644 index 00000000..b3525338 --- /dev/null +++ b/src/terminal_pane/plugin_pane.rs @@ -0,0 +1,168 @@ +#![allow(clippy::clippy::if_same_then_else)] + +use crate::{pty_bus::VteEvent, tab::Pane, wasm_vm::PluginInstruction, SenderWithContext}; + +use std::{os::unix::prelude::RawFd, sync::mpsc::channel}; + +use crate::terminal_pane::PositionAndSize; + +pub struct PluginPane { + pub pid: u32, + pub should_render: bool, + pub position_and_size: PositionAndSize, + pub position_and_size_override: Option, + pub send_plugin_instructions: SenderWithContext, +} + +impl PluginPane { + pub fn new( + pid: u32, + position_and_size: PositionAndSize, + send_plugin_instructions: SenderWithContext, + ) -> Self { + Self { + pid, + should_render: true, + position_and_size, + position_and_size_override: None, + send_plugin_instructions, + } + } +} + +impl Pane for PluginPane { + // FIXME: These position and size things should all be moved to default trait implementations, + // with something like a get_pos_and_sz() method underpinning all of them. Alternatively and + // preferably, just use an enum and not a trait object + fn x(&self) -> usize { + self.position_and_size_override + .unwrap_or(self.position_and_size) + .x + } + fn y(&self) -> usize { + self.position_and_size_override + .unwrap_or(self.position_and_size) + .y + } + fn rows(&self) -> usize { + self.position_and_size_override + .unwrap_or(self.position_and_size) + .rows + } + fn columns(&self) -> usize { + self.position_and_size_override + .unwrap_or(self.position_and_size) + .columns + } + fn reset_size_and_position_override(&mut self) { + self.position_and_size_override = None; + self.should_render = true; + } + fn change_pos_and_size(&mut self, position_and_size: &PositionAndSize) { + self.position_and_size = *position_and_size; + self.should_render = true; + } + // FIXME: This is obviously a bit outdated and needs the x and y moved into `size` + fn override_size_and_position(&mut self, x: usize, y: usize, size: &PositionAndSize) { + let position_and_size_override = PositionAndSize { + x, + y, + rows: size.rows, + columns: size.columns, + }; + self.position_and_size_override = Some(position_and_size_override); + self.should_render = true; + } + fn handle_event(&mut self, event: VteEvent) { + todo!() + } + fn cursor_coordinates(&self) -> Option<(usize, usize)> { + None + } + fn adjust_input_to_terminal(&self, input_bytes: Vec) -> Vec { + todo!() // FIXME: Shouldn't need this implmented? + } + + fn position_and_size_override(&self) -> Option { + self.position_and_size_override + } + fn should_render(&self) -> bool { + self.should_render + } + fn set_should_render(&mut self, should_render: bool) { + self.should_render = should_render; + } + fn render(&mut self) -> Option { + // if self.should_render { + if true { + // while checking should_render rather than rendering each pane every time + // is more performant, it causes some problems when the pane to the left should be + // rendered and has wide characters (eg. Chinese characters or emoji) + // as a (hopefully) temporary hack, we render all panes until we find a better solution + let (buf_tx, buf_rx) = channel(); + + self.send_plugin_instructions + .send(PluginInstruction::Draw( + buf_tx, + self.pid, + self.rows(), + self.columns(), + )) + .unwrap(); + + self.should_render = false; + Some(buf_rx.recv().unwrap()) + } else { + None + } + } + // FIXME: Really shouldn't be in this trait... + fn pid(&self) -> RawFd { + todo!() + } + fn reduce_height_down(&mut self, count: usize) { + self.position_and_size.y += count; + self.position_and_size.rows -= count; + self.should_render = true; + } + fn increase_height_down(&mut self, count: usize) { + self.position_and_size.rows += count; + self.should_render = true; + } + fn increase_height_up(&mut self, count: usize) { + self.position_and_size.y -= count; + self.position_and_size.rows += count; + self.should_render = true; + } + fn reduce_height_up(&mut self, count: usize) { + self.position_and_size.rows -= count; + self.should_render = true; + } + fn reduce_width_right(&mut self, count: usize) { + self.position_and_size.x += count; + self.position_and_size.columns -= count; + self.should_render = true; + } + fn reduce_width_left(&mut self, count: usize) { + self.position_and_size.columns -= count; + self.should_render = true; + } + fn increase_width_left(&mut self, count: usize) { + self.position_and_size.x -= count; + self.position_and_size.columns += count; + self.should_render = true; + } + fn increase_width_right(&mut self, count: usize) { + self.position_and_size.columns += count; + self.should_render = true; + } + fn scroll_up(&mut self, count: usize) { + todo!() + } + fn scroll_down(&mut self, count: usize) { + todo!() + } + fn clear_scroll(&mut self) { + todo!() + } +} diff --git a/src/terminal_pane/terminal_pane.rs b/src/terminal_pane/terminal_pane.rs index b61f1536..65b33e15 100644 --- a/src/terminal_pane/terminal_pane.rs +++ b/src/terminal_pane/terminal_pane.rs @@ -58,30 +58,11 @@ impl Pane for TerminalPane { self.reflow_lines(); self.mark_for_rerender(); } - fn change_size_p(&mut self, position_and_size: &PositionAndSize) { + fn change_pos_and_size(&mut self, position_and_size: &PositionAndSize) { self.position_and_size = *position_and_size; self.reflow_lines(); self.mark_for_rerender(); } - fn get_rows(&self) -> usize { - match &self.position_and_size_override.as_ref() { - Some(position_and_size_override) => position_and_size_override.rows, - None => self.position_and_size.rows as usize, - } - } - fn get_columns(&self) -> usize { - match &self.position_and_size_override.as_ref() { - Some(position_and_size_override) => position_and_size_override.columns, - None => self.position_and_size.columns as usize, - } - } - fn change_size(&mut self, ws: &PositionAndSize) { - self.position_and_size.columns = ws.columns; - self.position_and_size.rows = ws.rows; - self.reflow_lines(); - self.mark_for_rerender(); - } - fn override_size_and_position(&mut self, x: usize, y: usize, size: &PositionAndSize) { let position_and_size_override = PositionAndSize { x, @@ -179,8 +160,7 @@ impl Pane for TerminalPane { fn set_should_render(&mut self, should_render: bool) { self.should_render = should_render; } - fn buffer_as_vte_output(&mut self) -> Option { - // TODO: rename to render + fn render(&mut self) -> Option { // if self.should_render { if true { // while checking should_render rather than rendering each pane every time diff --git a/src/tests/fixtures/layouts/panes-with-plugins.yaml b/src/tests/fixtures/layouts/panes-with-plugins.yaml index 075228fb..d64114b5 100644 --- a/src/tests/fixtures/layouts/panes-with-plugins.yaml +++ b/src/tests/fixtures/layouts/panes-with-plugins.yaml @@ -12,8 +12,7 @@ parts: Percent: 80 split_size: Percent: 80 - plugin: strider.wasm - direction: Vertical split_size: Percent: 20 - plugin: strider.wasm + #plugin: strider.wasm diff --git a/src/wasm_vm.rs b/src/wasm_vm.rs index f07d9e48..5e273255 100644 --- a/src/wasm_vm.rs +++ b/src/wasm_vm.rs @@ -1,13 +1,16 @@ use std::{ path::PathBuf, process::{Command, Stdio}, + sync::mpsc::Sender, }; use wasmer::{imports, Function, ImportObject, Store}; use wasmer_wasi::WasiEnv; #[derive(Clone, Debug)] pub enum PluginInstruction { - Load(PathBuf), + Load(Sender, PathBuf), // FIXME: Maybe send a channel handle? + // String buffer, plugin id, rows, cols + Draw(Sender, u32, usize, usize), // FIXME: This is super gross Unload(u32), Quit, }