Skip to content

Commit

Permalink
scrollbar
Browse files Browse the repository at this point in the history
  • Loading branch information
0xshodan committed Jul 31, 2023
1 parent 55d4a44 commit a05cde0
Show file tree
Hide file tree
Showing 3 changed files with 159 additions and 19 deletions.
61 changes: 61 additions & 0 deletions .vscode/launch.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
{
"version": "0.2.0",
"configurations": [
{
"type": "lldb",
"request": "launch",
"name": "Debug unit tests in library 'whiz'",
"cargo": {
"args": [
"test",
"--no-run",
"--lib",
"--package=whiz"
],
"filter": {
"name": "whiz",
"kind": "lib"
}
},
"args": [],
"cwd": "${workspaceFolder}"
},
{
"type": "lldb",
"request": "launch",
"name": "Debug executable 'whiz'",
"cargo": {
"args": [
"build",
"--bin=whiz",
"--package=whiz"
],
"filter": {
"name": "whiz",
"kind": "bin"
}
},
"args": [],
"cwd": "${workspaceFolder}"
},
{
"type": "lldb",
"request": "launch",
"name": "Debug unit tests in executable 'whiz'",
"cargo": {
"args": [
"test",
"--no-run",
"--bin=whiz",
"--package=whiz"
],
"filter": {
"name": "whiz",
"kind": "bin"
}
},
"args": [],
"cwd": "${workspaceFolder}"
}
]
}
29 changes: 21 additions & 8 deletions src/actors/command.rs
Original file line number Diff line number Diff line change
Expand Up @@ -258,15 +258,25 @@ impl CommandActor {

let default_entrypoint = {
#[cfg(not(target_os = "windows"))]
{"bash -c"}
{
"bash -c"
}

#[cfg(target_os = "windows")]
{"cmd /c"}
{
"cmd /c"
}
};

let exec = {
let entrypoint_lex = match &self.entrypoint {
Some(e) => if !e.is_empty() { e.as_str() } else { default_entrypoint },
Some(e) => {
if !e.is_empty() {
e.as_str()
} else {
default_entrypoint
}
}
None => default_entrypoint,
};

Expand All @@ -277,19 +287,22 @@ impl CommandActor {
Some(a) => {
s.push(a.to_owned());
s
},
}
None => s,
}
};

let entrypoint = &entrypoint_split[0];
let nargs: Vec<String> = entrypoint_split[1..]
.to_owned()
.into_iter()
.iter()
.cloned()
.filter(|s| !s.is_empty())
.collect();

self.log_debug(format!("EXEC: {} {:?} at {:?}", entrypoint_lex, nargs, self.cwd));

