add shell crate with stupid int editor
This commit is contained in:
parent
6e3abbde41
commit
e5e1fc180e
3 changed files with 425 additions and 0 deletions
|
@ -3,6 +3,7 @@ members = [
|
|||
"nested",
|
||||
"terminal/display_server",
|
||||
"terminal/ansi_parser",
|
||||
"shell",
|
||||
"math/str2int",
|
||||
"math/int2str",
|
||||
"math/radix_transform",
|
||||
|
|
13
shell/Cargo.toml
Normal file
13
shell/Cargo.toml
Normal file
|
@ -0,0 +1,13 @@
|
|||
[package]
|
||||
name = "shell"
|
||||
version = "0.1.0"
|
||||
edition = "2018"
|
||||
|
||||
[dependencies]
|
||||
nested = { path = "../nested" }
|
||||
cgmath = "*"
|
||||
termion = "*"
|
||||
|
||||
[dependencies.async-std]
|
||||
version = "1.9.0"
|
||||
features = ["unstable", "attributes"]
|
411
shell/src/main.rs
Normal file
411
shell/src/main.rs
Normal file
|
@ -0,0 +1,411 @@
|
|||
use {
|
||||
std::sync::RwLock,
|
||||
cgmath::Point2,
|
||||
termion::event::{Event, Key},
|
||||
nested::{
|
||||
core::{
|
||||
ViewPort,
|
||||
OuterViewPort,
|
||||
context::{
|
||||
ReprTree,
|
||||
Object,
|
||||
MorphismType,
|
||||
MorphismMode,
|
||||
Context
|
||||
},
|
||||
port::{
|
||||
UpdateTask
|
||||
}
|
||||
},
|
||||
sequence::{SequenceView, VecBuffer},
|
||||
integer::{RadixProjection},
|
||||
terminal::{Terminal, TerminalAtom, TerminalStyle, TerminalCompositor, TerminalEvent},
|
||||
string_editor::StringEditor
|
||||
}
|
||||
};
|
||||
|
||||
#[async_std::main]
|
||||
async fn main() {
|
||||
/* todo:
|
||||
|
||||
open::
|
||||
>0:
|
||||
( Path )
|
||||
( Sequence ( Sequence UnicodeChar ) )
|
||||
( Sequence UnicodeChar )
|
||||
<1:
|
||||
( FileDescriptor )
|
||||
( MachineInt )
|
||||
|
||||
read::
|
||||
>0:
|
||||
( FileDescriptor )
|
||||
( MachineInt )
|
||||
<1:
|
||||
( Sequence MachineSyllab )
|
||||
( Vec MachineSyllab )
|
||||
|
||||
write::
|
||||
>0
|
||||
( FileDescriptor )
|
||||
( MachineInt )
|
||||
>1:
|
||||
( Sequence MachineSyllab )
|
||||
( Vec MachineSyllab )
|
||||
|
||||
*/
|
||||
|
||||
let mut args = std::env::args();
|
||||
|
||||
let arg0_port = ViewPort::new();
|
||||
let _arg0 = VecBuffer::<char>::with_data(
|
||||
args.next().expect("Arg $0 missing!")
|
||||
.chars().collect::<Vec<char>>(),
|
||||
arg0_port.inner()
|
||||
);
|
||||
/*
|
||||
let arg1_vec_port = ViewPort::new();
|
||||
let mut arg1 = VecBuffer::<char>::with_data(
|
||||
args.next().expect("Arg $1 missing!")
|
||||
.chars().collect::<Vec<char>>(),
|
||||
arg1_vec_port.inner()
|
||||
);
|
||||
*/
|
||||
|
||||
let arg1_vec = args.next().expect("Arg $1 missing!")
|
||||
.chars().collect::<Vec<char>>();
|
||||
|
||||
let term_port = ViewPort::new();
|
||||
let compositor = TerminalCompositor::new(term_port.inner());
|
||||
|
||||
let mut ed = StringEditor::new();
|
||||
|
||||
let mut term = Terminal::new(term_port.outer());
|
||||
let term_writer = term.get_writer();
|
||||
|
||||
async_std::task::spawn(
|
||||
async move {
|
||||
let mut ctx = Context::new();
|
||||
for tn in vec![
|
||||
"MachineWord", "MachineInt", "MachineSyllab", "Bits",
|
||||
"Vec", "Stream", "Json",
|
||||
"Sequence", "UTF-8-String", "UnicodeChar",
|
||||
"PositionalInt", "Digit", "LittleEndian", "BigEndian",
|
||||
"DiffStream", "ℕ"
|
||||
] { ctx.add_typename(tn.into()); }
|
||||
|
||||
let src_type =
|
||||
ctx.type_term_from_str("( Vec UnicodeChar )").unwrap();
|
||||
|
||||
let dst_type =
|
||||
ctx.type_term_from_str("( Sequence UnicodeChar )").unwrap();
|
||||
|
||||
ctx.add_morphism(
|
||||
MorphismType {
|
||||
mode: MorphismMode::Epi,
|
||||
src_type: src_type.clone(),
|
||||
dst_type: dst_type.clone()
|
||||
},
|
||||
Box::new(move |src| {
|
||||
assert!(src.type_tag == src_type);
|
||||
Object {
|
||||
type_tag: dst_type.clone(),
|
||||
repr: ReprTree::new_leaf(
|
||||
src.get_port::<RwLock<Vec<char>>>().unwrap()
|
||||
.to_sequence()
|
||||
.into()
|
||||
)
|
||||
}
|
||||
})
|
||||
);
|
||||
|
||||
let src_type = ctx.type_term_from_str("( Sequence UnicodeChar )").unwrap();
|
||||
let dst_type = ctx.type_term_from_str("( Sequence ( Bits 32 ) )").unwrap();
|
||||
ctx.add_morphism(
|
||||
MorphismType {
|
||||
mode: MorphismMode::Mono,
|
||||
src_type: src_type.clone(),
|
||||
dst_type: dst_type.clone()
|
||||
},
|
||||
Box::new({
|
||||
move |src| {
|
||||
assert!(src.type_tag == src_type);
|
||||
Object {
|
||||
type_tag: dst_type.clone(),
|
||||
repr: ReprTree::new_leaf(
|
||||
src.get_port::<dyn SequenceView<Item = char>>().unwrap()
|
||||
.map(
|
||||
|c| *c as u32
|
||||
)
|
||||
.into()
|
||||
)
|
||||
}
|
||||
}
|
||||
})
|
||||
);
|
||||
|
||||
/*
|
||||
let src_type = vec![
|
||||
ctx.type_term_from_str("( PositionalInteger )").unwrap(),
|
||||
];
|
||||
let dst_type = ctx.type_term_from_str("( Sequence MachineInt )").unwrap();
|
||||
ctx.add_morphism(
|
||||
MorphismType {
|
||||
mode: MorphismMode::Epi,
|
||||
src_type: src_type.clone(),
|
||||
dst_type: dst_type.clone()
|
||||
},
|
||||
Box::new({
|
||||
move |src| {
|
||||
assert!(src.type_tag == src_type);
|
||||
Object {
|
||||
type_tag: dst_type.clone(),
|
||||
repr: ReprTree::new_leaf(
|
||||
vec![ dst_type.clone() ].into_iter(),
|
||||
src.get_port::<RwLock<Vec<usize>>>().unwrap().to_sequence().into()
|
||||
)
|
||||
}
|
||||
}
|
||||
})
|
||||
);
|
||||
*/
|
||||
|
||||
let arg1_vec_port = ed.get_data_port();
|
||||
|
||||
ctx.add_obj("$1".into(), "( Vec UnicodeChar )");
|
||||
ctx.insert_repr(
|
||||
"$1",
|
||||
vec![].into_iter(),
|
||||
arg1_vec_port.clone().into()
|
||||
);
|
||||
|
||||
ctx.epi_cast("$1", "( Sequence UnicodeChar )");
|
||||
ctx.epi_cast("$1", "( Sequence ( Digit 10 ) )");
|
||||
ctx.epi_cast("$1", "( PositionalInt 10 LittleEndian )");
|
||||
ctx.epi_cast("$1", "( ℕ )");
|
||||
|
||||
let arg1_dec_unic_port: OuterViewPort<dyn SequenceView<Item = char>> =
|
||||
ctx.mono_view(
|
||||
"$1",
|
||||
vec![
|
||||
"( PositionalInt 10 LittleEndian )",
|
||||
"( Sequence ( Digit 10 ) )",
|
||||
"( Sequence UnicodeChar )"
|
||||
].into_iter()
|
||||
).unwrap();
|
||||
|
||||
let arg1_dec_mint_port: OuterViewPort<dyn SequenceView<Item = usize>> =
|
||||
arg1_dec_unic_port
|
||||
.map(|c| c.to_digit(10).map(|x| x as usize))
|
||||
.filter(|d| d.is_some())
|
||||
.map(|d| d.unwrap());
|
||||
|
||||
ctx.insert_repr(
|
||||
"$1",
|
||||
vec![
|
||||
"( PositionalInt 10 LittleEndian )",
|
||||
"( Sequence ( Digit 10 ) )",
|
||||
"( Sequence MachineInt )"
|
||||
].into_iter(),
|
||||
arg1_dec_mint_port.clone().into()
|
||||
);
|
||||
|
||||
let arg1_hex_mint_port: ViewPort<RwLock<Vec<usize>>>
|
||||
= ViewPort::new();
|
||||
let _radix_proj = RadixProjection::new(
|
||||
10,
|
||||
16,
|
||||
arg1_dec_mint_port.clone(),
|
||||
arg1_hex_mint_port.inner()
|
||||
);
|
||||
|
||||
ctx.insert_repr(
|
||||
"$1",
|
||||
vec![
|
||||
"( PositionalInt 16 LittleEndian )",
|
||||
"( Sequence ( Digit 16 ) )",
|
||||
"( Sequence MachineInt )"
|
||||
].into_iter(),
|
||||
arg1_hex_mint_port.outer().to_sequence().into()
|
||||
);
|
||||
|
||||
let arg1_hex_unic_port: OuterViewPort<dyn SequenceView<Item = char>> =
|
||||
arg1_hex_mint_port.outer().to_sequence()
|
||||
.map(
|
||||
|d| char::from_digit(*d as u32, 16).unwrap()
|
||||
);
|
||||
|
||||
ctx.insert_repr(
|
||||
"$1",
|
||||
vec![
|
||||
"( PositionalInt 16 LittleEndian )",
|
||||
"( Sequence ( Digit 16 ) )",
|
||||
"( Sequence UnicodeChar )"
|
||||
].into_iter(),
|
||||
arg1_hex_unic_port.clone().into()
|
||||
);
|
||||
|
||||
compositor.write().unwrap().push(
|
||||
ed.insert_view()
|
||||
.map_key(
|
||||
|pt| Point2::new(40 as i16 - pt.x, 1 as i16),
|
||||
|pt| if pt.y == 1 { Some(Point2::new(40 as i16 - pt.x, 0)) } else { None }
|
||||
)
|
||||
.map_item(
|
||||
|_pos, atom|
|
||||
TerminalAtom::new(
|
||||
atom.c.unwrap_or(' '),
|
||||
TerminalStyle::fg_color(
|
||||
if let Some(c) = atom.c {
|
||||
if c == '|' {
|
||||
(200, 200, 90)
|
||||
} else if c.is_digit(10) {
|
||||
(0, 200, 0)
|
||||
} else {
|
||||
(255, 0, 0)
|
||||
}
|
||||
} else {
|
||||
(0, 0, 0)
|
||||
}
|
||||
)
|
||||
)
|
||||
)
|
||||
);
|
||||
|
||||
let opening_port = ViewPort::new();
|
||||
let opening = VecBuffer::<char>::with_data("]".chars().collect(), opening_port.inner());
|
||||
|
||||
let dec_label_port = ViewPort::new();
|
||||
let dec_label = VecBuffer::<char>::with_data("d0".chars().collect(), dec_label_port.inner());
|
||||
|
||||
let hex_label_port = ViewPort::new();
|
||||
let hex_label = VecBuffer::<char>::with_data("x0".chars().collect(), hex_label_port.inner());
|
||||
|
||||
let delim_port = ViewPort::new();
|
||||
let delim = VecBuffer::<char>::with_data(" ,".chars().collect(), delim_port.inner());
|
||||
|
||||
let closing_port = ViewPort::new();
|
||||
let closing = VecBuffer::<char>::with_data("[".chars().collect(), closing_port.inner());
|
||||
for c in arg1_vec {
|
||||
ed.insert(c);
|
||||
ed.prev();
|
||||
}
|
||||
|
||||
{
|
||||
let tree_port = ViewPort::new();
|
||||
let mut tree = VecBuffer::with_data(
|
||||
vec![
|
||||
opening_port.outer()
|
||||
.to_sequence()
|
||||
.map(|c| TerminalAtom::new(*c, TerminalStyle::fg_color((170, 170, 30)))),
|
||||
|
||||
arg1_dec_mint_port
|
||||
.map(|val| char::from_digit(*val as u32, 16).unwrap())
|
||||
.map(|c| TerminalAtom::new(*c, TerminalStyle::fg_color((255, 255, 255)))),
|
||||
|
||||
dec_label_port.outer()
|
||||
.to_sequence()
|
||||
.map(|c| TerminalAtom::new(*c, TerminalStyle::fg_color((170, 170, 170)))),
|
||||
|
||||
delim_port.outer()
|
||||
.to_sequence()
|
||||
.map(|c| TerminalAtom::new(*c, TerminalStyle::fg_color((170, 170, 30)))),
|
||||
|
||||
arg1_hex_unic_port.clone()
|
||||
.map(|c| TerminalAtom::new(*c, TerminalStyle::fg_color((255, 255, 255)))),
|
||||
|
||||
hex_label_port.outer()
|
||||
.to_sequence()
|
||||
.map(|c| TerminalAtom::new(*c, TerminalStyle::fg_color((170, 170, 170)))),
|
||||
|
||||
closing_port.outer()
|
||||
.to_sequence()
|
||||
.map(|c| TerminalAtom::new(*c, TerminalStyle::fg_color((170, 170, 30)))),
|
||||
],
|
||||
tree_port.inner()
|
||||
);
|
||||
|
||||
compositor.write().unwrap().push(
|
||||
tree_port.outer()
|
||||
.to_sequence()
|
||||
.flatten()
|
||||
.to_index()
|
||||
.map_key(
|
||||
|idx| Point2::new(40 - *idx as i16, 2 as i16),
|
||||
|pt| if pt.y == 2 { Some(40 - pt.x as usize) } else { None }
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
compositor.write().unwrap().push(
|
||||
arg1_hex_unic_port
|
||||
.to_index()
|
||||
.map_key(
|
||||
|idx| Point2::new(40 - *idx as i16, 3 as i16),
|
||||
|pt| if pt.y == 3 { Some(40 - pt.x as usize) } else { None }
|
||||
)
|
||||
.map_item(
|
||||
|_idx, digit| TerminalAtom::from(digit)
|
||||
)
|
||||
);
|
||||
|
||||
let magic_vec_port = ViewPort::new();
|
||||
let _magic_vec = VecBuffer::with_data("<<<<>>>><<>><><<>><<<*>>><<>><><<>><<<<>>>>".chars().collect::<Vec<char>>(), magic_vec_port.inner());
|
||||
|
||||
compositor.write().unwrap().push(
|
||||
magic_vec_port.outer()
|
||||
.to_sequence()
|
||||
.to_index()
|
||||
.map_item(
|
||||
|idx, c| TerminalAtom::new(
|
||||
*c,
|
||||
TerminalStyle::fg_color((5, ((80+(idx*30)%100) as u8), (55+(idx*15)%180) as u8))
|
||||
)
|
||||
)
|
||||
.map_key(
|
||||
|idx| Point2::new(*idx as i16, 4),
|
||||
|pt| if pt.y == 4 { Some(pt.x as usize) } else { None }
|
||||
)
|
||||
);
|
||||
|
||||
compositor.write().unwrap().push(
|
||||
magic_vec_port.outer()
|
||||
.to_sequence()
|
||||
.to_index()
|
||||
.map_item(
|
||||
|idx, c| TerminalAtom::new(
|
||||
*c,
|
||||
TerminalStyle::fg_color((5, ((80+(idx*30)%100) as u8), (55+(idx*15)%180) as u8))
|
||||
)
|
||||
)
|
||||
.map_key(
|
||||
|idx| Point2::new(*idx as i16, 0),
|
||||
|pt| if pt.y == 0 { Some(pt.x as usize) } else { None }
|
||||
)
|
||||
);
|
||||
|
||||
term_port.update();
|
||||
|
||||
loop {
|
||||
match term.next_event().await {
|
||||
TerminalEvent::Input(Event::Key(Key::Left)) => ed.next(),
|
||||
TerminalEvent::Input(Event::Key(Key::Right)) => ed.prev(),
|
||||
TerminalEvent::Input(Event::Key(Key::Home)) => ed.goto_end(),
|
||||
TerminalEvent::Input(Event::Key(Key::End)) => ed.goto(0),
|
||||
TerminalEvent::Input(Event::Key(Key::Char('\n'))) => {},
|
||||
TerminalEvent::Input(Event::Key(Key::Char(c))) => { ed.insert(c); ed.prev() },
|
||||
TerminalEvent::Input(Event::Key(Key::Delete)) => ed.delete_prev(),
|
||||
TerminalEvent::Input(Event::Key(Key::Backspace)) => ed.delete(),
|
||||
TerminalEvent::Input(Event::Key(Key::Ctrl('c'))) => break,
|
||||
_ => {}
|
||||
}
|
||||
term_port.update();
|
||||
}
|
||||
|
||||
drop(term);
|
||||
}
|
||||
);
|
||||
|
||||
term_writer.show().await.expect("output error!");
|
||||
}
|
||||
|
Loading…
Reference in a new issue