aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/main.rs5
-rw-r--r--src/rope.rs20
-rw-r--r--src/term.rs5
3 files changed, 29 insertions, 1 deletions
diff --git a/src/main.rs b/src/main.rs
index dd20c3f..d376c2d 100644
--- a/src/main.rs
+++ b/src/main.rs
@@ -65,6 +65,11 @@ fn edit(file: &OsStr) -> Result<(), String> {
Key::CtrlQ => {
break;
}
+ Key::CtrlS => {
+ if let Err(err) = r.save(Path::new(file)) {
+ return Err(format!("write file {}: {}", file.to_string_lossy(), err));
+ }
+ }
Key::Up => {
if cursor_row == 0 {
continue;
diff --git a/src/rope.rs b/src/rope.rs
index 7d5ee28..f78dd7f 100644
--- a/src/rope.rs
+++ b/src/rope.rs
@@ -72,7 +72,7 @@ impl Node {
// TODO: escape unprintable characters
match self {
Node::Leaf(v) => {
- if let Err(err) = out.write(&v[start..end]) {
+ if let Err(err) = out.write_all(&v[start..end]) {
return Err(err);
}
return Ok(());
@@ -235,12 +235,30 @@ impl Rope {
if n == 0 {
break;
}
+ buf.truncate(n);
rope = rope.concat(Rope(Rc::new(Node::Leaf(buf))));
}
// TODO: rebalance
return Ok(rope);
}
+ pub fn save(&self, path: &Path) -> Result<(), std::io::Error> {
+ let mut f = match File::create(path) {
+ Ok(f) => f,
+ Err(err) => {
+ return Err(err);
+ }
+ };
+ let Rope(me) = self;
+ if let Err(err) = me.print(&mut f, 0, me.len()) {
+ return Err(err);
+ }
+ if let Err(err) = f.sync_all() {
+ return Err(err);
+ }
+ return Ok(());
+ }
+
pub fn len(&self) -> usize {
let Rope(me) = self;
return me.len();
diff --git a/src/term.rs b/src/term.rs
index 2303fa2..c4319b4 100644
--- a/src/term.rs
+++ b/src/term.rs
@@ -63,6 +63,7 @@ pub fn raw() -> Option<RawHandle> {
pub enum Key {
CtrlQ,
+ CtrlS,
Up,
Down,
Left,
@@ -72,6 +73,7 @@ pub enum Key {
pub fn read_key(stdin: &mut Stdin) -> Result<Key, String> {
const CTRL_Q: u8 = 17;
+ const CTRL_S: u8 = 19;
const ESC: u8 = 27;
loop {
@@ -82,6 +84,9 @@ pub fn read_key(stdin: &mut Stdin) -> Result<Key, String> {
if buf[0] == CTRL_Q {
return Ok(Key::CtrlQ);
}
+ if buf[0] == CTRL_S {
+ return Ok(Key::CtrlS);
+ }
if buf[0] != ESC {
return Ok(Key::Char(buf[0]));
}