self.log_debug(format!(
"EXEC: {} {:?} at {:?}",
entrypoint_lex, nargs, self.cwd
));
self.console.do_send(PanelStatus {
panel_name: self.op_name.clone(),
status: None,
Expand Down
88 changes: 77 additions & 11 deletions src/actors/console.rs
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,10 @@ use crossterm::{

use super::command::{CommandActor, PoisonPill, Reload};

const DIVIDER_LENGTH: usize = 3; // " | "
const MORE_TABS_LENGTH: usize = 3; // "..."
const BORDER_LENGTH: u16 = 2; // "| " or " |"

pub struct Panel {
logs: Vec<(String, Style)>,
lines: u16,
Expand All @@ -51,6 +55,9 @@ impl Panel {

pub struct ConsoleActor {
terminal: Terminal<CrosstermBackend<io::Stdout>>,
width: u16,
offset: usize,
step: usize,
index: String,
order: Vec<String>,
arbiter: Arbiter,
Expand All @@ -72,6 +79,9 @@ impl ConsoleActor {
let terminal = Terminal::new(backend).unwrap();
Self {
terminal,
width: 0,
offset: 0,
step: 0,
index: order[0].clone(),
order,
arbiter: Arbiter::new(),
Expand All @@ -86,7 +96,6 @@ impl ConsoleActor {
// maximum_scroll is the number of lines
// overflowing in the current focused panel
let maximum_scroll = focused_panel.lines - min(focused_panel.lines, log_height);

// `focused_panel.shift` goes from 0 until maximum_scroll
focused_panel.shift = min(focused_panel.shift + shift, maximum_scroll);
}
Expand All @@ -101,12 +110,52 @@ impl ConsoleActor {
}
}
}

pub fn get_offset(&self) -> usize {
if self.offset > 0 {
self.offset - 1 // first in tabs list "...", skip it
} else {
self.offset
}
}
pub fn get_log_height(&mut self) -> u16 {
let frame = self.terminal.get_frame();
chunks(&frame)[0].height
}

pub fn get_log_width(&mut self) -> u16 {
let frame = self.terminal.get_frame();
chunks(&frame)[0].width
}

pub fn get_visible_tabs(&self) -> (Vec<String>, usize) {
let mut counter: usize = 0;
let mut ret: Vec<String> = Vec::new();
let mut width = (self.width - (BORDER_LENGTH * 2)) as usize;
let mut r = 0;
if self.offset > 0 {
ret.push("...".to_string());
width -= MORE_TABS_LENGTH + DIVIDER_LENGTH; // "... | "
}
for i in self.offset..self.order.len() {
r = i;
let tab = self.order[i].clone();
let mut next = 0;
counter += tab.len() + 1; // has "." | "!" | "*"
if i < self.order.len() - 1 {
next = self.order[i + 1].clone().len() + DIVIDER_LENGTH + 1;
}
if counter + DIVIDER_LENGTH + MORE_TABS_LENGTH + next >= width {
ret.push(tab + &" ".repeat(width - MORE_TABS_LENGTH - DIVIDER_LENGTH - counter));
ret.push("...".to_string());
return (ret, r);
} else {
ret.push(tab);
}
counter += DIVIDER_LENGTH;
}
(ret, r)
}

pub fn go_to(&mut self, panel_index: usize) {
if panel_index < self.order.len() {
self.index = self.order[panel_index].clone();
Expand All @@ -121,10 +170,24 @@ impl ConsoleActor {
}

pub fn next(&mut self) {
let idx = self.idx();
let tabs = self.get_visible_tabs().1;
if idx == tabs {
self.offset = 0;
} else if idx + self.step + 1 >= tabs {
self.offset = (self.offset + 1) % self.order.len();
}
self.index = self.order[(self.idx() + 1) % self.order.len()].clone();
}

pub fn previous(&mut self) {
let idx = self.idx();
if idx == 0 {
self.offset = (self.offset + self.order.len() - 1) % self.order.len();
} else if self.offset == 0 && self.idx() <= self.step {
} else if self.idx() as isize - self.step as isize <= self.offset as isize {
self.offset = (self.offset + self.order.len() - 1) % self.order.len();
}
self.index = self.order[(self.idx() + self.order.len() - 1) % self.order.len()].clone();
}

Expand All @@ -139,13 +202,16 @@ impl ConsoleActor {
}

fn draw(&mut self) {
self.width = self.get_log_width();
let idx = self.idx();
let offset = self.get_offset();
let (visible_tabs, length) = self.get_visible_tabs();
self.step = length / 4;
if let Some(focused_panel) = &self.panels.get(&self.index) {
self.terminal
.draw(|f| {
let chunks = chunks(f);
let logs = &focused_panel.logs;

let log_height = chunks[0].height;
let maximum_scroll = focused_panel.lines - min(focused_panel.lines, log_height);

Expand All @@ -164,15 +230,15 @@ impl ConsoleActor {
let paragraph = paragraph
.scroll((maximum_scroll - min(maximum_scroll, focused_panel.shift), 0));
f.render_widget(paragraph, chunks[0]);

let /*mut*/ titles: Vec<Line> = self
.order
let /*mut*/ titles: Vec<Line> = visible_tabs
.iter()
.map(|panel| {
let span = self.panels.get(panel).map(|p| match p.status {
Some(ExitStatus::Exited(0)) => Span::styled(format!("{}.", panel), Style::default().fg(Color::Green)),
Some(_) => Span::styled(format!("{}!", panel), Style::default().fg(Color::Red)),
None => Span::styled(format!("{}*", panel), Style::default()),
let cleared_panel = panel.trim_end().to_string();
let spaces = " ".repeat(panel.len() - cleared_panel.len());
let span = self.panels.get(&cleared_panel).map(|p| match p.status {
Some(ExitStatus::Exited(0)) => Span::styled(format!("{}.{}", cleared_panel, spaces), Style::default().fg(Color::Green)),
Some(_) => Span::styled(format!("{}!{}", cleared_panel, spaces), Style::default().fg(Color::Red)),
None => Span::styled(format!("{}*{}", cleared_panel, spaces), Style::default()),
}).unwrap_or_else(|| Span::styled(panel, Style::default()));
Line::from(span)
})
Expand All @@ -189,7 +255,7 @@ impl ConsoleActor {
*/
let tabs = Tabs::new(titles)
.block(Block::default().borders(Borders::ALL))
.select(idx)
.select(idx - offset)
.highlight_style(
Style::default()
.add_modifier(Modifier::BOLD)
Expand Down

0 comments on commit a05cde0

Please sign in to comment.