From 5b5cfda05b07378211c78f93b5b55075ab683a82 Mon Sep 17 00:00:00 2001 From: Johannes Wolf Date: Sun, 21 Apr 2024 16:03:30 +0200 Subject: [PATCH] app: AnaGeo --- apps/{find_plane.lua => AnaGeo.lua} | 170 ++++++++++++++-------------- apps/init.lua | 5 +- config/config.lua | 8 +- 3 files changed, 94 insertions(+), 89 deletions(-) rename apps/{find_plane.lua => AnaGeo.lua} (73%) diff --git a/apps/find_plane.lua b/apps/AnaGeo.lua similarity index 73% rename from apps/find_plane.lua rename to apps/AnaGeo.lua index cb8f40e..31967b4 100644 --- a/apps/find_plane.lua +++ b/apps/AnaGeo.lua @@ -3,39 +3,46 @@ local matrix = require 'matrix' local advice = require 'advice' local ask = require('dialog.input').display_sync local choice = require('dialog.choice').display_sync -local choice = require('dialog.choice').display_sync local matrix_ed = require('rpn.matrixeditor').display_sync local expr = require 'expressiontree' local sym = require 'ti.sym' -local fn = require 'fn' +local fn = require 'fn' -local function table_to_vec(t) - local r = "" - for _, v in ipairs(t) do - r = r .. "[" .. v .. "]" - end - return "[" .. r .. "]" +-- Eval formatted string +local function E(fmt, ...) + return math.evalStr(string.format(fmt, ...)) end -local function ask_vector(title, dim) - dim = dim or 3 - while true do - local r = ask({title = title or 'Vector'}) - if not r then - return nil - end +-- Show results as cohice +local function show_results(ctrl, items) + table.insert(items, { title = 'Done', result = 'done', align = 0 }) - local v = {} - for c in r:gmatch("([^,]+)") do - table.insert(v, c) + local action + while not action do + action = choice({title = 'Results', items = items}) + if action == 'done' then + break + elseif type(action) == 'function' then + action = action(ctrl) end - - if #v == dim then - return v + if action ~= '*' then + ctrl:push_infix(action) + action = nil end end + return action +end + +-- Convert lua table to nspire column vector [[x][y]...] +local function table_to_vec(t) + local r = "" + for _, v in ipairs(t) do + r = r .. "[" .. v .. "]" + end + return "[" .. r .. "]" end +-- Ask for a list of n vectors of dimension dim using the matrix editor local function ask_n_vectors(ctrl, names, dim) local elems = {"x", "y", "z", "w"} local mat = matrix.new(4, 5) @@ -95,6 +102,7 @@ local function run_line_point(ctrl) if r_isection then table.insert(r, { title = 'Point on line', result = '*' }) table.insert(r, { title = 't: ' .. r_isection, result = r_isection, align = -1 }) + table.insert(r, { title = "Details...", result = "" }) else table.insert(r, { title = 'Point not on line', result = '*' }) table.insert(r, { title = 'Shortest distance: ' .. r_distance, result = r_distance, align = -1 }) @@ -103,18 +111,7 @@ local function run_line_point(ctrl) end -- Show results - table.insert(r, { title = 'Done', result = 'done' }) - while true do - local action = choice { - title = 'Results', - items = r, - } - if action == 'done' then - break - elseif action then - ctrl:push_infix(tostring(action)) - end - end + show_results(ctrl, r) end end @@ -133,7 +130,7 @@ local function run_line_line(ctrl) p1, p2, p1, n2, d1, n2, d1) local nearest2 = string.format("%s+(dotp(%s-%s,%s)/dotp(%s,%s))*%s", p2, p1, p2, n1, d2, n1, d2) - local distance = "norm(" .. nearest1 .. "-" .. nearest2 ..")" + local distance = "abs(norm(" .. nearest1 .. "-" .. nearest2 .."))" local angle = "arccos(abs(dotp(" .. d1 .. "," .. d2 .. "))/(norm(" .. d1 .. ")*norm(" .. d2 .. ")))" -- Results @@ -169,18 +166,7 @@ local function run_line_line(ctrl) end -- Show results - table.insert(r, { title = 'Done', result = 'done' }) - while true do - local action = choice { - title = 'Results', - items = r, - } - if action == 'done' then - break - elseif action then - ctrl:push_infix(tostring(action)) - end - end + show_results(ctrl, r) end end @@ -191,12 +177,12 @@ local function run_line_plane(ctrl) local parallel = "dotp(" .. n .. "," .. l .. ")=0" local angle = "arcsin(abs(dotp(" .. n .. "," .. l .. "))/(norm(" .. n .. ")*norm(" .. l .. ")))" local d = string.format("dotp((%s-%s),%s)/dotp(%s,%s)", p0, l0, n, l, n) - local dist = string.format("dotp((%s-%s),%s)/dotp(%s,%s)", p0, l0, n, n, n) + local dist = string.format("abs(dotp((%s-%s),%s))/dotp(%s,%s)", p0, l0, n, n, n) -- Results local r = {} local r_parallel = math.evalStr(parallel) == 'true' - + -- Collect results if not r_parallel then local r_d = math.evalStr(d) @@ -220,29 +206,50 @@ local function run_line_plane(ctrl) end -- Show results - table.insert(r, { title = 'Done', result = 'done' }) - while true do - local action = choice { - title = 'Results', - items = r, - } - if action == 'done' then - break - elseif action then - ctrl:push_infix(tostring(action)) - end - end + show_results(ctrl, r) end end -local function run_angle_2vec(ctrl, stack) - local a, b = table.unpack(fn.imap(ask_n_vectors(ctrl, {"a", "b"}), table_to_vec)) - stack:push_infix("arccos(dotp(" .. a .. "," .. b .. ")/(norm(" .. a .. ")*norm(" .. b .. "))") +local function run_plane_point(ctrl) + local p0, n, p = table.unpack(fn.imap(ask_n_vectors(ctrl, {"p0", "n", "p"}), table_to_vec)) + if p0 and n and p then + local signed_dist = E("dotp((%s-%s),%s)/dotp(%s,%s)", p0, p, n, n, n) + local abs_dist = E("abs(%s)", signed_dist) + local point = E("%s+%s*%s", p, signed_dist, n) + + -- Results + local r = {} + + table.insert(r, { title = 'Distance: ' .. abs_dist, result = abs_dist }) + table.insert(r, { title = 'Signed distance: ' .. signed_dist, result = signed_dist }) + table.insert(r, { title = 'Point on plane: ' .. point, result = point }) + + -- Show results + show_results(ctrl, r) + end end -local function run_dist_2pt(ctrl, stack) - local a, b = table.unpack(fn.imap(ask_n_vectors(ctrl, {"a", "b"}), table_to_vec)) - stack:push_infix("norm(" .. b .. "-" .. a .. ")") +local function run_plane_plane(ctrl) + local p0, n0, p1, n1 = table.unpack(fn.imap(ask_n_vectors(ctrl, {"p0", "n0", "p1", "n1"}), table_to_vec)) + if p0 and p1 then + local is_parallel = E("norm(crossp(%s,%s))=0", n0, n1) + print(is_parallel) + is_parallel = is_parallel == "true" + + -- Results + local r = {} + + if not is_parallel then + local angle = E("arccos(abs(dotp(%s,%s))/abs(norm(%s)*norm(%s)))", n0, n1, n0, n1) + table.insert(r, { title = 'Angle: ' .. angle, result = angle }) + --table.insert(r, { title = 'Intersection: ' .. intersection, result = intersection }) + else + local dist = E("abs(dotp((%s-%s),%s))/dotp(%s,%s)", p0, p1, n0, n0, n0) + table.insert(r, { title = 'Distance: ' .. dist, result = dist }) + end + + show_results(ctrl, r) + end end local function run_convert_plane(ctrl) @@ -299,25 +306,16 @@ local function run_convert_plane(ctrl) local r_vector = string.format("dotp((x-%s), %s)", p0, n) local r_vector_norm = string.format("dotp((x-%s), %s)", p0, math.evalStr(n .. "/norm(" .. n .. ")")) - while true do - local action = choice { - title = "Resutl", - items = { - { title = r_eq, result = r_eq }, - { title = r_vector, result = r_vector }, - { title = r_vector_norm, result = r_vector_norm }, - { title = 'Done', result = 'done' }, - } - } - if action == 'done' then - break - elseif action then - ctrl:push_infix(action) - end - end + show_results(ctrl, { + { title = r_eq, result = r_eq, align = -1 }, + { title = r_vector, result = r_vector, align = -1 }, + { title = r_vector_norm, result = r_vector_norm, align = -1 }, + }) end -apps.add('AnaGeo: line-point', 'line-point', run_line_point) -apps.add('AnaGeo: line-line', 'line-line', run_line_line) -apps.add('AnaGeo: line-plane', 'line-plane', run_line_plane) -apps.add('AnaGeo: convert plane', 'convert plane', run_convert_plane) +apps.add('AnaGeo: line-point', 'l-pt', run_line_point) +apps.add('AnaGeo: line-line', 'l-l', run_line_line) +apps.add('AnaGeo: line-plane', 'l-pl', run_line_plane) +apps.add('AnaGeo: plane-point', 'pl-pt', run_plane_point) +apps.add('AnaGeo: plane-plane', 'pl-pl', run_plane_plane) +apps.add('AnaGeo: convert plane', 'cnv-pl', run_convert_plane) diff --git a/apps/init.lua b/apps/init.lua index 1d455a3..1b0bfc3 100644 --- a/apps/init.lua +++ b/apps/init.lua @@ -4,6 +4,7 @@ require 'apps.app_trassierung' require 'apps.app_punktsteigung' require 'apps.app_triangle' require 'apps.app_constants' ---require 'apps.app_analyze_fn' -require 'apps.find_plane' require 'apps.app_binom' +--require 'apps.app_analyze_fn' + +require 'apps.AnaGeo' \ No newline at end of file diff --git a/config/config.lua b/config/config.lua index 02c7d96..3b72241 100644 --- a/config/config.lua +++ b/config/config.lua @@ -29,6 +29,12 @@ return { inf = sym.INFTY, oo = sym.INFTY, deg = sym.DEGREE, - to = sym.CONVERT + rad = sym.RAD, + to = sym.CONVERT, + leq = sym.LEQ, + geq = sym.GEQ, + neq = sym.NEQ, + ii = sym.IMAG, + ee = sym.EULER, } }