mirror of
https://github.com/zellij-org/zellij.git
synced 2024-12-26 18:55:26 +03:00
Merge pull request #600 from a-kenji/layout-command
Add commands to layout
This commit is contained in:
commit
0ab00e2c6c
20
example/run_htop_layout.yaml
Normal file
20
example/run_htop_layout.yaml
Normal file
@ -0,0 +1,20 @@
|
||||
---
|
||||
direction: Vertical
|
||||
parts:
|
||||
- direction: Horizontal
|
||||
split_size:
|
||||
Percent: 50
|
||||
parts:
|
||||
- direction: Vertical
|
||||
split_size:
|
||||
Percent: 50
|
||||
- direction: Vertical
|
||||
split_size:
|
||||
Percent: 50
|
||||
run:
|
||||
command: {cmd: htop}
|
||||
- direction: Horizontal
|
||||
split_size:
|
||||
Percent: 50
|
||||
run:
|
||||
command: {cmd: htop}
|
30
example/run_htop_layout_with_plugins.yaml
Normal file
30
example/run_htop_layout_with_plugins.yaml
Normal file
@ -0,0 +1,30 @@
|
||||
---
|
||||
direction: Horizontal
|
||||
parts:
|
||||
- direction: Vertical
|
||||
split_size:
|
||||
Fixed: 1
|
||||
run:
|
||||
plugin: tab-bar
|
||||
- direction: Vertical
|
||||
parts:
|
||||
- direction: Vertical
|
||||
parts:
|
||||
- direction: Vertical
|
||||
split_size:
|
||||
Percent: 50
|
||||
run:
|
||||
command: {cmd: htop}
|
||||
- direction: Vertical
|
||||
split_size:
|
||||
Percent: 50
|
||||
run:
|
||||
command: {cmd: htop, args: ["-C"]}
|
||||
- direction: Vertical
|
||||
split_size:
|
||||
Fixed: 5
|
||||
- direction: Vertical
|
||||
split_size:
|
||||
Fixed: 2
|
||||
run:
|
||||
plugin: status-bar
|
@ -1,11 +1,3 @@
|
||||
use zellij_utils::async_std;
|
||||
|
||||
use async_std::future::timeout as async_timeout;
|
||||
use async_std::task::{self, JoinHandle};
|
||||
use std::collections::HashMap;
|
||||
use std::os::unix::io::RawFd;
|
||||
use std::time::{Duration, Instant};
|
||||
|
||||
use crate::{
|
||||
os_input_output::{AsyncReader, Pid, ServerOsApi},
|
||||
panes::PaneId,
|
||||
@ -14,9 +6,22 @@ use crate::{
|
||||
wasm_vm::PluginInstruction,
|
||||
ServerInstruction,
|
||||
};
|
||||
use async_std::{
|
||||
future::timeout as async_timeout,
|
||||
task::{self, JoinHandle},
|
||||
};
|
||||
use std::{
|
||||
collections::HashMap,
|
||||
os::unix::io::RawFd,
|
||||
time::{Duration, Instant},
|
||||
};
|
||||
use zellij_utils::{
|
||||
async_std,
|
||||
errors::{get_current_ctx, ContextType, PtyContext},
|
||||
input::{command::TerminalAction, layout::Layout},
|
||||
input::{
|
||||
command::TerminalAction,
|
||||
layout::{Layout, Run},
|
||||
},
|
||||
logging::debug_to_file,
|
||||
};
|
||||
|
||||
@ -236,20 +241,37 @@ impl Pty {
|
||||
pub fn spawn_terminals_for_layout(
|
||||
&mut self,
|
||||
layout: Layout,
|
||||
terminal_action: Option<TerminalAction>,
|
||||
default_shell: Option<TerminalAction>,
|
||||
) {
|
||||
let total_panes = layout.total_terminal_panes();
|
||||
let extracted_run_instructions = layout.extract_run_instructions();
|
||||
let mut new_pane_pids = vec![];
|
||||
for _ in 0..total_panes {
|
||||
for run_instruction in extracted_run_instructions {
|
||||
match run_instruction {
|
||||
Some(Run::Command(command)) => {
|
||||
let cmd = TerminalAction::RunCommand(command);
|
||||
let (pid_primary, pid_secondary): (RawFd, Pid) = self
|
||||
.bus
|
||||
.os_input
|
||||
.as_mut()
|
||||
.unwrap()
|
||||
.spawn_terminal(terminal_action.clone());
|
||||
.spawn_terminal(Some(cmd));
|
||||
self.id_to_child_pid.insert(pid_primary, pid_secondary);
|
||||
new_pane_pids.push(pid_primary);
|
||||
}
|
||||
None => {
|
||||
let (pid_primary, pid_secondary): (RawFd, Pid) = self
|
||||
.bus
|
||||
.os_input
|
||||
.as_mut()
|
||||
.unwrap()
|
||||
.spawn_terminal(default_shell.clone());
|
||||
self.id_to_child_pid.insert(pid_primary, pid_secondary);
|
||||
new_pane_pids.push(pid_primary);
|
||||
}
|
||||
// Investigate moving plugin loading to here.
|
||||
Some(Run::Plugin(_)) => {}
|
||||
}
|
||||
}
|
||||
self.bus
|
||||
.senders
|
||||
.send_to_screen(ScreenInstruction::ApplyLayout(
|
||||
|
@ -26,7 +26,10 @@ use std::{
|
||||
};
|
||||
use zellij_tile::data::{Event, InputMode, ModeInfo, Palette};
|
||||
use zellij_utils::{
|
||||
input::{layout::Layout, parse_keys},
|
||||
input::{
|
||||
layout::{Layout, Run},
|
||||
parse_keys,
|
||||
},
|
||||
pane_size::PositionAndSize,
|
||||
shared::adjust_to_size,
|
||||
};
|
||||
@ -338,7 +341,7 @@ impl Tab {
|
||||
let mut new_pids = new_pids.iter();
|
||||
for (layout, position_and_size) in positions_and_size {
|
||||
// A plugin pane
|
||||
if let Some(plugin) = &layout.plugin {
|
||||
if let Some(Run::Plugin(Some(plugin))) = &layout.run {
|
||||
let (pid_tx, pid_rx) = channel();
|
||||
self.senders
|
||||
.send_to_plugin(PluginInstruction::Load(pid_tx, plugin.clone()))
|
||||
|
@ -4,9 +4,11 @@ parts:
|
||||
- direction: Vertical
|
||||
split_size:
|
||||
Fixed: 1
|
||||
run:
|
||||
plugin: tab-bar
|
||||
- direction: Vertical
|
||||
- direction: Vertical
|
||||
split_size:
|
||||
Fixed: 2
|
||||
run:
|
||||
plugin: status-bar
|
||||
|
@ -4,5 +4,6 @@ parts:
|
||||
- direction: Vertical
|
||||
split_size:
|
||||
Fixed: 1
|
||||
run:
|
||||
plugin: tab-bar
|
||||
- direction: Vertical
|
||||
|
@ -4,15 +4,18 @@ parts:
|
||||
- direction: Vertical
|
||||
split_size:
|
||||
Fixed: 1
|
||||
run:
|
||||
plugin: tab-bar
|
||||
- direction: Vertical
|
||||
parts:
|
||||
- direction: Horizontal
|
||||
split_size:
|
||||
Percent: 20
|
||||
run:
|
||||
plugin: strider
|
||||
- direction: Horizontal
|
||||
- direction: Vertical
|
||||
split_size:
|
||||
Fixed: 2
|
||||
run:
|
||||
plugin: status-bar
|
||||
|
@ -11,6 +11,7 @@ pub enum TerminalAction {
|
||||
|
||||
#[derive(Clone, Debug, Deserialize, Default, Serialize, PartialEq, Eq)]
|
||||
pub struct RunCommand {
|
||||
#[serde(alias = "cmd")]
|
||||
pub command: PathBuf,
|
||||
#[serde(default)]
|
||||
pub args: Vec<String>,
|
||||
|
@ -8,7 +8,11 @@
|
||||
// place.
|
||||
// If plugins should be able to depend on the layout system
|
||||
// then [`zellij-utils`] could be a proper place.
|
||||
use crate::{input::config::ConfigError, pane_size::PositionAndSize, setup};
|
||||
use crate::{
|
||||
input::{command::RunCommand, config::ConfigError},
|
||||
pane_size::PositionAndSize,
|
||||
setup,
|
||||
};
|
||||
use crate::{serde, serde_yaml};
|
||||
|
||||
use serde::{Deserialize, Serialize};
|
||||
@ -29,6 +33,15 @@ pub enum SplitSize {
|
||||
Fixed(u16), // An absolute number of columns or rows
|
||||
}
|
||||
|
||||
#[derive(Debug, Serialize, Deserialize, Clone)]
|
||||
#[serde(crate = "self::serde")]
|
||||
pub enum Run {
|
||||
#[serde(rename = "plugin")]
|
||||
Plugin(Option<PathBuf>),
|
||||
#[serde(rename = "command")]
|
||||
Command(RunCommand),
|
||||
}
|
||||
|
||||
#[derive(Debug, Serialize, Deserialize, Clone)]
|
||||
#[serde(crate = "self::serde")]
|
||||
pub struct Layout {
|
||||
@ -36,7 +49,7 @@ pub struct Layout {
|
||||
#[serde(default)]
|
||||
pub parts: Vec<Layout>,
|
||||
pub split_size: Option<SplitSize>,
|
||||
pub plugin: Option<PathBuf>,
|
||||
pub run: Option<Run>,
|
||||
}
|
||||
|
||||
type LayoutResult = Result<Layout, ConfigError>;
|
||||
@ -127,13 +140,28 @@ impl Layout {
|
||||
let mut total_panes = 0;
|
||||
total_panes += self.parts.len();
|
||||
for part in self.parts.iter() {
|
||||
if part.plugin.is_none() {
|
||||
match part.run {
|
||||
Some(Run::Command(_)) | None => {
|
||||
total_panes += part.total_terminal_panes();
|
||||
}
|
||||
Some(Run::Plugin(_)) => {}
|
||||
}
|
||||
}
|
||||
total_panes
|
||||
}
|
||||
|
||||
pub fn extract_run_instructions(&self) -> Vec<Option<Run>> {
|
||||
let mut run_instructions = vec![];
|
||||
if self.parts.is_empty() {
|
||||
run_instructions.push(self.run.clone());
|
||||
}
|
||||
for part in self.parts.iter() {
|
||||
let mut current_runnables = part.extract_run_instructions();
|
||||
run_instructions.append(&mut current_runnables);
|
||||
}
|
||||
run_instructions
|
||||
}
|
||||
|
||||
pub fn position_panes_in_space(
|
||||
&self,
|
||||
space: &PositionAndSize,
|
||||
|
Loading…
Reference in New Issue
Block a user