Switch up ui::Drawable write command and run UI in separate thread
This commit is contained in:
parent
aa796e533e
commit
deca53e834
9 changed files with 332 additions and 40 deletions
259
Cargo.lock
generated
259
Cargo.lock
generated
|
@ -71,6 +71,26 @@ version = "1.5.0"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9b34d609dfbaf33d6889b2b7106d3ca345eacad44200913df5ba02bfd31d2ba9"
|
||||
|
||||
[[package]]
|
||||
name = "async-io"
|
||||
version = "1.3.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9315f8f07556761c3e48fec2e6b276004acf426e6dc068b2c2251854d65ee0fd"
|
||||
dependencies = [
|
||||
"concurrent-queue",
|
||||
"fastrand",
|
||||
"futures-lite",
|
||||
"libc",
|
||||
"log",
|
||||
"nb-connect",
|
||||
"once_cell",
|
||||
"parking",
|
||||
"polling",
|
||||
"vec-arena",
|
||||
"waker-fn",
|
||||
"winapi",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "async-trait"
|
||||
version = "0.1.42"
|
||||
|
@ -253,6 +273,12 @@ version = "1.0.1"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b700ce4376041dcd0a327fd0097c41095743c4c8af8887265942faf1100bd040"
|
||||
|
||||
[[package]]
|
||||
name = "cache-padded"
|
||||
version = "1.1.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "631ae5198c9be5e753e5cc215e1bd73c2b466a3565173db433f52bb9d3e66dba"
|
||||
|
||||
[[package]]
|
||||
name = "cast5"
|
||||
version = "0.8.0"
|
||||
|
@ -345,6 +371,15 @@ dependencies = [
|
|||
"winapi",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "concurrent-queue"
|
||||
version = "1.2.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "30ed07550be01594c6026cff2a1d7fe9c8f683caa798e12b68694ac9e88286a3"
|
||||
dependencies = [
|
||||
"cache-padded",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "constant_time_eq"
|
||||
version = "0.1.5"
|
||||
|
@ -473,13 +508,14 @@ dependencies = [
|
|||
]
|
||||
|
||||
[[package]]
|
||||
name = "dbus"
|
||||
version = "0.9.2"
|
||||
name = "derivative"
|
||||
version = "2.2.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f597e08dfa79b593f23bbfc7840b23b2c5aa2e3a98d8e68b67b5b9ff800dc0db"
|
||||
checksum = "fcc3dd5e9e9c0b295d6e1e4d811fb6f157d5ffd784b8d202fc62eac8035a770b"
|
||||
dependencies = [
|
||||
"libc",
|
||||
"libdbus-sys",
|
||||
"proc-macro2",
|
||||
"quote 1.0.9",
|
||||
"syn 1.0.60",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
|
@ -570,12 +606,42 @@ dependencies = [
|
|||
"zeroize",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "enumflags2"
|
||||
version = "0.6.4"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "83c8d82922337cd23a15f88b70d8e4ef5f11da38dd7cdb55e84dd5de99695da0"
|
||||
dependencies = [
|
||||
"enumflags2_derive",
|
||||
"serde",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "enumflags2_derive"
|
||||
version = "0.6.4"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "946ee94e3dbf58fdd324f9ce245c7b238d46a66f00e86a020b71996349e46cce"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote 1.0.9",
|
||||
"syn 1.0.60",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "fake-simd"
|
||||
version = "0.1.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e88a8acf291dafb59c2d96e8f59828f3838bb1a70398823ade51a84de6a6deed"
|
||||
|
||||
[[package]]
|
||||
name = "fastrand"
|
||||
version = "1.4.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ca5faf057445ce5c9d4329e382b2ce7ca38550ef3b73a5348362d5f24e0c7fe3"
|
||||
dependencies = [
|
||||
"instant",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "fern"
|
||||
version = "0.6.0"
|
||||
|
@ -674,6 +740,21 @@ version = "0.3.13"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d71c2c65c57704c32f5241c1223167c2c3294fd34ac020c807ddbe6db287ba59"
|
||||
|
||||
[[package]]
|
||||
name = "futures-lite"
|
||||
version = "1.11.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b4481d0cd0de1d204a4fa55e7d45f07b1d958abcb06714b3446438e2eff695fb"
|
||||
dependencies = [
|
||||
"fastrand",
|
||||
"futures-core",
|
||||
"futures-io",
|
||||
"memchr",
|
||||
"parking",
|
||||
"pin-project-lite",
|
||||
"waker-fn",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "futures-macro"
|
||||
version = "0.3.13"
|
||||
|
@ -870,15 +951,6 @@ version = "0.2.86"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b7282d924be3275cec7f6756ff4121987bc6481325397dde6ba3e7802b1a8b1c"
|
||||
|
||||
[[package]]
|
||||
name = "libdbus-sys"
|
||||
version = "0.2.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "dc12a3bc971424edbbf7edaf6e5740483444db63aa8e23d3751ff12a30f306f0"
|
||||
dependencies = [
|
||||
"pkg-config",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "libm"
|
||||
version = "0.2.1"
|
||||
|
@ -980,6 +1052,29 @@ dependencies = [
|
|||
"winapi",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "nb-connect"
|
||||
version = "1.0.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "670361df1bc2399ee1ff50406a0d422587dd3bb0da596e1978fe8e05dabddf4f"
|
||||
dependencies = [
|
||||
"libc",
|
||||
"socket2",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "nix"
|
||||
version = "0.17.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "50e4785f2c3b7589a0d0c1dd60285e1188adac4006e8abd6dd578e1567027363"
|
||||
dependencies = [
|
||||
"bitflags 1.2.1",
|
||||
"cc",
|
||||
"cfg-if 0.1.10",
|
||||
"libc",
|
||||
"void",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "nom"
|
||||
version = "4.2.3"
|
||||
|
@ -996,9 +1091,12 @@ version = "4.2.2"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "95a3a5dd7b4b415b112ce0fae1988f3e6dee90a96918bf3950b5f2289b19a04b"
|
||||
dependencies = [
|
||||
"dbus",
|
||||
"mac-notification-sys",
|
||||
"serde",
|
||||
"winrt-notification",
|
||||
"zbus",
|
||||
"zvariant",
|
||||
"zvariant_derive",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
|
@ -1200,6 +1298,12 @@ dependencies = [
|
|||
name = "panorama-smtp"
|
||||
version = "0.1.0"
|
||||
|
||||
[[package]]
|
||||
name = "parking"
|
||||
version = "2.0.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "427c3892f9e783d91cc128285287e70a59e206ca452770ece88a76f7a3eddd72"
|
||||
|
||||
[[package]]
|
||||
name = "parking_lot"
|
||||
version = "0.11.1"
|
||||
|
@ -1361,10 +1465,17 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|||
checksum = "8b870d8c151b6f2fb93e84a13146138f05d02ed11c7e7c54f8826aaaf7c9f184"
|
||||
|
||||
[[package]]
|
||||
name = "pkg-config"
|
||||
version = "0.3.19"
|
||||
name = "polling"
|
||||
version = "2.0.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3831453b3449ceb48b6d9c7ad7c96d5ea673e9b470a1dc578c2ce6521230884c"
|
||||
checksum = "a2a7bc6b2a29e632e45451c941832803a18cce6781db04de8a04696cdca8bde4"
|
||||
dependencies = [
|
||||
"cfg-if 0.1.10",
|
||||
"libc",
|
||||
"log",
|
||||
"wepoll-sys",
|
||||
"winapi",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "ppv-lite86"
|
||||
|
@ -1372,6 +1483,15 @@ version = "0.2.10"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ac74c624d6b2d21f425f752262f42188365d7b8ff1aff74c82e45136510a4857"
|
||||
|
||||
[[package]]
|
||||
name = "proc-macro-crate"
|
||||
version = "0.1.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1d6ea3c4595b96363c13943497db34af4460fb474a95c43f4446ad341b8c9785"
|
||||
dependencies = [
|
||||
"toml",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "proc-macro-error"
|
||||
version = "0.4.12"
|
||||
|
@ -1653,6 +1773,12 @@ dependencies = [
|
|||
"winapi",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "scoped-tls"
|
||||
version = "1.0.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ea6a9290e3c9cf0f18145ef7ffa62d68ee0bf5fcd651017e586dc7fd5da448c2"
|
||||
|
||||
[[package]]
|
||||
name = "scopeguard"
|
||||
version = "1.1.0"
|
||||
|
@ -1712,6 +1838,17 @@ dependencies = [
|
|||
"syn 1.0.60",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "serde_repr"
|
||||
version = "0.1.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "2dc6b7951b17b051f3210b063f12cc17320e2fe30ae05b0fe2a3abb068551c76"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote 1.0.9",
|
||||
"syn 1.0.60",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "sha-1"
|
||||
version = "0.8.2"
|
||||
|
@ -2131,6 +2268,12 @@ version = "0.7.1"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a156c684c91ea7d62626509bce3cb4e1d9ed5c4d978f7b4352658f96a4c26b4a"
|
||||
|
||||
[[package]]
|
||||
name = "vec-arena"
|
||||
version = "1.0.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "eafc1b9b2dfc6f5529177b62cf806484db55b32dc7c9658a118e11bbeb33061d"
|
||||
|
||||
[[package]]
|
||||
name = "vec_map"
|
||||
version = "0.8.2"
|
||||
|
@ -2149,6 +2292,18 @@ version = "0.9.2"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b5a972e5669d67ba988ce3dc826706fb0a8b01471c088cb0b6110b805cc36aed"
|
||||
|
||||
[[package]]
|
||||
name = "void"
|
||||
version = "1.0.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "6a02e4885ed3bc0f2de90ea6dd45ebcbb66dacffe03547fadbb0eeae2770887d"
|
||||
|
||||
[[package]]
|
||||
name = "waker-fn"
|
||||
version = "1.1.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9d5b2c62b4012a3e1eca5a7e077d13b3bf498c4073e33ccd58626607748ceeca"
|
||||
|
||||
[[package]]
|
||||
name = "wasi"
|
||||
version = "0.9.0+wasi-snapshot-preview1"
|
||||
|
@ -2244,6 +2399,15 @@ dependencies = [
|
|||
"webpki",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "wepoll-sys"
|
||||
version = "3.0.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0fcb14dea929042224824779fbc82d9fab8d2e6d3cbc0ac404de8edf489e77ff"
|
||||
dependencies = [
|
||||
"cc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "winapi"
|
||||
version = "0.3.9"
|
||||
|
@ -2314,6 +2478,41 @@ dependencies = [
|
|||
"bitflags 0.9.1",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "zbus"
|
||||
version = "1.8.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "40b4d4aa39daed4e32aed75f0c37b969184949a0fdfd5f2e1277abfda61f02a8"
|
||||
dependencies = [
|
||||
"async-io",
|
||||
"byteorder",
|
||||
"derivative",
|
||||
"enumflags2",
|
||||
"fastrand",
|
||||
"futures",
|
||||
"nb-connect",
|
||||
"nix",
|
||||
"once_cell",
|
||||
"polling",
|
||||
"scoped-tls",
|
||||
"serde",
|
||||
"serde_repr",
|
||||
"zbus_macros",
|
||||
"zvariant",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "zbus_macros"
|
||||
version = "1.8.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "87cc141cda72384bef359badf1808e391d3968f9299e8f3c3cbb78dafa1e0930"
|
||||
dependencies = [
|
||||
"proc-macro-crate",
|
||||
"proc-macro2",
|
||||
"quote 1.0.9",
|
||||
"syn 1.0.60",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "zeroize"
|
||||
version = "1.2.0"
|
||||
|
@ -2334,3 +2533,27 @@ dependencies = [
|
|||
"syn 1.0.60",
|
||||
"synstructure",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "zvariant"
|
||||
version = "2.5.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "2fc67d552ac18ccd9e440f062f5b32c46776f96073122a8da2fe0c533833a213"
|
||||
dependencies = [
|
||||
"byteorder",
|
||||
"enumflags2",
|
||||
"serde",
|
||||
"zvariant_derive",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "zvariant_derive"
|
||||
version = "2.5.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "eaee686340b5bff077d52423d8cc4f0f7cb323fe3f31ef676b8a3a2810bc53c5"
|
||||
dependencies = [
|
||||
"proc-macro-crate",
|
||||
"proc-macro2",
|
||||
"quote 1.0.9",
|
||||
"syn 1.0.60",
|
||||
]
|
||||
|
|
|
@ -22,7 +22,7 @@ format-bytes = "0.2.0"
|
|||
futures = "0.3.13"
|
||||
inotify = { version = "0.9.2", features = ["stream"] }
|
||||
log = "0.4.14"
|
||||
notify-rust = "4.2.2"
|
||||
notify-rust = { version = "4.2.2", default-features = false, features = ["z"] }
|
||||
parking_lot = "0.11.1"
|
||||
pgp = "0.7.1"
|
||||
pin-project = "1.0.5"
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
use std::fmt;
|
||||
|
||||
/// Commands, without the tag part.
|
||||
#[derive(Clone)]
|
||||
#[derive(Clone, Debug)]
|
||||
pub enum Command {
|
||||
Capability,
|
||||
Starttls,
|
||||
|
|
30
src/main.rs
30
src/main.rs
|
@ -2,13 +2,18 @@
|
|||
extern crate log;
|
||||
|
||||
use std::path::{Path, PathBuf};
|
||||
use std::thread;
|
||||
|
||||
use anyhow::Result;
|
||||
use fern::colors::{Color, ColoredLevelConfig};
|
||||
use futures::future::TryFutureExt;
|
||||
use panorama::{config::spawn_config_watcher_system, mail, report_err, ui};
|
||||
use structopt::StructOpt;
|
||||
use tokio::{runtime::Runtime, sync::mpsc};
|
||||
use tokio::{
|
||||
runtime::{Builder as RuntimeBuilder, Runtime},
|
||||
sync::mpsc,
|
||||
task::LocalSet,
|
||||
};
|
||||
use xdg::BaseDirectories;
|
||||
|
||||
#[derive(Debug, StructOpt)]
|
||||
|
@ -58,8 +63,7 @@ async fn run(opt: Opt) -> Result<()> {
|
|||
});
|
||||
|
||||
if !opt.headless {
|
||||
let stdout = std::io::stdout();
|
||||
tokio::spawn(ui::run_ui(stdout, exit_tx).unwrap_or_else(report_err));
|
||||
run_ui(exit_tx);
|
||||
}
|
||||
|
||||
exit_rx.recv().await;
|
||||
|
@ -71,6 +75,26 @@ async fn run(opt: Opt) -> Result<()> {
|
|||
// Ok(())
|
||||
}
|
||||
|
||||
// Spawns the entire UI in a different thread, since it must be thread-local
|
||||
fn run_ui(exit_tx: mpsc::Sender<()>) {
|
||||
let stdout = std::io::stdout();
|
||||
|
||||
let rt = RuntimeBuilder::new_current_thread()
|
||||
.enable_all()
|
||||
.build()
|
||||
.unwrap();
|
||||
|
||||
thread::spawn(move || {
|
||||
let localset = LocalSet::new();
|
||||
|
||||
localset.spawn_local(async {
|
||||
ui::run_ui(stdout, exit_tx).unwrap_or_else(report_err).await;
|
||||
});
|
||||
|
||||
rt.block_on(localset);
|
||||
});
|
||||
}
|
||||
|
||||
fn setup_logger(log_file: Option<impl AsRef<Path>>) -> Result<()> {
|
||||
let now = chrono::Local::now().format("[%Y-%m-%d][%H:%M:%S]");
|
||||
let colors = ColoredLevelConfig::new()
|
||||
|
|
|
@ -1 +1,13 @@
|
|||
pub trait Drawable {}
|
||||
use std::io::Write;
|
||||
|
||||
use anyhow::Result;
|
||||
|
||||
use super::{Rect, Screen};
|
||||
|
||||
pub trait Drawable {
|
||||
/// Draws this UI element to the screen
|
||||
fn draw(&self, w: &mut Screen, rect: Rect) -> Result<()>;
|
||||
|
||||
/// Invalidates this UI element, queueing it for redraw
|
||||
fn invalidate(&mut self);
|
||||
}
|
||||
|
|
|
@ -5,7 +5,7 @@ mod table;
|
|||
mod tabs;
|
||||
|
||||
use std::fmt::Debug;
|
||||
use std::io::Write;
|
||||
use std::io::{Stdout, Write};
|
||||
use std::time::Duration;
|
||||
|
||||
use anyhow::Result;
|
||||
|
@ -20,25 +20,30 @@ use tokio::time;
|
|||
|
||||
use crate::ExitSender;
|
||||
|
||||
use self::drawable::Drawable;
|
||||
use self::table::Table;
|
||||
use self::tabs::Tabs;
|
||||
|
||||
const FRAME_DURATION: Duration = Duration::from_millis(20);
|
||||
|
||||
/// Type alias for the screen object we're drawing to
|
||||
pub type Screen = Stdout;
|
||||
|
||||
/// X Y W H
|
||||
#[derive(Copy, Clone)]
|
||||
pub struct Rect(u16, u16, u16, u16);
|
||||
|
||||
/// UI entrypoint.
|
||||
pub async fn run_ui(mut w: impl Write + Debug, exit: ExitSender) -> Result<()> {
|
||||
pub async fn run_ui(mut w: Stdout, exit: ExitSender) -> Result<()> {
|
||||
execute!(w, cursor::Hide, terminal::EnterAlternateScreen)?;
|
||||
terminal::enable_raw_mode()?;
|
||||
|
||||
let mut tabs = Tabs::new();
|
||||
|
||||
let mut table = Table::default();
|
||||
table.push_row(vec!["ur mom Lol!".to_owned()]);
|
||||
table.push_row(vec!["hek".to_owned()]);
|
||||
|
||||
let dirty = false;
|
||||
|
||||
loop {
|
||||
queue!(
|
||||
w,
|
||||
|
|
|
@ -7,7 +7,7 @@ use crossterm::{
|
|||
style::{self, Color},
|
||||
};
|
||||
|
||||
use super::Rect;
|
||||
use super::{Drawable, Rect, Screen};
|
||||
|
||||
#[derive(Default)]
|
||||
pub struct Table {
|
||||
|
@ -36,10 +36,16 @@ impl Table {
|
|||
}
|
||||
}
|
||||
|
||||
pub fn draw<W>(&self, w: &mut W, rect: Rect) -> Result<()>
|
||||
where
|
||||
W: Write,
|
||||
{
|
||||
pub fn push_row(&mut self, row: Vec<String>) {
|
||||
self.rows.push(row);
|
||||
if self.selected_row.is_none() {
|
||||
self.selected_row = Some(0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Drawable for Table {
|
||||
fn draw(&self, w: &mut Screen, rect: Rect) -> Result<()> {
|
||||
if !self.rows.is_empty() {
|
||||
let mut columns = Vec::new();
|
||||
for row in self.rows.iter() {
|
||||
|
@ -102,10 +108,7 @@ impl Table {
|
|||
Ok(())
|
||||
}
|
||||
|
||||
pub fn push_row(&mut self, row: Vec<String>) {
|
||||
self.rows.push(row);
|
||||
if self.selected_row.is_none() {
|
||||
self.selected_row = Some(0);
|
||||
}
|
||||
fn invalidate(&mut self) {
|
||||
// TODO: do something
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1 +1,26 @@
|
|||
pub struct Tabs {}
|
||||
use std::collections::HashMap;
|
||||
use std::io::Write;
|
||||
|
||||
use anyhow::Result;
|
||||
|
||||
use super::{Drawable, Rect, Screen};
|
||||
|
||||
pub struct Tabs {
|
||||
tabs: HashMap<String, Box<dyn Drawable>>,
|
||||
}
|
||||
|
||||
impl Drawable for Tabs {
|
||||
fn draw(&self, w: &mut Screen, rect: Rect) -> Result<()> {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn invalidate(&mut self) {}
|
||||
}
|
||||
|
||||
impl Tabs {
|
||||
pub fn new() -> Self {
|
||||
Tabs {
|
||||
tabs: HashMap::new(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue