-- tkz_elements_functions_circles.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.

--  define a circle by the center and a radius

-- function circle_cr ( c, r )
--     return c +  point(r,0)
-- end

function midarc_ (o,a,b) -- a -> b
   local phi = 0.5 * get_angle_ ( a,o,b )
   return rotation_ (o,phi,b)
end

function radical_center (C1,C2,C3)
   local t1,t2,t3,t4
   t1,t2 = radical_axis_ (C3.center,C3.through,C1.center,C1.through)
   t3,t4 = radical_axis_ (C3.center,C3.through,C2.center,C2.through)
return intersection_ll_ (t1,t2,t3,t4)
end

function  radical_circle (C1,C2,C3)
   local rc
   rc = radical_center (C1,C2,C3)
 return C1 : orthogonal_from (rc)
end

function tangent_from_ (c,p,pt)
  local o
   o  = midpoint_ ( c,pt )
 return  intersection_cc_ (o,c,c,p)
end

function tangent_at_ (a,b,p)
   return rotation_ (p,math.pi/2,a),rotation_ (p,-math.pi/2,a)
end

function orthogonal_from_ (a,b,p)
    return tangent_from_ (a,b,p)
end

function orthogonal_through_ (a,b,x,y)
    local d,z
   d =  1/point.mod(x-a)
   z = a +(b-a)*d
   return circum_center_ (x,y,z)
end

 
function inversion_ (c,p,pt)
  local ry = point.abs(c-p)
  local d  = point.abs(c-pt)
  local r  = (ry*ry)/d
  return c+polar_ (r,point.arg(pt-c))
end
  
function radical_axis_ (c1,p1,c2,p2)
   local d,m,m1,m2,epsilon,ci,cj,ck,cm,cn,r1,r2
   r1 = point.abs(c1-p1)
   r2 = point.abs(c2-p2)
   epsilon = 10^(-12)
   d = point.abs (c2 - c1)
   m = d - (r1+r2)
   m1 = math.abs (d - (r1+r2))
   m2 = math.abs (d - math.abs(r1-(r2)))
   if m2 < epsilon then
      ci = rotation_ (p1,math.pi/2,c2)
      cj = rotation_ (p1,-math.pi/2,c2)
      return ci,cj
   elseif m1 < epsilon then -- circles tangent
   ci = rotation_ (p1,math.pi/2,c2)
   cj = rotation_ (p1,-math.pi/2,c2)
   return ci,cj
    -- circles disjoints
     elseif   m > 0 then
         ck = rotation_ (c1,math.pi/3,c2)
         ci,cj = intersection_cc_ (c1,p1,ck,c1)
         cm,cn = intersection_cc_ (c2,p2,ck,c1)
         ci = intersection_ll_ (ci,cj,cm,cn)
         cj = projection_ (c1,c2,ci)
         return ci,cj
     else         
     ci,cj = intersection_cc_ (c1,p1,c2,p2)
     return ci,cj
   end
end

function south_pole_ (c,p)
   local r
   r = point.abs (c-p)
   return c - point (0,r)
 end

function north_pole_ (c,p)
   local r
   r = point.abs (c-p)
   return c + point (0,r)
end

function antipode_ (c,pt)
   return 2 * c - pt
end
