From 3651b7fe18017544e8c8c83a37b160605ced5c4a Mon Sep 17 00:00:00 2001 From: Sander Hautvast Date: Mon, 8 Mar 2021 17:38:58 +0100 Subject: [PATCH] support for arrays and a shorthand for vector --- README.md | 6 +++++- src/js/functions.js | 2 +- src/js/index.js | 10 ++++++++++ src/js/parser.js | 20 ++++++++++++++++++-- src/js/scanner.js | 3 +++ 5 files changed, 37 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index 2dd6f6c..bb638bd 100644 --- a/README.md +++ b/README.md @@ -21,7 +21,11 @@ The repl has the following syntax (It's work in progress, new capabilities will ```a = vector(12, 1)``` > > vector@0{x0:0, y0: 2, x:12, y:1} * ```vector(1 2)``` works as well. The start is now the origin. - commas are not mandatory. I'm planning to add a more mathematical notation for vectors: ```[1 2]``` + commas are not mandatory. +* This means spaces are meaningful. + ```vector(-1 -1)``` != ```vector(-1-1)``` and the latter would mean ```vector(-2)``` which is not legal. +* arrays: \[i0 i1 i2 ... in] or \[i0, i1, i2, ... in] creates an array. + * \[i0 i1] is special: it is a shorthand for creating a vector. I'll have to think of another way to create an array of length 2... * properties * ```a = vector(12, 1)``` diff --git a/src/js/functions.js b/src/js/functions.js index 79dee63..5af6def 100644 --- a/src/js/functions.js +++ b/src/js/functions.js @@ -65,7 +65,7 @@ const help = function () { } } -const create_vector = function (x0, y0, x, y) { //rename to create_vector +export const create_vector = function (x0, y0, x, y) { //rename to create_vector const vector = { id: index_sequence++, x0: x0, diff --git a/src/js/index.js b/src/js/index.js index 9b2c19a..88cde53 100644 --- a/src/js/index.js +++ b/src/js/index.js @@ -4,6 +4,7 @@ import {parse} from './parser'; import {add_vector_arrow, add_vector_arrow_to_svg, update_vector_arrow} from "./svg_functions"; import { addition, + create_vector, division, functions, label, @@ -274,6 +275,15 @@ const visit = function (expr) { case 'reference': { return references[expr.name]; } + case 'array': { //unsure this is what I want + let array = expr.elements.map(x => x.value); + if (array.length === 2) { + return create_vector(0, 0, array[0], array[1]); + } else { + return array; + } + + } } } diff --git a/src/js/parser.js b/src/js/parser.js index 7d26670..efd8946 100644 --- a/src/js/parser.js +++ b/src/js/parser.js @@ -103,14 +103,13 @@ export const parse = function (tokens) { } else { throw {message: "Expect ')' after arguments."}; } - match([token_types.COMMA]); + match([token_types.COMMA, token_types.SPACE]); } while (!match([token_types.RIGHT_PAREN])); } return {type: 'call', name: callee, arguments: arguments_list}; } - function primary() { if (match([token_types.NUMERIC, token_types.STRING])) { return {type: 'literal', value: previous_token().value, value_type: previous_token().type}; @@ -147,6 +146,23 @@ export const parse = function (tokens) { }; advance(); return result; + } else if (match([token_types.LEFT_BRACKET])) { + let array = []; + if (!check(token_types.RIGHT_BRACKET, token_index)) { + let result; + do { + result = expression(); + if (result) { + array.push(result); + } else { + throw {message: "Expect ']' after array elements."}; + } + match([token_types.COMMA, token_types.SPACE]); + } while (!match([token_types.RIGHT_BRACKET])); + } + + return {type: 'array', elements: array}; + } } diff --git a/src/js/scanner.js b/src/js/scanner.js index 51055e7..d8f1b36 100644 --- a/src/js/scanner.js +++ b/src/js/scanner.js @@ -31,6 +31,8 @@ export const scan = function (command) { return token_types.RIGHT_BRACKET; case ',': return token_types.COMMA; + case ' ': + return token_types.SPACE; case '.': return token_types.DOT; case '-': @@ -192,6 +194,7 @@ export const token_types = { LEFT_BRACKET: {type: 'left_bracket'}, RIGHT_BRACKET: {type: 'right_bracket'}, COMMA: {type: 'comma'}, + SPACE: {type: 'space'}, DOT: {type: 'dot'}, MINUS: {type: 'minus'}, PLUS: {type: 'plus'},