aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJesse Luehrs <doy@tozt.net>2013-03-20 21:33:19 -0500
committerJesse Luehrs <doy@tozt.net>2013-03-20 21:33:19 -0500
commitd00c8ec76c498196be8bfe2d58f27697bda9de69 (patch)
treec3126e111332355683d533d7741afbaca7f36cd4
parent8fc473d033a4c38f7c0024bd259ff54b9867d50d (diff)
downloadrust-term-d00c8ec76c498196be8bfe2d58f27697bda9de69.tar.gz
rust-term-d00c8ec76c498196be8bfe2d58f27697bda9de69.zip
start working on a terminfo wrapper
-rw-r--r--Makefile13
-rw-r--r--src/curses_helper.c7
-rw-r--r--src/info.rs103
-rw-r--r--test/rl.rs18
4 files changed, 138 insertions, 3 deletions
diff --git a/Makefile b/Makefile
index 71436be..9d6f29b 100644
--- a/Makefile
+++ b/Makefile
@@ -2,7 +2,7 @@ RUSTC = rustc
MAIN_SOURCE = src/term.rs
OTHER_SOURCES = src/ios.rs src/info.rs
-TESTS = bin/termios bin/termios2 bin/termios3
+TESTS = bin/termios bin/termios2 bin/termios3 bin/rl
all: build tests
@@ -14,17 +14,24 @@ bin/%: test/%.rs
@mkdir -p bin
$(RUSTC) --out-dir bin -L lib $<
-lib/built: $(MAIN_SOURCE) $(OTHER_SOURCES) tmp/libtermios_wrapper.a
+lib/built: $(MAIN_SOURCE) $(OTHER_SOURCES) tmp/libtermios_wrapper.a tmp/libcurses_helper.a
@mkdir -p lib
$(RUSTC) --out-dir lib -L tmp $(MAIN_SOURCE) && touch tmp/built
tmp/libtermios_wrapper.a: tmp/termios_wrapper.o
- ar cr tmp/libtermios_wrapper.a tmp/termios_wrapper.o
+ ar cr $@ $<
tmp/termios_wrapper.o: src/termios_wrapper.c
@mkdir -p tmp
cc -fPIC -c -o $@ $<
+tmp/libcurses_helper.a: tmp/curses_helper.o
+ ar cr $@ $<
+
+tmp/curses_helper.o: src/curses_helper.c
+ @mkdir -p tmp
+ cc -fPIC -c -o $@ $<
+
clean:
-@rm -rf lib/ bin/ tmp/
diff --git a/src/curses_helper.c b/src/curses_helper.c
new file mode 100644
index 0000000..2e71e0a
--- /dev/null
+++ b/src/curses_helper.c
@@ -0,0 +1,7 @@
+#include <curses.h>
+#include <term.h>
+
+char *tiparm2(const char *name, int p1, int p2)
+{
+ return tiparm(name, p1, p2);
+}
diff --git a/src/info.rs b/src/info.rs
index e69de29..d1b3695 100644
--- a/src/info.rs
+++ b/src/info.rs
@@ -0,0 +1,103 @@
+use core::libc::{c_char,c_int};
+
+pub fn init () {
+ unsafe { c::setupterm(ptr::null(), 1, ptr::null()) };
+}
+
+pub fn clear () {
+ write_escape("clear");
+}
+
+pub fn move (col: uint, row: uint) {
+ if col == 0u && row == 0u {
+ write_escape("home");
+ }
+ else {
+ write_escape2("cup", row as int, col as int);
+ }
+}
+
+/*
+pub fn color_name (name: &str) -> u8 {
+}
+
+pub fn color_rgb (r: u8, g: u8, b: u8) -> u8 {
+}
+
+pub fn color (color: u8) {
+}
+
+pub fn bold (enabled: bool) {
+}
+
+pub fn reverse (enabled: bool) {
+}
+*/
+
+pub fn cursor (enabled: bool) {
+ if enabled {
+ write_escape("civis");
+ }
+ else {
+ write_escape("cnorm");
+ }
+}
+
+pub fn with_alternate_screen<T> (body: &fn () -> T) -> T {
+ write_escape("smcup");
+ let ret = body();
+ write_escape("rmcup");
+ ret
+}
+
+fn write_escape (name: &str) {
+ let output = do str::as_c_str(name) |c_name| {
+ unsafe {
+ str::raw::from_c_str(tigetstr(c_name))
+ }
+ };
+ io::print(output);
+}
+
+fn write_escape2 (name: &str, p1: int, p2: int) {
+ let output = do str::as_c_str(name) |c_name| {
+ unsafe {
+ str::raw::from_c_str(tiparm2(tigetstr(c_name), p1, p2))
+ }
+ };
+ io::print(output);
+}
+
+unsafe fn tigetstr (name: *c_char) -> *c_char {
+ let c_out = c::tigetstr(name);
+ if c_out as int == -1 {
+ fail!(fmt!("%s is not a terminal capability",
+ unsafe { str::raw::from_c_str(name) }));
+ }
+ else if c_out == ptr::null() {
+ fail!(fmt!("The current terminal doesn't support %s",
+ unsafe { str::raw::from_c_str(name) }));
+ }
+ c_out
+}
+
+unsafe fn tiparm2 (name: *c_char, p1: int, p2: int) -> *c_char {
+ let ret = helper::tiparm2(name, p1 as c_int, p2 as c_int);
+ if ret == ptr::null() {
+ fail!(fmt!("Couldn't assemble parameters with %s %d %d",
+ unsafe { str::raw::from_c_str(name) }, p1, p2));
+ }
+ ret
+}
+
+#[link_name = "curses"]
+extern mod c {
+ fn setupterm (term: *c_char, fd: c_int, errret: *c_int) -> c_int;
+ fn tigetstr (s: *c_char) -> *c_char;
+}
+
+// tiparm uses varargs, which you can't bind from rust yet
+#[link_name = "curses_helper"]
+extern mod helper {
+ fn tiparm2(s: *c_char, p1: c_int, p2: c_int) -> *c_char;
+}
diff --git a/test/rl.rs b/test/rl.rs
new file mode 100644
index 0000000..2ea664f
--- /dev/null
+++ b/test/rl.rs
@@ -0,0 +1,18 @@
+extern mod term;
+use core::io::ReaderUtil;
+
+fn main () {
+ term::info::init();
+ let (rows, cols) = term::ios::size();
+ do term::ios::preserve {
+ term::ios::cbreak();
+ do term::info::with_alternate_screen {
+ term::info::clear();
+ for uint::range(0, rows) |i| {
+ term::info::move(0, i);
+ io::print(str::repeat(".", cols));
+ }
+ io::stdin().read_char();
+ }
+ }
+}