Add --help, terminal scrollback + scrollbar, run-dialog fix, client-safe exit, true rounded corners
- -h/--help prints a full usage overview (modes, config keys, keys, mouse) - Run dialog now executes the typed command directly in the new window (previously it spawned the default shell and typed the command into it, which showed up as just an empty terminal) - Virtual terminals get vt100 scrollback (config scrollback_lines, default 1000): mouse wheel scrolls history when the app doesn't capture the mouse, arrow-key fallback on the alternate screen, any keypress jumps back to the bottom; optional scrollbar on the right border (show_scrollbar) plus configurable default_window_size - Exit triggered from a connected display client (ctrl+q / panel button) now only disconnects that client — the daemon/standalone session and its programs keep running - Windows now paint the border zone in the desktop background color so rounded corners actually look rounded instead of a filled square with an inner rounded frame; popup dialogs rounded too - Integration suite extended to 19 checks (scrollback, run dialog, client-safe exit) — all passing Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
69
src/main.rs
69
src/main.rs
@@ -28,6 +28,7 @@ enum Mode {
|
||||
Standalone,
|
||||
Daemon,
|
||||
Client(String),
|
||||
Help,
|
||||
}
|
||||
|
||||
fn parse_args() -> Mode {
|
||||
@@ -35,6 +36,7 @@ fn parse_args() -> Mode {
|
||||
let mut i = 1;
|
||||
while i < args.len() {
|
||||
match args[i].as_str() {
|
||||
"-h" | "--help" => return Mode::Help,
|
||||
"-d" | "--daemon" => return Mode::Daemon,
|
||||
"-c" | "--connect" => {
|
||||
let path = args
|
||||
@@ -56,9 +58,58 @@ fn main() -> io::Result<()> {
|
||||
Mode::Standalone => run_standalone(),
|
||||
Mode::Daemon => run_daemon_mode(),
|
||||
Mode::Client(path) => client::run(&path),
|
||||
Mode::Help => {
|
||||
print_help();
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn print_help() {
|
||||
println!(
|
||||
"\
|
||||
TUI-WM — fönsterhanterare i terminalen (tmux-liknande, med mus)
|
||||
|
||||
ANVÄNDNING:
|
||||
tui-wm [FLAGGA]
|
||||
|
||||
FLAGGOR:
|
||||
(ingen) Standalone: kör fönsterhanteraren i den här
|
||||
terminalen och starta samtidigt socket-servern.
|
||||
-d, --daemon Daemon: kör headless utan lokal rendering.
|
||||
Anslut med `tui-wm -c`. Stoppas med `pkill tui-wm`
|
||||
eller via systemd — INTE av att klienter kopplar ner.
|
||||
-c, --connect [SOCKET]
|
||||
Klient: anslut till en körande server (även över
|
||||
SSH). Tangentbord, mus (klick/scroll/drag) och
|
||||
resize vidarebefordras. Koppla ner med Ctrl+Shift+Q
|
||||
— servern och dess program fortsätter köra.
|
||||
-h, --help Visa den här hjälpen.
|
||||
|
||||
KONFIGURATION (./config.toml + panels/*.toml):
|
||||
default_shell = \"/bin/bash\" # skal för nya terminaler
|
||||
default_window_size = [82, 26] # [bredd, höjd] för nya fönster
|
||||
scrollback_lines = 1000 # historikrader per terminal
|
||||
show_scrollbar = true # scrollbar på fönstrens högerkant
|
||||
background_image = \"bild.png\" # bakgrund (Kitty graphics)
|
||||
terminal_bg_color = \"#1e1e2e\" # terminalbakgrund
|
||||
|
||||
TANGENTER (standard, ändras via [[keybind]] i config.toml):
|
||||
ctrl+space Kommandodialog — skriv t.ex. `htop` och tryck Enter
|
||||
alt+enter Ny terminal
|
||||
ctrl+q Avsluta (från en ansluten klient: kopplar bara ner den)
|
||||
|
||||
MUS:
|
||||
Dra titelraden = flytta fönster Dra kant/hörn = ändra storlek
|
||||
Scroll = historik (skal) eller vidarebefordras (appar med mus-stöd)
|
||||
Klick/hover vidarebefordras till appar som vim, htop, mc ...
|
||||
|
||||
SOCKET-API:
|
||||
Program i fönstren får $TUI_WM_SOCKET och $TUI_WM_WINDOW_ID och kan
|
||||
öppna fönster/popups via socketen — se SOCKET_API.md."
|
||||
);
|
||||
}
|
||||
|
||||
fn run_standalone() -> io::Result<()> {
|
||||
log::init();
|
||||
let socket_path = ipc::default_socket_path();
|
||||
@@ -400,9 +451,11 @@ fn handle_ipc_event(
|
||||
}
|
||||
ClientMessage::KeyEvent { event } => {
|
||||
app.handle_event(crossterm::event::Event::Key(event));
|
||||
disconnect_instead_of_quit(app, all_clients, client_id);
|
||||
}
|
||||
ClientMessage::MouseEvent { event } => {
|
||||
app.handle_event(crossterm::event::Event::Mouse(event));
|
||||
disconnect_instead_of_quit(app, all_clients, client_id);
|
||||
}
|
||||
ClientMessage::Resize { width, height } => {
|
||||
if let Some(client) = all_clients.get_mut(&client_id) {
|
||||
@@ -476,6 +529,22 @@ fn handle_ipc_event(
|
||||
}
|
||||
}
|
||||
|
||||
/// Exit utlöst av en ansluten klient (t.ex. ctrl+q eller panelens
|
||||
/// Avsluta-knapp) ska bara koppla ner DEN klienten — servern/daemonen
|
||||
/// och alla program fortsätter köra. Lokal Exit i standalone-läget
|
||||
/// går inte via IPC och stänger som vanligt hela WM:et.
|
||||
fn disconnect_instead_of_quit(
|
||||
app: &mut App,
|
||||
all_clients: &mut HashMap<usize, (ClientRole, u16, u16, mpsc::SyncSender<ServerMessage>)>,
|
||||
client_id: usize,
|
||||
) {
|
||||
if app.should_quit {
|
||||
app.should_quit = false;
|
||||
// Sändaren droppas → klientens ström stängs → klienten avslutar.
|
||||
all_clients.remove(&client_id);
|
||||
}
|
||||
}
|
||||
|
||||
fn send_app_ipc_out(
|
||||
out_ev: AppIpcOut,
|
||||
all_clients: &HashMap<usize, (ClientRole, u16, u16, mpsc::SyncSender<ServerMessage>)>,
|
||||
|
||||
Reference in New Issue
Block a user