-- tkz_elements_functions_maths.lua
-- date 2023/11/10
-- version 1.20b
-- Copyright 2023  Alain Matthes
-- This work may be distributed and/or modified under the
-- conditions of the LaTeX Project Public License, either version 1.3
-- of this license or (at your option) any later version.
-- The latest version of this license is in
--   http://www.latex-project.org/lppl.txt
-- and version 1.3 or later is part of all distributions of LaTeX
-- version 2005/12/01 or later.
-- This work has the LPPL maintenance status “maintained”.
-- The Current Maintainer of this work is Alain Matthes.

-- constant
tkzphi      = (1+math.sqrt(5))/2
tkzinvphi   = (math.sqrt(5)-1)/2
tkzsqrtphi  =  math.sqrt(tkzphi)
---------------------------------------------------------------------------
function round(num, idp)
  return topoint(string.format("%." .. (idp or 0) .. "f", num))
end

function tkzround( num, idp )
	local mult = 10 ^ ( idp or 0 )
	return math.floor( num * mult + 0.5 ) / mult
end  

function dot_product (a,b,c)
   return (b-a)..(c-a)
end

function Cramer33(a1,a2,a3,b1,b2,b3,c1,c2,c3)
  return a1*b2*c3+a3*b1*c2+a2*b3*c1-a3*b2*c1-a1*b3*c2-a2*b1*c3
end

function Cramer22(a1,a2,b1,b2)
  return a1*b2-a2*b1
end

function aligned ( m,a,b )
    local z,epsilon
    epsilon = 10^(-8)
    z = (b-a)/(m-b)
      if math.abs(z.im) < epsilon
        then
            return true
        else
            return false
        end
end 

function islinear (z1,z2,z3)
     local epsilon
     local dp
     epsilon = 10^(-8)
    dp = (z2-z1) ^ (z3-z1)
    if math.abs(dp) < epsilon 
    then 
        return true
    else 
        return false
    end
end

function isortho (z1,z2,z3)
     local epsilon
     local dp
     epsilon = 10^(-8)
    dp = (z2-z1) .. (z3-z1)
    if math.abs(dp) < epsilon 
    then 
        return true
    else 
        return false
    end
end

function set_lua_to_tex (t)
   for k,v in pairs(t) do
    token.set_macro(v,_ENV[v],'global')
   end
end  

function parabola (a,b,c)
   local xa,xb,xc,ya,yb,yc
   xa = a.re
   ya = a.im
   xb = b.re
   yb = b.im
   xc = c.re
   yc = c.im
   D = (xa-xb)*(xa-xc)*(xb-xc)
   A = (xc*(yb-ya) + xb*(ya-yc)+xa*(yc-yb))/D
   B = (xc*xc*(ya-yb)+xb*xb*(yc-ya)+xa*xa*(yb-yc))/D
   C = (xb*xc*(xb-xc)*ya + xc*xa*(xc-xa)*yb +xa*xb*(xa-xb)*yc)/D
   return A,B,C
end

function value (v)
   return scale * v
end

function real (v)
   return v/scale
end

function get_angle (a,b,c)
  return angle_normalize(get_angle_( a,b,c ))
end 
   
function get_angle_( a,b,c )
	 return point.arg ((c-a)/(b-a))
end

function angle_normalize (a)
local dblpi 
 dblpi = 2 * math.pi
 if a > dblpi 
 then 
     a = a - dblpi
  end
  if a < 0 then
  a = a + dblpi
  end
  return a
end