mirror of
https://github.com/NerdyPepper/eva
synced 2024-07-08 19:45:52 +00:00
parent
d31097959f
commit
ea95516537
|
@ -2,11 +2,16 @@
|
|||
* Refer to LICENCE for more information.
|
||||
* */
|
||||
|
||||
use std::iter::ExactSizeIterator;
|
||||
|
||||
use crate::lex;
|
||||
|
||||
#[derive(Debug)]
|
||||
pub enum CalcError {
|
||||
Math(Math),
|
||||
Syntax(String),
|
||||
Parser(String),
|
||||
Help,
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
|
@ -25,5 +30,42 @@ pub fn handler(e: CalcError) -> String {
|
|||
},
|
||||
CalcError::Syntax(details) => format!("Syntax Error: {}", details),
|
||||
CalcError::Parser(details) => format!("Parser Error: {}", details),
|
||||
CalcError::Help => format!(
|
||||
"Constants\n{}\nFunctions\n{}\nOperators\n{}\n",
|
||||
blocks(lex::CONSTANTS.keys().cloned()),
|
||||
blocks(lex::FUNCTIONS.keys().cloned()),
|
||||
{
|
||||
let l: Vec<_> = lex::OPERATORS.keys().map(|c| c.to_string()).collect();
|
||||
l.join(" ")
|
||||
}
|
||||
),
|
||||
}
|
||||
}
|
||||
|
||||
/// Convert iterator into strings of chunks of 8 right padded with space.
|
||||
fn blocks(mut iter: impl Iterator<Item = &'static str> + ExactSizeIterator) -> String {
|
||||
// calculate max width but ideally this should be calculated once
|
||||
let mut max_width = 79; // capped at 79
|
||||
if let Ok(s) = std::env::var("COLUMNS") {
|
||||
if let Ok(n) = s.parse() {
|
||||
if n < max_width {
|
||||
max_width = n;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// multiply by eight since we are formatting it into chunks of 8
|
||||
let items_per_line = max_width / 8;
|
||||
let full_bytes = (iter.len() - iter.len() % items_per_line) * 8;
|
||||
let part_bytes = iter.len() % items_per_line * 8; // leftovers
|
||||
let n_newlines = iter.len() / items_per_line + if part_bytes > 0 { 1 } else { 0 };
|
||||
let mut s = String::with_capacity(full_bytes + part_bytes + n_newlines);
|
||||
for _ in 0..n_newlines {
|
||||
for item in iter.by_ref().take(items_per_line) {
|
||||
s.extend(format!("{:>8}", item).chars());
|
||||
}
|
||||
s.push('\n');
|
||||
}
|
||||
debug_assert_eq!(s.capacity(), s.len()); // check capacity calculation
|
||||
s
|
||||
}
|
||||
|
|
|
@ -70,14 +70,14 @@ pub enum Token {
|
|||
}
|
||||
|
||||
lazy_static! {
|
||||
static ref CONSTANTS: HashMap<&'static str, Token> = {
|
||||
pub static ref CONSTANTS: HashMap<&'static str, Token> = {
|
||||
let mut m = HashMap::new();
|
||||
m.insert("e", Token::Num(std::f64::consts::E));
|
||||
m.insert("pi", Token::Num(std::f64::consts::PI));
|
||||
m
|
||||
};
|
||||
|
||||
static ref FUNCTIONS: HashMap<&'static str, Token> = {
|
||||
pub static ref FUNCTIONS: HashMap<&'static str, Token> = {
|
||||
let mut m = HashMap::new();
|
||||
m.insert("sin", Function::token_from_fn("sin".into(), |x| is_radian_mode(x, CONFIGURATION.radian_mode).sin()));
|
||||
m.insert("cos", Function::token_from_fn("cos".into(), |x| is_radian_mode(x, CONFIGURATION.radian_mode).cos()));
|
||||
|
@ -106,7 +106,7 @@ lazy_static! {
|
|||
m
|
||||
};
|
||||
|
||||
static ref OPERATORS: HashMap<char, Token> = {
|
||||
pub static ref OPERATORS: HashMap<char, Token> = {
|
||||
let mut m = HashMap::new();
|
||||
m.insert('+', Operator::token_from_op('+', |x, y| x + y, 2, true));
|
||||
m.insert('-', Operator::token_from_op('-', |x, y| x - y, 2, true));
|
||||
|
|
|
@ -193,7 +193,9 @@ fn parse_arguments() -> Configuration {
|
|||
|
||||
pub fn eval_math_expression(input: &str, prev_ans: Option<f64>) -> Result<f64, CalcError> {
|
||||
let input = input.trim();
|
||||
let input = input.replace(" ", "");
|
||||
if input == "help" {
|
||||
return Err(CalcError::Help);
|
||||
}
|
||||
if input.is_empty() {
|
||||
return Ok(0.);
|
||||
}
|
||||
|
|
|
@ -12,6 +12,7 @@ use directories::ProjectDirs;
|
|||
|
||||
use regex::Regex;
|
||||
|
||||
use crate::error::CalcError;
|
||||
use crate::eval_math_expression;
|
||||
|
||||
pub struct RLHelper {
|
||||
|
@ -67,6 +68,7 @@ impl Highlighter for LineHighlighter {
|
|||
}
|
||||
Owned(coloured)
|
||||
}
|
||||
Err(CalcError::Help) => Owned(line.replace("help", "\x1b[36mhelp\x1b[0m")),
|
||||
Err(_) => Owned(format!("\x1b[31m{}\x1b[0m", line)),
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue
Block a user