summaryrefslogtreecommitdiffstats
path: root/src/printer.rs
diff options
context:
space:
mode:
Diffstat (limited to 'src/printer.rs')
-rw-r--r--src/printer.rs117
1 files changed, 117 insertions, 0 deletions
diff --git a/src/printer.rs b/src/printer.rs
new file mode 100644
index 0000000..7091124
--- /dev/null
+++ b/src/printer.rs
@@ -0,0 +1,117 @@
+pub struct Printer<W: std::io::Write> {
+ lines: usize,
+ buffer: String,
+ writer: W,
+}
+
+impl<W> From<W> for Printer<W>
+where
+ W: std::io::Write,
+{
+ fn from(value: W) -> Self {
+ Self {
+ lines: 0,
+ buffer: String::new(),
+ writer: value,
+ }
+ }
+}
+
+impl<W: std::io::Write> Printer<W> {
+ pub fn write(&mut self) -> std::io::Result<&mut Self> {
+ writeln!(self.writer, "{}", self.buffer)?;
+ self.writer.flush()?;
+
+ self.lines = self.buffer.lines().count() + 1;
+ self.buffer.clear();
+
+ Ok(self)
+ }
+
+ pub fn write_pause(&mut self, prompt: &str) -> std::io::Result<&mut Self> {
+ use std::io::Read;
+
+ self.buffer.push('\n');
+ self.buffer.push_str(prompt);
+
+ self.write()?;
+ let _ = std::io::stdin().read(&mut [0u8])?;
+ Ok(self)
+ }
+
+ pub fn write_pause_condition(
+ &mut self,
+ prompt: &str,
+ cond: bool,
+ ) -> std::io::Result<&mut Self> {
+ if cond {
+ self.write_pause(prompt)
+ } else {
+ self.write()
+ }
+ }
+
+ pub fn write_sleep(&mut self, time: u64) -> std::io::Result<&mut Self> {
+ self.write()?;
+ std::thread::sleep(std::time::Duration::from_millis(time));
+
+ Ok(self)
+ }
+
+ pub fn clear(&mut self) -> &mut Self {
+ self.buffer
+ .insert_str(0, &"\x1b[1A\x1b[K".repeat(self.lines));
+ self.lines = 0;
+ self
+ }
+
+ pub fn with(&mut self, fmt: std::fmt::Arguments) -> &mut Self {
+ self.buffer.push('\n');
+ self.buffer.push_str(format!("{}", fmt).as_str());
+ self
+ }
+
+ pub fn with_grid<T: std::fmt::Display>(&mut self, grid: &[Vec<T>]) -> &mut Self {
+ let s = grid
+ .iter()
+ .flat_map(|row| {
+ row.iter()
+ .map(|s| s.to_string())
+ .chain(std::iter::once("\n".to_string()))
+ })
+ .collect::<String>();
+
+ self.buffer.push('\n');
+ self.buffer.push_str(s.as_str());
+
+ self
+ }
+
+ pub fn with_grid_path<T: std::fmt::Display>(
+ &mut self,
+ grid: &[Vec<T>],
+ highlight: &[(usize, usize)],
+ ) -> &mut Self {
+ let s = grid
+ .iter()
+ .enumerate()
+ .flat_map(|(x, row)| {
+ row.iter()
+ .enumerate()
+ .map(move |(y, s)| {
+ if highlight.contains(&(x, y)) {
+ format!("\x1b[1;30;42m{s}\x1b[0m")
+ } else {
+ s.to_string()
+ }
+ })
+ .chain(std::iter::once("\n".to_string()))
+ })
+ .collect::<String>();
+
+ self.buffer.push('\n');
+ self.buffer.push_str(s.as_str());
+
+ self
+ }
+}