1use std::io::{Read, Write};
2
3use crate::{geometry::Position, Result};
4
5#[derive(Debug, Clone)]
6pub struct CharBuffer {
7 buffer_size: Position,
8 data: Vec<char>,
9}
10
11impl CharBuffer {
12 pub fn new(size: Position) -> Self {
13 let data = vec![' '; size.area()];
14 Self {
15 buffer_size: size.into(),
16 data,
17 }
18 }
19
20 pub fn with_data(self, data: Vec<char>) -> Self {
21 Self {
22 buffer_size: self.buffer_size,
23 data: data.into(),
24 }
25 }
26
27 pub fn size(&self) -> usize {
28 self.buffer_size.area()
29 }
30
31 pub fn clear(&mut self) {
32 self.data = vec![' '; self.size()];
33 }
34
35 pub fn read(&mut self, reader: &mut impl Read) -> Result<()> {
38 todo!()
39 }
40
41 pub fn write(&self, writer: &mut impl Write) -> Result<()> {
42 let data = self.data.iter().map(|c| *c as u8).collect::<Vec<u8>>();
43 writer.write_all(&data)?;
44 Ok(())
45 }
46
47 pub fn set_char_idx(&mut self, c: char, idx: usize) -> Result<()> {
48 self.data[idx] = c;
49 Ok(())
50 }
51
52 pub fn set_char(&mut self, c: char, x: usize, y: usize) -> Result<()> {
53 self.data[y * self.buffer_size.x + x] = c;
54 Ok(())
55 }
56
57 pub fn rows(&self) -> Vec<String> {
58 self.data
59 .split(|char| char == &'\n')
60 .map(|row| row.iter().collect())
61 .collect()
62 }
63}
64
65impl Read for CharBuffer {
66 fn read(&mut self, buf: &mut [u8]) -> std::io::Result<usize> {
67 let data = self.data.iter().map(|c| *c as u8).collect::<Vec<u8>>();
68 buf.as_mut().write(&*data)?;
69
70 Ok(std::cmp::min(buf.len(), self.data.len()))
71 }
72}
73
74impl Write for CharBuffer {
75 fn write(&mut self, buf: &[u8]) -> std::io::Result<usize> {
76 self.data = buf.iter().map(|b| *b as char).collect();
77
78 Ok(buf.len())
79 }
80
81 fn flush(&mut self) -> std::io::Result<()> {
82 Ok(())
83 }
84}