diff --git a/justfile b/justfile index 6aacdfe..063793e 100644 --- a/justfile +++ b/justfile @@ -1,3 +1,6 @@ # start a repl repl: - clj -X:repl \ No newline at end of file + clj -X:repl + +build: + shadow-cljs release node diff --git a/package.json b/package.json index 41e03a0..095ff81 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "@ludus/ludus-js-pure", - "version": "0.1.0-alpha.5", + "version": "0.1.0-alpha.7.6", "description": "A Ludus interpreter in a pure JS function.", "main": "target/js/ludus.js", "directories": {}, diff --git a/src/ludus/error.cljc b/src/ludus/error.cljc index 4fddd3b..548087d 100644 --- a/src/ludus/error.cljc +++ b/src/ludus/error.cljc @@ -12,7 +12,7 @@ line-start (reduce (fn [len line] (+ len (count line))) (count lines-before) lines-before) from-start (- start line-start) underline-length (count lexeme) - padding (string/join (take (+ prefix from-start) (repeat " "))) + padding (string/join (take (+ prefix from-start) (repeat "-"))) underline (string/join (take underline-length (repeat "^")))] (apply str padding underline) )) @@ -31,3 +31,9 @@ (str message "\n" prefix line "\n" underline) ) ) + +(defn run-error [source {:keys [line message]}] + (if line + (str "Ludus panicked on line " line ":\n" (get-line source {:line line}) "\n" message) + (str "Ludus panicked!\n" message) + )) diff --git a/src/ludus/interpreter.cljc b/src/ludus/interpreter.cljc index 59e24cd..516d69b 100644 --- a/src/ludus/interpreter.cljc +++ b/src/ludus/interpreter.cljc @@ -302,7 +302,7 @@ (if (= match-value value) {:success true :ctx {}} {:success false - :reason (str "No match: Could not match " (show/show-pattern match-value) " with " (show/show value))})) + :reason (str "No match: Could not match " (show/show-pattern pattern) " with " (show/show value))})) :word (let [word (-> pattern :data first)] @@ -965,10 +965,10 @@ ;(println "Running source: " source) (interpret-ast parsed base-ctx) (catch #?(:clj Throwable :cljs js/Object) e - (println "Ludus panicked!") - (println "On line" (get-in (ex-data e) [:ast :token :line])) - (println ">>> " (get-line source (get-in (ex-data e) [:ast :token :line]))) - (println (ex-message e)) + ;(println "Ludus panicked!") + ;(println "On line" (get-in (ex-data e) [:ast :token :line])) + ;(println ">>> " (get-line source (get-in (ex-data e) [:ast :token :line]))) + ;(println (ex-message e)) ;(pp/pprint (ex-data e)) ;(throw e) {::data/error true diff --git a/src/ludus/node.cljc b/src/ludus/node.cljc index f5a8fdd..163e2ef 100644 --- a/src/ludus/node.cljc +++ b/src/ludus/node.cljc @@ -51,7 +51,7 @@ (clean-out {:errors [(error/parse-error source user_parsed)]}) (::data/error user_result) - (clean-out {:errors [user_result]}) + (clean-out (assoc (ld->clj post_result) :errors [(error/run-error source user_result)])) :else (clean-out clj_result) diff --git a/src/ludus/prelude.ld b/src/ludus/prelude.ld index 476394e..1c02570 100644 --- a/src/ludus/prelude.ld +++ b/src/ludus/prelude.ld @@ -256,7 +256,10 @@ fn string { "Converts a value to a string by using `show`. If it is a string, returns it unharmed. Use this to build up strings of differen kinds of values." (x as :string) -> x (x) -> show (x) - (x, ...xs) -> fold (string, xs, x) + (x, ...xs) -> loop (x, xs) with { + (out, [x]) -> concat (out, show(x)) + (out, [x, ...xs]) -> recur (concat (out, show (x)), xs) + } } fn join { @@ -887,31 +890,32 @@ fn make_line ((x1, y1), (x2, y2)) -> (:line, x1, y1, x2, y2) let turtle_radius = 20 -let turtle_angle = 0.375 +let turtle_angle = 0.385 -let turtle_color = (150, 150, 150, 200) +let turtle_color = (255, 255, 255, 150) fn render_turtle! () -> { let state = do turtle_states > deref > last if state :visible? then { - add_call! ((:push)) let (r, g, b, a) = turtle_color add_call! ((:fill, r, g, b, a)) - add_call! ((:noStroke)) let #{heading, :position (x, y)} = state - add_call! ((:translate, x, y)) - add_call! ((:rotate, turn/rad (add (heading, 0.25)))) - add_call! ((:beginShape)) - let head_unit = heading/vector (heading) - let first = mult (head_unit, turtle_radius) + let first = mult ((0, 1), turtle_radius) let (x1, y1) = first let (x2, y2) = rotate (first, turtle_angle) let (x3, y3) = rotate (first, neg (turtle_angle)) + add_call! ((:push)) + add_call! ((:translate, x, y)) + add_call! ((:rotate, turn/rad (heading))) + add_call! ((:noStroke)) + add_call! ((:beginShape)) add_call! ((:vertex, x1, y1)) add_call! ((:vertex, x2, y2)) add_call! ((:vertex, x3, y3)) add_call! ((:endShape)) + add_call! ((:stroke, 0)) + add_call! ((:line, 0, 0, x1, y1)) add_call! ((:pop)) :ok } @@ -1046,8 +1050,8 @@ fn apply_command { (:goto, (x, y)) -> assoc (state, :position, (x, y)) (:home) -> assoc (state, :position, (0, 0)) (:clear) -> assoc (state, :position, (0, 0)) - (:right, turns) -> update (state, :heading, sub (_, turns)) - (:left, turns) -> update (state, :heading, add (_, turns)) + (:right, turns) -> update (state, :heading, add (_, turns)) + (:left, turns) -> update (state, :heading, sub (_, turns)) (:forward, steps) -> { let #{heading, position} = state let unit = heading/vector (heading) @@ -1208,6 +1212,7 @@ ns prelude { penup!, pu! pendown!, pd! pencolor!, pc! + background!, bg! penwidth!, pw! home!, clear!, goto!, heading, position, pendown? diff --git a/src/ludus/show.cljc b/src/ludus/show.cljc index 064fe7c..0ac637a 100644 --- a/src/ludus/show.cljc +++ b/src/ludus/show.cljc @@ -1,6 +1,10 @@ (ns ludus.show (:require [ludus.data :as data] + ; [ludus.scanner :as s] + ; [ludus.parser :as p] + ; [ludus.grammar :as g] + ; [ludus.interpreter :as i] [clojure.pprint :as pp])) (declare show show-linear show-keyed) @@ -75,7 +79,7 @@ :else "else" - (:word :number :keyword :true :false :nil :string) (-> pattern :data first) + (:word :number :keyword :true :false :nil :string) (-> pattern :data first show) :typed (let [word (-> pattern :data first :data first) @@ -100,3 +104,11 @@ :struct-pattern (show-coll-pattern pattern ["@{" "}"]) )) + +(comment + (def source "let 1 = 0") + (def tokens (-> source s/scan :tokens)) + (def ast (p/apply-parser g/script tokens)) + (println (i/prettify-ast ast)) + (println (-> ast :data first :data first show-pattern)) + )