add quit, remove enums and rework parsing command
This commit is contained in:
parent
fb9bfdeda8
commit
ccc536ec6a
3 changed files with 162 additions and 117 deletions
|
@ -1,14 +1,4 @@
|
||||||
use std::env;
|
|
||||||
use std::fs::File;
|
|
||||||
use std::io::BufReader;
|
|
||||||
use std::io::prelude::*;
|
|
||||||
use std::io;
|
use std::io;
|
||||||
use nom::bytes::complete::{tag, take_while, take_till};
|
|
||||||
use nom::character::complete::one_of;
|
|
||||||
use nom::sequence::Tuple;
|
|
||||||
use nom::branch::alt;
|
|
||||||
use nom::error::ErrorKind;
|
|
||||||
use nom::error::Error;
|
|
||||||
|
|
||||||
pub struct Buffer {
|
pub struct Buffer {
|
||||||
has_changed: bool,
|
has_changed: bool,
|
||||||
|
|
117
src/enums.rs
Normal file
117
src/enums.rs
Normal file
|
@ -0,0 +1,117 @@
|
||||||
|
#[derive(Debug)]
|
||||||
|
pub enum Address {
|
||||||
|
Actual,
|
||||||
|
Last,
|
||||||
|
Line(u32),
|
||||||
|
FromStartTo(u32),
|
||||||
|
FromToEnd(u32),
|
||||||
|
FromTo(u32, u32),
|
||||||
|
Null,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Address {
|
||||||
|
pub fn is_null(&self) -> bool {
|
||||||
|
println!("{:?}", self);
|
||||||
|
match self {
|
||||||
|
Self::Null => true,
|
||||||
|
_ => false,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn parse_address(addr: &str) -> Address {
|
||||||
|
let mut tmp = String::from(addr);
|
||||||
|
tmp.retain(|c| c != ' ');
|
||||||
|
let addr = tmp.as_str();
|
||||||
|
|
||||||
|
if addr.is_empty() {
|
||||||
|
Address::Actual
|
||||||
|
} else {
|
||||||
|
match addr {
|
||||||
|
"." => Address::Actual,
|
||||||
|
"$" => Address::Last,
|
||||||
|
_ => Address::Null,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Debug)]
|
||||||
|
pub enum Command {
|
||||||
|
ChangeAddr(Address),
|
||||||
|
|
||||||
|
Append(Address),
|
||||||
|
Insert(Address),
|
||||||
|
Change(Address),
|
||||||
|
Delete(Address),
|
||||||
|
// bool pour check ou pas (e et E) TODO mettre le chemin vers le fichier
|
||||||
|
Edit(bool),
|
||||||
|
// TODO chemin vers fichier
|
||||||
|
File(),
|
||||||
|
// TODO
|
||||||
|
Help,
|
||||||
|
// TODO
|
||||||
|
SetHelp,
|
||||||
|
Join(Address),
|
||||||
|
// TODO nom de la marque
|
||||||
|
Mark(Address),
|
||||||
|
List(Address),
|
||||||
|
// TODO
|
||||||
|
Move(Address),
|
||||||
|
Number(Address),
|
||||||
|
Print(Address),
|
||||||
|
Prompt,
|
||||||
|
// bool pour check ou pas (q et Q)
|
||||||
|
Quit(bool),
|
||||||
|
// TODO
|
||||||
|
Read,
|
||||||
|
// TODO
|
||||||
|
Substitute,
|
||||||
|
// TODO
|
||||||
|
CopyLines,
|
||||||
|
Undo,
|
||||||
|
// TODO
|
||||||
|
Write,
|
||||||
|
// TODO
|
||||||
|
Line,
|
||||||
|
// TODO
|
||||||
|
ShellCommand,
|
||||||
|
// TODO
|
||||||
|
Null,
|
||||||
|
// TODO
|
||||||
|
Global,
|
||||||
|
// TODO
|
||||||
|
NonMatched,
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
fn parse_without_addr(c: char) -> Command {
|
||||||
|
match c {
|
||||||
|
'q' => Command::Quit(false),
|
||||||
|
'Q' => Command::Quit(true),
|
||||||
|
_ => Command::Help,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
*/
|
||||||
|
|
||||||
|
fn parse(c: char, addr: Address) -> Command {
|
||||||
|
match c {
|
||||||
|
'p' => Command::Print(addr),
|
||||||
|
'n' => Command::Number(addr),
|
||||||
|
'q' => Command::Quit(false),
|
||||||
|
'Q' => Command::Quit(true),
|
||||||
|
_ => Command::Help,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn parse_command(c: char, addr: Address) -> Command {
|
||||||
|
parse(c, addr)
|
||||||
|
/*
|
||||||
|
if let Some(a) = addr {
|
||||||
|
println!("Ok");
|
||||||
|
parse_with_addr(c, a)
|
||||||
|
} else {
|
||||||
|
println!("No");
|
||||||
|
parse_without_addr(c)
|
||||||
|
}
|
||||||
|
*/
|
||||||
|
}
|
152
src/main.rs
152
src/main.rs
|
@ -1,5 +1,7 @@
|
||||||
mod buffer;
|
mod buffer;
|
||||||
|
mod enums;
|
||||||
pub use self::buffer::Buffer;
|
pub use self::buffer::Buffer;
|
||||||
|
pub use self::enums::{Address, Command, parse_address, parse_command};
|
||||||
|
|
||||||
use std::env;
|
use std::env;
|
||||||
use std::fs::File;
|
use std::fs::File;
|
||||||
|
@ -11,65 +13,10 @@ use nom::character::complete::one_of;
|
||||||
use nom::sequence::Tuple;
|
use nom::sequence::Tuple;
|
||||||
use nom::branch::alt;
|
use nom::branch::alt;
|
||||||
use nom::error::ErrorKind;
|
use nom::error::ErrorKind;
|
||||||
use nom::error::Error;
|
use nom::Err::Error;
|
||||||
|
|
||||||
const FILE : &'static str = "test";
|
const FILE : &'static str = "test";
|
||||||
|
|
||||||
enum Address {
|
|
||||||
Actual,
|
|
||||||
Last,
|
|
||||||
Line(u32),
|
|
||||||
FromStartTo(u32),
|
|
||||||
FromToEnd(u32),
|
|
||||||
FromTo(u32, u32),
|
|
||||||
Null,
|
|
||||||
}
|
|
||||||
|
|
||||||
enum Command {
|
|
||||||
Append(Address),
|
|
||||||
Insert(Address),
|
|
||||||
Change(Address),
|
|
||||||
Delete(Address),
|
|
||||||
// bool pour check ou pas (e et E) TODO mettre le chemin vers le fichier
|
|
||||||
Edit(bool),
|
|
||||||
// TODO chemin vers fichier
|
|
||||||
File(),
|
|
||||||
// TODO
|
|
||||||
Help,
|
|
||||||
// TODO
|
|
||||||
SetHelp,
|
|
||||||
Join(Address),
|
|
||||||
// TODO nom de la marque
|
|
||||||
Mark(Address),
|
|
||||||
List(Address),
|
|
||||||
// TODO
|
|
||||||
Move(Address),
|
|
||||||
Number(Address),
|
|
||||||
Print(Address),
|
|
||||||
Prompt,
|
|
||||||
// bool pour check ou pas (q et Q)
|
|
||||||
Quit(bool),
|
|
||||||
// TODO
|
|
||||||
Read,
|
|
||||||
// TODO
|
|
||||||
Substitute,
|
|
||||||
// TODO
|
|
||||||
CopyLines,
|
|
||||||
Undo,
|
|
||||||
// TODO
|
|
||||||
Write,
|
|
||||||
// TODO
|
|
||||||
Line,
|
|
||||||
// TODO
|
|
||||||
ShellCommand,
|
|
||||||
// TODO
|
|
||||||
Null,
|
|
||||||
// TODO
|
|
||||||
Global,
|
|
||||||
// TODO
|
|
||||||
NonMatched,
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* .
|
* .
|
||||||
* $
|
* $
|
||||||
|
@ -84,6 +31,9 @@ enum Command {
|
||||||
|
|
||||||
// TODO juste $ pour l'instant dans l'adresse
|
// TODO juste $ pour l'instant dans l'adresse
|
||||||
// TODO faire les commandes mais juste p pour l'instant
|
// TODO faire les commandes mais juste p pour l'instant
|
||||||
|
// TODO faire un système de retour d'erreur pour afficher ? et l'erreur si l'utilisateur le demande
|
||||||
|
// (cad les fonctions pour parser retournent un Err et on peut parser ce Err pour voir le type de
|
||||||
|
// l'erreur, idem pour les fonctions d'exécutiosn ?)
|
||||||
|
|
||||||
/*
|
/*
|
||||||
fn read_address(input: &str) -> Result<&str, Address> {
|
fn read_address(input: &str) -> Result<&str, Address> {
|
||||||
|
@ -95,25 +45,6 @@ fn read_address(input: &str) -> Result<&str, Address> {
|
||||||
* Le char doit être une commande valide.
|
* Le char doit être une commande valide.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
fn parse_without_addr(c: char) -> Command {
|
|
||||||
Command::Help
|
|
||||||
}
|
|
||||||
|
|
||||||
fn parse_with_addr(c: char, addr: Address) -> Command {
|
|
||||||
match c {
|
|
||||||
'p' => Command::Print(addr),
|
|
||||||
'n' => Command::Number(addr),
|
|
||||||
_ => Command::Help,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fn parse_command(c: char, addr: Option<Address>) -> Command {
|
|
||||||
if let Some(a) = addr {
|
|
||||||
parse_with_addr(c, a)
|
|
||||||
} else {
|
|
||||||
parse_without_addr(c)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
fn parse_multi_addr(addr: &str) -> Address {
|
fn parse_multi_addr(addr: &str) -> Address {
|
||||||
|
@ -128,22 +59,6 @@ fn parse_multi_addr(addr: &str) -> Address {
|
||||||
}
|
}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
fn parse_address(addr: &str) -> Address {
|
|
||||||
let mut tmp = String::from(addr);
|
|
||||||
tmp.retain(|c| c != ' ');
|
|
||||||
let addr = tmp.as_str();
|
|
||||||
|
|
||||||
if addr.is_empty() {
|
|
||||||
Address::Actual
|
|
||||||
} else {
|
|
||||||
match addr {
|
|
||||||
"." => Address::Actual,
|
|
||||||
"$" => Address::Last,
|
|
||||||
_ => Address::Null,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fn check_address(c: char) -> bool {
|
fn check_address(c: char) -> bool {
|
||||||
c.is_digit(10) || c == '$' || c == ' ' || c == '.'
|
c.is_digit(10) || c == '$' || c == ' ' || c == '.'
|
||||||
}
|
}
|
||||||
|
@ -152,7 +67,7 @@ fn check_address_complete(c: char) -> bool {
|
||||||
check_address(c) || c == ','
|
check_address(c) || c == ','
|
||||||
}
|
}
|
||||||
|
|
||||||
fn print(buffer: Buffer, addr: Address, print_numbers: bool) {
|
fn print(buffer: &Buffer, addr: Address, print_numbers: bool) {
|
||||||
match addr {
|
match addr {
|
||||||
Address::Actual => buffer.print_line(buffer.act(), print_numbers),
|
Address::Actual => buffer.print_line(buffer.act(), print_numbers),
|
||||||
Address::Null => println!("nul !"),
|
Address::Null => println!("nul !"),
|
||||||
|
@ -160,24 +75,40 @@ fn print(buffer: Buffer, addr: Address, print_numbers: bool) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn execute_command(buffer: Buffer, c: Command) {
|
fn execute_command(buffer: &mut Buffer, c: Command) -> bool {
|
||||||
|
println!("coucou {:?}", c);
|
||||||
|
let mut ret = false;
|
||||||
|
|
||||||
match c {
|
match c {
|
||||||
Command::Print(a) => print(buffer, a, false),
|
Command::Print(a) => print(buffer, a, false),
|
||||||
Command::Number(a) => print(buffer, a, true),
|
Command::Number(a) => print(buffer, a, true),
|
||||||
|
Command::Quit(_) => ret = true,
|
||||||
_ => println!("coucou"),
|
_ => println!("coucou"),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ret
|
||||||
}
|
}
|
||||||
|
|
||||||
fn parse_line(input: &str) -> Result<Command, String> {
|
fn parse_line(input: &str) -> Result<Command, String> {
|
||||||
let address = take_while(check_address_complete);
|
let address = take_while(check_address_complete);
|
||||||
let command = one_of::<_, _, (&str, ErrorKind)>("pn");
|
let command = one_of::<_, _, (&str, ErrorKind)>("pnqQ");
|
||||||
|
|
||||||
//if let Ok((input, (a, c))) = alt(address, command).parse(input) {
|
//if let Ok((input, (a, c))) = alt(address, command).parse(input) {
|
||||||
if let Ok((input, (a, c))) = (address, command).parse(input) {
|
let tmp = (address, command).parse(input);
|
||||||
|
if let Ok((input, (a, c))) = tmp {
|
||||||
|
println!("Ok");
|
||||||
//println!("{:?} - {:?} - {:?}", input, a, c);
|
//println!("{:?} - {:?} - {:?}", input, a, c);
|
||||||
let addr = parse_address(a);
|
let addr = parse_address(a);
|
||||||
Ok(parse_command(c, Some(addr)))
|
Ok(parse_command(c, addr))
|
||||||
|
} else if let Err(Error(("bc", ErrorKind::OneOf))) = tmp {
|
||||||
|
//println!("{:?}", e);
|
||||||
|
println!("?");
|
||||||
|
Err(String::from("bruh moment"))
|
||||||
|
} else if let Err(Error((_, t))) = tmp {
|
||||||
|
println!("?");
|
||||||
|
Err(String::from("bruh moment"))
|
||||||
} else {
|
} else {
|
||||||
|
println!("bruh");
|
||||||
Err(String::from("bruh moment"))
|
Err(String::from("bruh moment"))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -190,19 +121,26 @@ fn main() {
|
||||||
panic!("Le fichier n'existe pas.");
|
panic!("Le fichier n'existe pas.");
|
||||||
};
|
};
|
||||||
|
|
||||||
let buffer_struct = Buffer::new(buffer);
|
let mut buffer_struct = Buffer::new(buffer);
|
||||||
|
|
||||||
println!("fichier lu !");
|
println!("fichier lu !");
|
||||||
|
let mut quit = false;
|
||||||
|
|
||||||
let mut input = String::new();
|
while !quit {
|
||||||
match io::stdin().read_line(&mut input) {
|
let mut input = String::new();
|
||||||
Ok(n) => {
|
match io::stdin().read_line(&mut input) {
|
||||||
if let Ok(c) = parse_line(&input) {
|
Ok(n) => {
|
||||||
execute_command(buffer_struct, c);
|
if let Ok(c) = parse_line(&input) {
|
||||||
} else {
|
let tmp = execute_command(&mut buffer_struct, c);
|
||||||
println!("coucou");
|
if tmp {
|
||||||
}
|
quit = true;
|
||||||
},
|
}
|
||||||
Err(e) => println!("error"),
|
} else {
|
||||||
|
println!("coucou");
|
||||||
|
}
|
||||||
|
},
|
||||||
|
Err(e) => println!("error"),
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue