diff options
Diffstat (limited to 'src/lisp')
-rw-r--r-- | src/lisp/error.rs | 2 | ||||
-rw-r--r-- | src/lisp/prelude.rs | 15 |
2 files changed, 16 insertions, 1 deletions
diff --git a/src/lisp/error.rs b/src/lisp/error.rs index f323bb8..9e9dc90 100644 --- a/src/lisp/error.rs +++ b/src/lisp/error.rs | |||
@@ -98,6 +98,7 @@ pub enum EvalError { | |||
98 | DivByZero, | 98 | DivByZero, |
99 | TypeMismatch, | 99 | TypeMismatch, |
100 | NoFileName, | 100 | NoFileName, |
101 | FileError(io::Error), | ||
101 | AccessEmptyList, | 102 | AccessEmptyList, |
102 | InvalidCoordinates((LispNumber, LispNumber)), | 103 | InvalidCoordinates((LispNumber, LispNumber)), |
103 | AssertionError { expected: LispExpr, got: LispExpr }, | 104 | AssertionError { expected: LispExpr, got: LispExpr }, |
@@ -126,6 +127,7 @@ impl fmt::Display for EvalError { | |||
126 | Self::TypeMismatch => write!(f, "mismatched types"), | 127 | Self::TypeMismatch => write!(f, "mismatched types"), |
127 | Self::DivByZero => write!(f, "attempt to divide by zero"), | 128 | Self::DivByZero => write!(f, "attempt to divide by zero"), |
128 | Self::NoFileName => write!(f, "no file name specified"), | 129 | Self::NoFileName => write!(f, "no file name specified"), |
130 | Self::FileError(e) => write!(f, "file error: {}", e), | ||
129 | Self::AccessEmptyList => write!(f, "attempted to access empty list"), | 131 | Self::AccessEmptyList => write!(f, "attempted to access empty list"), |
130 | Self::InvalidCoordinates((x, y)) => write!(f, "invalid coordinates: {} {}", x, y), | 132 | Self::InvalidCoordinates((x, y)) => write!(f, "invalid coordinates: {} {}", x, y), |
131 | Self::AssertionError { expected, got } => { | 133 | Self::AssertionError { expected, got } => { |
diff --git a/src/lisp/prelude.rs b/src/lisp/prelude.rs index 7cb46ff..8088510 100644 --- a/src/lisp/prelude.rs +++ b/src/lisp/prelude.rs | |||
@@ -14,7 +14,7 @@ use crate::{ | |||
14 | utils::{load_script, rect_coords}, | 14 | utils::{load_script, rect_coords}, |
15 | }; | 15 | }; |
16 | 16 | ||
17 | use std::convert::TryInto; | 17 | use std::{convert::TryInto, fs::File, io::BufWriter, path::Path}; |
18 | 18 | ||
19 | #[macro_export] | 19 | #[macro_export] |
20 | macro_rules! primitive { | 20 | macro_rules! primitive { |
@@ -260,6 +260,18 @@ pub fn new_env() -> Result<Environment, LispError> { | |||
260 | } | 260 | } |
261 | }); | 261 | }); |
262 | 262 | ||
263 | primitive!(env, Arity::Exact(1), "export-png", |args, app| { | ||
264 | if let LispExpr::StringLit(s) = &args[0] { | ||
265 | let export_path = Path::new(&s); | ||
266 | let file = File::create(export_path).map_err(EvalError::FileError)?; | ||
267 | let w = BufWriter::new(file); | ||
268 | app.export().write_png(w); | ||
269 | Ok(LispExpr::Unit) | ||
270 | } else { | ||
271 | Err(EvalError::TypeMismatch.into()) | ||
272 | } | ||
273 | }); | ||
274 | |||
263 | primitive!(env, Arity::Exact(0), "grid-enabled?", |_, app| { | 275 | primitive!(env, Arity::Exact(0), "grid-enabled?", |_, app| { |
264 | Ok(LispExpr::BoolLit(app.grid.enabled)) | 276 | Ok(LispExpr::BoolLit(app.grid.enabled)) |
265 | }); | 277 | }); |
@@ -524,5 +536,6 @@ pub fn new_env() -> Result<Environment, LispError> { | |||
524 | primitive!(env, Arity::Exact(1), "id", |args, _| { | 536 | primitive!(env, Arity::Exact(1), "id", |args, _| { |
525 | Ok(args[0].clone()) | 537 | Ok(args[0].clone()) |
526 | }); | 538 | }); |
539 | |||
527 | Ok(env) | 540 | Ok(env) |
528 | } | 541 | } |