+
    i                        R t ^ RIHtHtHt ^ RIHt ^ RIt^ RIH	t	  ^ RI
t
]
P                  tRt]	! R. RQO4      t. RROtRSR ltR	 t]
P*                  ! ]
P,                  4      ]
P.                  ! ]
P0                  ]
P0                  ]
P0                  ]
P0                  R
7      ]
P.                  ! ]
P,                  ]
P,                  ]
P,                  R7      R 4       4       4       t]
P*                  ! ]
P,                  4      ]
P.                  ! ]
P0                  ]
P0                  ]
P0                  ]
P0                  R7      ]
P.                  ! ]
P,                  ]
P,                  R7      RSR l4       4       4       t^tRt]
P:                  ]
P<                  ]
P*                  ! ]
P,                  4      ]
P.                  ! ]
P0                  ]
P0                  R7      R 4       4       4       4       t]
P:                  ]
P<                  ]
P*                  ! ]
P,                  4      ]
P.                  ! ]
P,                  R7      R 4       4       4       4       t R t!]
P*                  ! ]
P,                  4      ]
P.                  ! ]
P0                  ]
P0                  ]
P0                  ]
P0                  ]
P0                  ]
P0                  ]
P0                  R7      ]
P.                  ! ]
P,                  ]
P,                  ]
P,                  ]
P,                  ]
P,                  ]
P,                  ]
P,                  R7      R 4       4       4       t"R t#]
P*                  ! ]
P,                  4      ]
P.                  ! ]
P0                  ]
P0                  ]
P0                  R7      ]
P.                  ! ]
P,                  ]
P,                  ]
P,                  R7      R 4       4       4       t$R t%R t&]
P*                  ! ]
P,                  4      ]
P.                  ! ]
P0                  ]
P0                  ]
P0                  ]
P0                  R7      ]
P.                  ! ]
P,                  ]
P,                  ]
P,                  ]
P,                  ]
P,                  R7      R  4       4       4       t'R! t(R" t)R# t*R$ t+R% t,R& t-]
P.                  ! ]
P0                  ]
P0                  ]
P0                  ]
P0                  ]
P0                  ]
P0                  ]
P0                  ]
P0                  R'7      R( 4       t.]
P*                  ! ]
P0                  4      ]
P.                  ! ]
P,                  ]
P0                  ]
P0                  ]
P0                  ]
P0                  ]
P0                  ]
P0                  ]
P0                  R)7      ]
P.                  ! ]
P,                  ]
P,                  ]
P,                  ]
P,                  R*7      R+ 4       4       4       t/R, t0R- t1]
P.                  ! ]
P0                  ]
P0                  ]
P0                  ]
P0                  ]
P,                  ]
P,                  ]
P,                  ]
P,                  ]
P,                  ]
P0                  ]
P0                  ]
P0                  ]
P0                  R.7      R/ 4       t2^ R0IH3t3H4t4H5t5H6t6 ]33R1 lt7R2 t8R3 t9R4 t:]
P:                  ]
P<                  ]
P.                  ! ]
P0                  ]
P0                  ]
P0                  ]
P0                  ]
P0                  ]
P0                  ]
P0                  R57      R6 4       4       4       t;R7 t<R8 t=]
P:                  ]
P<                  ]
P.                  ! ]
P0                  ]
P0                  ]
P0                  ]
P0                  ]
P0                  ]
P0                  ]
P0                  R97      R: 4       4       4       t>R; t?R< t@R= tA]
P*                  ! ]
P0                  4      ]
P.                  ! ]
P,                  ]
P0                  ]
P0                  ]
P0                  ]
P0                  R>7      ]
P.                  ! ]
P,                  ]
P,                  ]
P,                  R?7      R@ 4       4       4       tBRA tCRB tDRC tERD tFRE tGRF tHRG tIRH tJRI tKRTRJ ltLRK tMRL tNRM tORN tPRO tQ]RRP8X  d6   ^ RIStS^ RITtT]SP                  ! ]TP                  ! 4       P                  4       R# R#   ]]3 d    ^ RIH
t
  ELi ; i)UzNfontTools.misc.bezierTools.py -- tools for working with Bezier path segments.
)
calcBoundssectRectrectArea)IdentityN)
namedtuple)cythong&.>Intersectionc           	     X    \        \        V !  \        V!  \        V!  \        V!  V4      # )a  Calculates the arc length for a cubic Bezier segment.

Whereas :func:`approximateCubicArcLength` approximates the length, this
function calculates it by "measuring", recursively dividing the curve
until the divided segments are shorter than ``tolerance``.

Args:
    pt1,pt2,pt3,pt4: Control points of the Bezier as 2D tuples.
    tolerance: Controls the precision of the calcuation.

Returns:
    Arc length value.
)calcCubicArcLengthCcomplex)pt1pt2pt3pt4	tolerances   &&&&&z/Users/tonyclaw/.openclaw/workspace/skills/math-calculator/venv/lib/python3.14/site-packages/fontTools/misc/bezierTools.pycalcCubicArcLengthr   8   s,     w}gsmWc]I     c                     V ^W,           ,          ,           V,           R,          pW2,           V,
          V ,
          R,          pW V,           R,          WE,
          V3WDV,           W#,           R,          V33# )   g      ?      ? )p0p1p2p3midderiv3s   &&&&  r   _split_cubic_into_twor   K   sc    RW"e
+CglR5(F	2g_clC0	FlRWOR0 r   )r   r   r   r   )multarchboxc                 F   \        W,
          4      p\        W,
          4      \        W#,
          4      ,           \        W4,
          4      ,           pWP,          \        ,           V8  d   WV,           R ,          # \        WW44      w  rx\        V .VO5!  \        V .VO5!  ,           # r   )absEPSILONr   _calcCubicArcLengthCRecurse)	r   r   r   r   r   r    r!   onetwos	   &&&&&    r   r&   r&   T   s     rw<D
bg,RW
%BG
4C{W#
c!!(8*46#69T:
:
 
 	
r   r   r   r   r   )r   r   c                <    RRV,          ,           p\        WPWV4      # )zCalculates the arc length for a cubic Bezier segment.

Args:
    pt1,pt2,pt3,pt4: Control points of the Bezier as complex numbers.
    tolerance: Controls the precision of the calcuation.

Returns:
    Arc length value.
      ?g      ?)r&   )r   r   r   r   r   r   s   &&&&& r   r
   r
   h   s!    * y D&t#C@@r   g|=v1v2c                 B    WP                  4       ,          P                  # N)	conjugaterealr,   s   &&r   _dotr3      s    
 %%%r   xc                     V \         P                  ! V ^,          ^,           4      ,          ^,          \         P                  ! V 4      ^,          ,           # )   )mathsqrtasinhr4   s   &r   _intSecAtanr;      s7     tyyA""Q&A):::r   c                F    \        \        V !  \        V!  \        V!  4      # )a6  Calculates the arc length for a quadratic Bezier segment.

Args:
    pt1: Start point of the Bezier as 2D tuple.
    pt2: Handle point of the Bezier as 2D tuple.
    pt3: End point of the Bezier as 2D tuple.

Returns:
    Arc length value.

Example::

    >>> calcQuadraticArcLength((0, 0), (0, 0), (0, 0)) # empty segment
    0.0
    >>> calcQuadraticArcLength((0, 0), (50, 0), (80, 0)) # collinear points
    80.0
    >>> calcQuadraticArcLength((0, 0), (0, 50), (0, 80)) # collinear points vertical
    80.0
    >>> calcQuadraticArcLength((0, 0), (50, 20), (100, 40)) # collinear points
    107.70329614269008
    >>> calcQuadraticArcLength((0, 0), (0, 100), (100, 0))
    154.02976155645263
    >>> calcQuadraticArcLength((0, 0), (0, 50), (100, 0))
    120.21581243984076
    >>> calcQuadraticArcLength((0, 0), (50, -10), (80, 50))
    102.53273816445825
    >>> calcQuadraticArcLength((0, 0), (40, 0), (-40, 0)) # collinear points, control point outside
    66.66666666666667
    >>> calcQuadraticArcLength((0, 0), (40, 0), (0, 0)) # collinear points, looping back
    40.0
)calcQuadraticArcLengthCr   r   r   r   s   &&&r   calcQuadraticArcLengthr?      s     @ #7C='3-#OOr   )r   r   r   d0d1dn)scaleorigDistabx0x1Lenc                P   W,
          pW!,
          pWC,
          pVR,          p\        V4      pVR8X  d   \        W ,
          4      # \        Wc4      p\        V4      \        8  dY   \        W44      ^ 8  d   \        W ,
          4      # \        V4      \        V4      rW,          W,          ,           W,           ,          # \        WS4      V,          p\        WT4      V,          p\        ^\        V4      \        V4      ,
          ,          V,          W|V,
          ,          ,          4      pV# )a  Calculates the arc length for a quadratic Bezier segment.

Args:
    pt1: Start point of the Bezier as a complex number.
    pt2: Handle point of the Bezier as a complex number.
    pt3: End point of the Bezier as a complex number.

Returns:
    Arc length value.
y              ?        )r$   r3   epsilonr;   )r   r   r   r@   rA   rB   rC   rD   rE   rF   rG   rH   rI   rJ   s   &&&           r   r=   r=      s    @ 
B	B
A	BAFE|39~A{H
8}w<1sy>!2wB1!%((	ax	B	ax	B
a;r?[_45@ERTWDUV
WCJr   c                F    \        \        V !  \        V!  \        V!  4      # )a  Calculates the arc length for a quadratic Bezier segment.

Uses Gauss-Legendre quadrature for a branch-free approximation.
See :func:`calcQuadraticArcLength` for a slower but more accurate result.

Args:
    pt1: Start point of the Bezier as 2D tuple.
    pt2: Handle point of the Bezier as 2D tuple.
    pt3: End point of the Bezier as 2D tuple.

Returns:
    Approximate arc length value.
)approximateQuadraticArcLengthCr   r>   s   &&&r   approximateQuadraticArcLengthrP      s      *'3-#QTVVr   r>   )v0r-   r.   c                   \        RV ,          RV,          ,           RV,          ,           4      p\        W ,
          4      R,          p\        RV ,          RV,          ,
          RV,          ,           4      pW4,           V,           # )a  Calculates the arc length for a quadratic Bezier segment.

Uses Gauss-Legendre quadrature for a branch-free approximation.
See :func:`calcQuadraticArcLength` for a slower but more accurate result.

Args:
    pt1: Start point of the Bezier as a complex number.
    pt2: Handle point of the Bezier as a complex number.
    pt3: End point of the Bezier as a complex number.

Returns:
    Approximate arc length value.
g̔xb?gb?gFVW?gqq?g̔xb߿gFVWr$   )r   r   r   rQ   r-   r.   s   &&&   r   rO   rO      sx    B 
S #4s#::=ORU=UU
B 
SY,	,B	c!$5$;;>ORU>UU
B 7R<r   c                   \        WV4      w  w  r4w  rVw  rxVR,          p	VR,          p
. pV	^ 8w  d   VP                  V) V	,          4       V
^ 8w  d   VP                  V) V
,          4       V Uu. uF^  p^ Tu;8:  d
   ^8  g   K  M K  W<,          V,          W\,          ,           V,           WL,          V,          Wl,          ,           V,           3NK`  	  upW.,           p\        V4      # u upi )a  Calculates the bounding rectangle for a quadratic Bezier segment.

Args:
    pt1: Start point of the Bezier as a 2D tuple.
    pt2: Handle point of the Bezier as a 2D tuple.
    pt3: End point of the Bezier as a 2D tuple.

Returns:
    A four-item tuple representing the bounding rectangle ``(xMin, yMin, xMax, yMax)``.

Example::

    >>> calcQuadraticBounds((0, 0), (50, 100), (100, 0))
    (0, 0, 100, 50.0)
    >>> calcQuadraticBounds((0, 0), (100, 0), (100, 100))
    (0.0, 0.0, 100, 100)
       @)calcQuadraticParametersappendr   )r   r   r   axaybxbycxcyax2ay2rootstpointss   &&&           r   calcQuadraticBoundsrc   *  s    $ $;3S#I HRhr
s(C
s(CE
axbS3Y
axbS3Y A:A: 	= 	=!bf	r	!26A:#6#;< 

	F
 fs   /C)C)	A
C)c           	     V    \        \        V !  \        V!  \        V!  \        V!  4      # )af  Approximates the arc length for a cubic Bezier segment.

Uses Gauss-Lobatto quadrature with n=5 points to approximate arc length.
See :func:`calcCubicArcLength` for a slower but more accurate result.

Args:
    pt1,pt2,pt3,pt4: Control points of the Bezier as 2D tuples.

Returns:
    Arc length value.

Example::

    >>> approximateCubicArcLength((0, 0), (25, 100), (75, 100), (100, 0))
    190.04332968932817
    >>> approximateCubicArcLength((0, 0), (50, 0), (100, 50), (100, 100))
    154.8852074945903
    >>> approximateCubicArcLength((0, 0), (50, 0), (100, 0), (150, 0)) # line; exact result should be 150.
    149.99999999999991
    >>> approximateCubicArcLength((0, 0), (50, 0), (100, 0), (-50, 0)) # cusp; exact result should be 150.
    136.9267662156362
    >>> approximateCubicArcLength((0, 0), (50, 0), (100, -50), (-50, 0)) # cusp
    154.80848416537057
)approximateCubicArcLengthCr   r)   s   &&&&r   approximateCubicArcLengthrf   L  s*    2 &w}gsmWc] r   )rQ   r-   r.   v3v4c                   \        W,
          4      R,          p\        RV ,          RV,          ,           RV,          ,           RV,          ,           4      p\        W0,
          V,           V,
          4      R,          p\        RV ,          RV,          ,
          RV,          ,
          RV,          ,           4      p\        W2,
          4      R,          pWE,           V,           V,           V,           # )	zApproximates the arc length for a cubic Bezier segment.

Args:
    pt1,pt2,pt3,pt4: Control points of the Bezier as complex numbers.

Returns:
    Arc length value.
g333333?gc1?g85$t?gu|Y?g#$?g?gc1g#$rS   )	r   r   r   r   rQ   r-   r.   rg   rh   s	   &&&&     r   re   re   j  s    > 
SY$	B	S 
c
!	"
c
!	" c
!	"
B 
SY_s"	#&9	9B	S 
c
!	"
c
!	" c
!	"
B 
SY$	B7R<"r!!r   c                   \        WW#4      w  w  rEw  rgw  rw  rVR,          pVR,          pVR,          pVR,          p\        WV4       Uu. uF  p^ Tu;8:  d
   ^8  g   K  M K  VNK  	  pp\        WV	4       Uu. uF  p^ Tu;8:  d
   ^8  g   K  M K  VNK  	  ppVV,           pV Uu. uF  pVV,          V,          V,          VV,          V,          ,           VV,          ,           V
,           VV,          V,          V,          VV,          V,          ,           V	V,          ,           V,           3NK  	  upW.,           p\        V4      # u upi u upi u upi )a(  Calculates the bounding rectangle for a quadratic Bezier segment.

Args:
    pt1,pt2,pt3,pt4: Control points of the Bezier as 2D tuples.

Returns:
    A four-item tuple representing the bounding rectangle ``(xMin, yMin, xMax, yMax)``.

Example::

    >>> calcCubicBounds((0, 0), (25, 100), (75, 100), (100, 0))
    (0, 0, 100, 75.0)
    >>> calcCubicBounds((0, 0), (50, 0), (100, 50), (100, 100))
    (0.0, 0.0, 100, 100)
    >>> print("%f %f %f %f" % calcCubicBounds((50, 0), (0, 100), (100, 100), (50, 0)))
    35.566243 0.000000 64.433757 75.000000
      @rU   )calcCubicParameterssolveQuadraticr   )r   r   r   r   rX   rY   rZ   r[   r\   r]   dxdyax3ay3bx2by2ra   xRootsyRootsr`   rb   s   &&&&                 r   calcCubicBoundsrv     sE   $ .A3-T*HRhr(2
s(C
s(C
s(C
s(C'"5D5Aa!aa5FD'"5D5Aa!aa5FDVOE 
 A FQJNR!VaZ'"q&025FQJNR!VaZ'"q&025	
  

F f EDs+   E"E&E<EEE+BEc                   V w  rEVw  rgWd,
          pWu,
          p	Tp
TpW3V,          pV^ 8X  d   W3.# W*V3V,          ,
          V,          p^ Tu;8:  d   ^8  d(   M M$W,          V
,           W,          V,           3pW3W3.# W3.# )a  Split a line at a given coordinate.

Args:
    pt1: Start point of line as 2D tuple.
    pt2: End point of line as 2D tuple.
    where: Position at which to split the line.
    isHorizontal: Direction of the ray splitting the line. If true,
        ``where`` is interpreted as a Y coordinate; if false, then
        ``where`` is interpreted as an X coordinate.

Returns:
    A list of two line segments (each line segment being two 2D tuples)
    if the line was successfully split, or a list containing the original
    line.

Example::

    >>> printSegments(splitLine((0, 0), (100, 100), 50, True))
    ((0, 0), (50, 50))
    ((50, 50), (100, 100))
    >>> printSegments(splitLine((0, 0), (100, 100), 100, True))
    ((0, 0), (100, 100))
    >>> printSegments(splitLine((0, 0), (100, 100), 0, True))
    ((0, 0), (0, 0))
    ((0, 0), (100, 100))
    >>> printSegments(splitLine((0, 0), (100, 100), 0, False))
    ((0, 0), (0, 0))
    ((0, 0), (100, 100))
    >>> printSegments(splitLine((100, 0), (0, 0), 50, False))
    ((100, 0), (50, 0))
    ((50, 0), (0, 0))
    >>> printSegments(splitLine((0, 100), (0, 0), 50, True))
    ((0, 100), (0, 50))
    ((0, 50), (0, 0))
r   )r   r   whereisHorizontalpt1xpt1ypt2xpt2yrX   rY   rZ   r[   rF   ra   midPts   &&&&           r   	splitLiner     s    H JDJD	B	B	B	B	AAv
|	b,'	'1,AAzzRVb[(ul++
|r   c                    \        WV4      w  rVp\        WT,          Wd,          Wt,          V,
          4      p\        R V 4       4      pV'       g   WV3.# \        WVV.VO5!  # )a  Split a quadratic Bezier curve at a given coordinate.

Args:
    pt1,pt2,pt3: Control points of the Bezier as 2D tuples.
    where: Position at which to split the curve.
    isHorizontal: Direction of the ray splitting the curve. If true,
        ``where`` is interpreted as a Y coordinate; if false, then
        ``where`` is interpreted as an X coordinate.

Returns:
    A list of two curve segments (each curve segment being three 2D tuples)
    if the curve was successfully split, or a list containing the original
    curve.

Example::

    >>> printSegments(splitQuadratic((0, 0), (50, 100), (100, 0), 150, False))
    ((0, 0), (50, 100), (100, 0))
    >>> printSegments(splitQuadratic((0, 0), (50, 100), (100, 0), 50, False))
    ((0, 0), (25, 50), (50, 50))
    ((50, 50), (75, 50), (100, 0))
    >>> printSegments(splitQuadratic((0, 0), (50, 100), (100, 0), 25, False))
    ((0, 0), (12.5, 25), (25, 37.5))
    ((25, 37.5), (62.5, 75), (100, 0))
    >>> printSegments(splitQuadratic((0, 0), (50, 100), (100, 0), 25, True))
    ((0, 0), (7.32233, 14.6447), (14.6447, 25))
    ((14.6447, 25), (50, 75), (85.3553, 25))
    ((85.3553, 25), (92.6777, 14.6447), (100, -7.10543e-15))
    >>> # XXX I'm not at all sure if the following behavior is desirable:
    >>> printSegments(splitQuadratic((0, 0), (50, 100), (100, 0), 50, True))
    ((0, 0), (25, 50), (50, 50))
    ((50, 50), (50, 50), (50, 50))
    ((50, 50), (75, 50), (100, 0))
c              3   P   "   T F  p^ Tu;8:  d
   ^8  g   K  M K  Vx  K  	  R# 5i    Nr   .0ra   s   & r   	<genexpr>!splitQuadratic.<locals>.<genexpr>"       :)QqAzzqzq)   &&
&)rV   rm   sorted_splitQuadraticAtT)	r   r   r   rx   ry   rF   rG   c	solutionss	   &&&&&    r   splitQuadraticr     se    F &c4GA!	!/E*AI :)::I3  aA2	22r   c                    \        WW#4      w  rgr\        We,          Wu,          W,          W,          V,
          4      p
\        R V
 4       4      p
V
'       g   WW#3.# \        WgW.V
O5!  # )a  Split a cubic Bezier curve at a given coordinate.

Args:
    pt1,pt2,pt3,pt4: Control points of the Bezier as 2D tuples.
    where: Position at which to split the curve.
    isHorizontal: Direction of the ray splitting the curve. If true,
        ``where`` is interpreted as a Y coordinate; if false, then
        ``where`` is interpreted as an X coordinate.

Returns:
    A list of two curve segments (each curve segment being four 2D tuples)
    if the curve was successfully split, or a list containing the original
    curve.

Example::

    >>> printSegments(splitCubic((0, 0), (25, 100), (75, 100), (100, 0), 150, False))
    ((0, 0), (25, 100), (75, 100), (100, 0))
    >>> printSegments(splitCubic((0, 0), (25, 100), (75, 100), (100, 0), 50, False))
    ((0, 0), (12.5, 50), (31.25, 75), (50, 75))
    ((50, 75), (68.75, 75), (87.5, 50), (100, 0))
    >>> printSegments(splitCubic((0, 0), (25, 100), (75, 100), (100, 0), 25, True))
    ((0, 0), (2.29379, 9.17517), (4.79804, 17.5085), (7.47414, 25))
    ((7.47414, 25), (31.2886, 91.6667), (68.7114, 91.6667), (92.5259, 25))
    ((92.5259, 25), (95.202, 17.5085), (97.7062, 9.17517), (100, 1.77636e-15))
c              3   P   "   T F  p^ Tu;8:  d
   ^8  g   K  M K  Vx  K  	  R# 5ir   r   r   s   & r   r   splitCubic.<locals>.<genexpr>G  r   r   )rl   
solveCubicr   _splitCubicAtT)r   r   r   r   rx   ry   rF   rG   r   rB   r   s   &&&&&&     r   
splitCubicr   (  si    6 %Ss8JA!	!/1?U;RI :)::I3$%%!1y11r   c                <    \        WV4      w  rEp\        WEV.VO5!  # )a]  Split a quadratic Bezier curve at one or more values of t.

Args:
    pt1,pt2,pt3: Control points of the Bezier as 2D tuples.
    *ts: Positions at which to split the curve.

Returns:
    A list of curve segments (each curve segment being three 2D tuples).

Examples::

    >>> printSegments(splitQuadraticAtT((0, 0), (50, 100), (100, 0), 0.5))
    ((0, 0), (25, 50), (50, 50))
    ((50, 50), (75, 50), (100, 0))
    >>> printSegments(splitQuadraticAtT((0, 0), (50, 100), (100, 0), 0.5, 0.75))
    ((0, 0), (25, 50), (50, 50))
    ((50, 50), (62.5, 50), (75, 37.5))
    ((75, 37.5), (87.5, 25), (100, 0))
)rV   r   )r   r   r   tsrF   rG   r   s   &&&*   r   splitQuadraticAtTr   M  s&    ( &c4GA!aA+++r   c                    \        WW#4      w  rVrx\        WVWx.VO5!  p	V .V	^ ,          R,          O5V	^ &   . V	R,          RR OVN5V	R&   V	# )a  Split a cubic Bezier curve at one or more values of t.

Args:
    pt1,pt2,pt3,pt4: Control points of the Bezier as 2D tuples.
    *ts: Positions at which to split the curve.

Returns:
    A list of curve segments (each curve segment being four 2D tuples).

Examples::

    >>> printSegments(splitCubicAtT((0, 0), (25, 100), (75, 100), (100, 0), 0.5))
    ((0, 0), (12.5, 50), (31.25, 75), (50, 75))
    ((50, 75), (68.75, 75), (87.5, 50), (100, 0))
    >>> printSegments(splitCubicAtT((0, 0), (25, 100), (75, 100), (100, 0), 0.5, 0.75))
    ((0, 0), (12.5, 50), (31.25, 75), (50, 75))
    ((50, 75), (59.375, 75), (68.75, 68.75), (77.3438, 56.25))
    ((77.3438, 56.25), (85.9375, 43.75), (93.75, 25), (100, 0))
:   NNN)rl   r   )
r   r   r   r   r   rF   rG   r   rB   splits
   &&&&*     r   splitCubicAtTr   e  sb    ( %Ss8JA!1++E
 #eAhrl#E!H&%)CR.&#&E"ILr   )r   r   r   r   rF   rG   r   rB   c              '  \   "   \        WW#4      w  rVrx\        WVWx.VO5!   Rj  xL
  R#  L5i)a  Split a cubic Bezier curve at one or more values of t.

Args:
    pt1,pt2,pt3,pt4: Control points of the Bezier as complex numbers..
    *ts: Positions at which to split the curve.

Yields:
    Curve segments (each curve segment being four complex numbers).
N)calcCubicParametersC_splitCubicAtTC)	r   r   r   r   r   rF   rG   r   rB   s	   &&&&*    r   splitCubicAtTCr     s,     ( &c9JA!qQ/B///s   !,*,)ra   r   r   r   r   pointAtToff1off2)t2_1_t_1_t_2_2_t_1_tc                   WD,          p^V,
          pWf,          p^V,          V,          pWv,          V ,          ^Wt,          V,          We,          V,          ,           ,          ,           WT,          V,          ,           p	Wp,          W,          ,           WR,          ,           p
Wq,          W,          ,           WS,          ,           pWV ,
          V,          ,           pW2V,
          V,          ,           pWW3WW#33# )zSplit a cubic Bezier curve at t.

Args:
    pt1,pt2,pt3,pt4: Control points of the Bezier as complex numbers.
    t: Position at which to split the curve.

Returns:
    A tuple of two curve segments (each curve segment being four complex numbers).
r   )r   r   r   r   ra   r   r   r   r   r   r   r   s   &&&&&       r   splitCubicIntoTwoAtTCr     s    0 
Bq5D[F1ut|Ha6:#3di#o#EFFRUU  <(.(283D<(.(283D
sa
C
sd"
"Ct&(BCCr   c                    \        V4      p. pVP                  ^ R4       VP                  R4       V w  rVVw  rxVw  r\        \	        V4      ^,
          4       F  pW;,          pW;^,           ,          pW,
          pW,          pW_,          pWo,          p^V,          V,          V,           V,          p^V,          V,          V,           V,          pW,          pVV,          W|,          ,           V	,           pVV,          W,          ,           V
,           p\        VV3VV3VV34      w  pppVP                  VVV34       K  	  V# r   rL   r+   )listinsertrW   rangelencalcQuadraticPoints)rF   rG   r   r   segmentsrX   rY   rZ   r[   r\   r]   it1r   deltadelta_2a1xa1yb1xb1yt1_2c1xc1yr   r   r   s   &&&*                      r   r   r     s   	bBHIIaIIcNFBFBFB3r7Q;UAY-ll2v{R5(2v{R5(w4i"'!B&4i"'!B&+S#Jc
S#JOS#c3(    Or   c                    \        V4      pVP                  ^ R4       VP                  R4       . pV w  rgVw  rVw  rVw  r\        \	        V4      ^,
          4       EF  pWN,          pWN^,           ,          pVV,
          pVV,          pVV,          pW,          pVV,          pVV,          pVV,          p^V,          V,          V,           V,          p^V,          V,          V	,           V,          p^V,          V,          V
,           ^V,          V,          ,           V,          p^V	,          V,          V,           ^V,          V,          ,           V,          pVV,          VV,          ,           W,          ,           V,           pVV,          V	V,          ,           W,          ,           V,           p\        VV3VV3VV3VV34      w  ppp p!VP                  VVV V!34       EK  	  V# r   )r   r   rW   r   r   calcCubicPoints)"rF   rG   r   rB   r   r   rX   rY   rZ   r[   r\   r]   rn   ro   r   r   r   r   r   delta_3r   t1_3r   r   r   r   r   r   d1xd1yr   r   r   r   s"   &&&&*                             r   r   r     s   	bBIIaIIcNHFBFBFBFB3r7Q;UAYR%-'/wDy 7l7l2v{R7*2v{R7*2v{R!b&4-/582v{R!b&4-/584i"t)#bg-24i"t)#bg-2,#Jc
S#Jc

S#s 	c3,--  . Or   )rF   rG   r   rB   r   r   r   r   r   a1b1c1rA   c              '   d  "   \        V4      pVP                  ^ R4       VP                  R4       \        \	        V4      ^,
          4       F  pWE,          pWE^,           ,          pWv,
          pW,          p	W,          p
Wf,          pWk,          pW
,          p^V ,          V,          V,           V	,          p^V,          V,          V,           ^V ,          V,          ,           V,          pW,          W,          ,           W&,          ,           V,           p\        WVV4      w  ppppVVVV3x  K  	  R# 5i)r   rL   r+   N)r   r   rW   r   r   calcCubicPointsC)rF   rG   r   rB   r   r   r   r   r   r   r   r   r   r   r   r   rA   r   r   r   r   s   &&&&*                r   r   r     s       
bBIIaIIcN3r7Q;UAY-/wy [!ebj1n'!ebj1nq1ut|+u4X 16)A--bb"=S#sCc""!  s   D.D0)r9   acoscospic                :   \        V 4      \        8  d'   \        V4      \        8  d   . pV# V) V,          .p V# W,          RV ,          V,          ,
          pVR8  d;   V! V4      pV) V,           R,          V ,          V) V,
          R,          V ,          .pV# . pV# )u'  Solve a quadratic equation.

Solves *a*x*x + b*x + c = 0* where a, b and c are real.

Args:
    a: coefficient of *x²*
    b: coefficient of *x*
    c: constant term

Returns:
    A list of roots. Note that the returned list is neither guaranteed to
    be sorted nor to contain unique values!
      @rL   rU   r$   rM   )rF   rG   r   r9   r`   DDrDDs   &&&&   r   rm   rm   /  s     1vq6GE L R!VHE L US1Wq[ 9r(Cb3h#%)QBH+;a+?@E L ELr   c           
        \        V 4      \        8  d   \        WV4      # \        V 4      p W,          pW ,          pW0,          pWD,          RV,          ,
          R,          pRV,          V,          V,          RV,          V,          ,
          RV,          ,           R,          pW,          p	Ww,          V,          p
V	\        8  d   ^ MT	p	\        V
4      \        8  d   ^ MT
p
W,
          pV	R8X  d$   V
R8X  d   \	        V) R,          \
        4      pWV.# V\        R,          8:  Ed   \        \        \        V\        V
4      ,          R4      R
4      4      pR\        V4      ,          pVR,          pV\        VR,          4      ,          V,
          pV\        VR\        ,          ,           R,          4      ,          V,
          pV\        VR	\        ,          ,           R,          4      ,          V,
          p\        VVV.4      w  pppVV,
          \        8  d=   VV,
          \        8  d+   \	        VV,           V,           R,          \
        4      ;p;ppMVV,
          \        8  d2   \	        VV,           R,          \
        4      ;pp\	        V\
        4      pMsVV,
          \        8  d2   \	        V\
        4      p\	        VV,           R,          \
        4      ;ppM0\	        V\
        4      p\	        V\
        4      p\	        V\
        4      pVVV.# \        \        V4      \        V4      ,           R4      pWV,          ,           pVR8  d   V) p\	        WR,          ,
          \
        4      pV.# )u  Solve a cubic equation.

Solves *a*x*x*x + b*x*x + c*x + d = 0* where a, b, c and d are real.

Args:
    a: coefficient of *x³*
    b: coefficient of *x²*
    c: coefficient of *x*
    d: constant term

Returns:
    A list of roots. Note that the returned list is neither guaranteed to
    be sorted nor to contain unique values!

Examples::

    >>> solveCubic(1, 1, -6, 0)
    [-3.0, -0.0, 2.0]
    >>> solveCubic(-10.0, -9.0, 48.0, -29.0)
    [-2.9, 1.0, 1.0]
    >>> solveCubic(-9.875, -9.0, 47.625, -28.75)
    [-2.911392, 1.0, 1.0]
    >>> solveCubic(1.0, -4.5, 6.75, -3.375)
    [1.5, 1.5, 1.5]
    >>> solveCubic(-12.0, 18.0, -9.0, 1.50023651123)
    [0.5, 0.5, 0.5]
    >>> solveCubic(
    ...     9.0, 0.0, 0.0, -7.62939453125e-05
    ... ) == [-0.0, -0.0, -0.0]
    True
rk   g      "@rU   g      ;@g      K@rL   r   r+   r   g      g       UUUUUU?)r$   rM   rm   floatroundepsilonDigitsr   maxminr9   r   r   r   pow)rF   rG   r   rB   r   a2a3QRR2Q3R2_Q3r5   thetarQ2a1_3rH   rI   x2s   &&&&               r   r   r   P  s   L 1v aA&&aA	
B	
B	
B	38	s"A	rB	cBhm	+dRi	74?A	
B	
B7lB"gRBGE	SyR3Y2#)]+ay	'C-	SQb\3/67T!WnCx3us{##d*3b(C/00473b(C/0047RRL)
B7Wb7!2 "r'B,#!5}EEBEb"WwR"WO];;Br=)B"Wwr=)BR"WO];;Br=)Br=)Br=)BB|Uc!f$g.AI8A!3h,.s
r   c                     Vw  r4Vw  rVV w  rxW7,
          R ,          p	WH,
          R ,          p
WW,
          V	,
          pWh,
          V
,
          pW3W3Wx33# )rU   r   )r   r   r   r   y2x3y3r\   r]   rZ   r[   rX   rY   s   &&&          r   rV   rV     sV    FBFBFB
'SB
'SB	2B	2B8bXx''r   c                 $   Vw  rEVw  rgVw  rV w  rWJ,
          R ,          pW[,
          R ,          pWd,
          R ,          V,
          pWu,
          R ,          V,
          pW,
          V,
          V,
          pW,
          V,
          V,
          pVV3W3W3W33# rk   r   )r   r   r   r   r   r   r   r   x4y4rn   ro   r\   r]   rZ   r[   rX   rY   s   &&&&              r   rl   rl     s    FBFBFBFB
'SB
'SB
'S2	B
'S2	B	2	B	2	B8bXx"11r   )r   r   r   r   rF   rG   r   c                     W,
          R ,          pW!,
          R ,          V,
          pW0,
          V,
          V,
          pWeW@3# r   r   )r   r   r   r   r   rG   rF   s   &&&&   r   r   r     s;     
cA	cAA	AA!>r   c                     V w  r4Vw  rVVw  rxTp	Tp
VR ,          V,           pVR ,          V,           pW5,           V,           pWF,           V,           pW3W3W33# r#   r   )rF   rG   r   rX   rY   rZ   r[   r\   r]   rI   y1r   r   r   r   s   &&&            r   r   r     sd    FBFBFB	B	B
s(bB
s(bB	2B	2B8bXx''r   c                 2   V w  rEVw  rgVw  rVw  rT
pTpVR ,          V
,           pV	R ,          V,           pWh,           R ,          V,           pWy,           R ,          V,           pWJ,           V,           V,           pW[,           V	,           V,           pW3W3VV3VV33# r   r   )rF   rG   r   rB   rX   rY   rZ   r[   r\   r]   rn   ro   rI   r   r   r   r   r   r   r   s   &&&&                r   r   r     s    FBFBFBFB	B	B
s(bB
s(bB
'S2	B
'S2	B	2	B	2	B8bXBx"b11r   rF   rG   r   rB   r   r   p4c                     VR,          V,           pW,           R,          V,           pW,           V,           V,           pW4WV3# )r   r   r   r   s   &&&&   r   r   r     s;     
eqB
%E	R	B	
QB2?r   c                    V ^ ,          ^V,
          ,          V^ ,          V,          ,           V ^,          ^V,
          ,          V^,          V,          ,           3# )zFinds the point at time `t` on a line.

Args:
    pt1, pt2: Coordinates of the line as 2D tuples.
    t: The time along the line.

Returns:
    A 2D tuple with the coordinates of the point.
r   )r   r   ra   s   &&&r   linePointAtTr     sC     Vq1uA
*c!fA.>Q!.KMMr   c                   ^V,
          ^V,
          ,          V ^ ,          ,          ^^V,
          ,          V,          V^ ,          ,          ,           W3,          V^ ,          ,          ,           p^V,
          ^V,
          ,          V ^,          ,          ^^V,
          ,          V,          V^,          ,          ,           W3,          V^,          ,          ,           pWE3# )zFinds the point at time `t` on a quadratic curve.

Args:
    pt1, pt2, pt3: Coordinates of the curve as 2D tuples.
    t: The time along the curve.

Returns:
    A 2D tuple with the coordinates of the point.
r   )r   r   r   ra   r5   ys   &&&&  r   quadraticPointAtTr     s     
Q1q5CF"Q!a%[1_s1v%==ANA	
Q1q5CF"Q!a%[1_s1v%==ANA6Mr   c                   WD,          p^V,
          pWf,          pWv,          V ^ ,          ,          ^Wt,          V^ ,          ,          We,          V^ ,          ,          ,           ,          ,           WT,          V^ ,          ,          ,           pWv,          V ^,          ,          ^Wt,          V^,          ,          We,          V^,          ,          ,           ,          ,           WT,          V^,          ,          ,           p	W3# )zFinds the point at time `t` on a cubic curve.

Args:
    pt1, pt2, pt3, pt4: Coordinates of the curve as 2D tuples.
    t: The time along the curve.

Returns:
    A 2D tuple with the coordinates of the point.
r   )
r   r   r   r   ra   r   r   r   r5   r   s
   &&&&&     r   cubicPointAtTr   ,  s     
Bq5D[FA
vzCF"TYQ%77
8	9
&3q6/	  	A
vzCF"TYQ%77
8	9
&3q6/	 
 6Mr   )ra   r   r   r   r   )r   r   r   c                    WD,          p^V,
          pWf,          pWv,          V ,          ^Wt,          V,          We,          V,          ,           ,          ,           WT,          V,          ,           # )zFinds the point at time `t` on a cubic curve.

Args:
    pt1, pt2, pt3, pt4: Coordinates of the curve as complex numbers.
    t: The time along the curve.

Returns:
    A complex number with the coordinates of the point.
r   )r   r   r   r   ra   r   r   r   s   &&&&&   r   cubicPointAtTCr   F  sP    & 
Bq5D[F=3fj3&6S&H!IIBFUXLXXr   c                     \        V 4      ^8X  d   \        . V OVN5!  # \        V 4      ^8X  d   \        . V OVN5!  # \        V 4      ^8X  d   \        . V OVN5!  # \	        R4      hr7   Unknown curve degree)r   r   r   r   
ValueError)segra   s   &&r   segmentPointAtTr   _  sh    
3x1}$S$!$$	SQ )#)q))	SQ%c%1%%
+
,,r   c                 $   V w  r4Vw  rVVw  rx\        W5,
          4      \        8  d   \        WF,
          4      \        8  d   R# \        W5,
          4      \        WF,
          4      8  d   Ws,
          WS,
          ,          # W,
          Wd,
          ,          # )r   r   r   )	septsxsyexeypxpys	   &&&      r   _line_t_of_ptr  n  si    FBFBFB
27|g#bg,"8	
27|c"'l"BG$$BG$$r   c                     V ^ ,          V^ ,          ,
          V^ ,          V^ ,          ,
          ,          pV ^,          V^,          ,
          V^,          V^,          ,
          ,          pVR8*  ;'       d    VR8*  '       * # )r   rL   r   )rF   rG   originxDiffyDiffs   &&&  r   '_both_points_are_on_same_side_of_originr  |  sc    qTF1I!A$"23EqTF1I!A$"23E--#..r   c           	        V w  rEVw  rgVw  rVw  r\         P                  ! W4      '       d;   \         P                  ! WF4      '       d   \         P                  ! WH4      '       g   . # \         P                  ! W4      '       d;   \         P                  ! WW4      '       d   \         P                  ! WY4      '       g   . # \         P                  ! W4      '       d   \         P                  ! W4      '       d   . # \         P                  ! WF4      '       d   \         P                  ! WW4      '       d   . # \         P                  ! Wd4      '       dT   TpW,
          W,
          ,          pWV,
          ,          V	,           pW3p\        V\        WV4      \        W#V4      R7      .# \         P                  ! W4      '       dT   TpWu,
          Wd,
          ,          pVW,
          ,          V,           pW3p\        V\        WV4      \        W#V4      R7      .# Wu,
          Wd,
          ,          pW,
          W,
          ,          p\         P                  ! VV4      '       d   . # VV,          V,
          W,          ,
          V	,           VV,
          ,          pVW,
          ,          V,           pW3p\	        WV 4      '       d6   \	        WV4      '       d$   \        V\        WV4      \        W#V4      R7      .# . # )a  Finds intersections between two line segments.

Args:
    s1, e1: Coordinates of the first line as 2D tuples.
    s2, e2: Coordinates of the second line as 2D tuples.

Returns:
    A list of ``Intersection`` objects, each object having ``pt``, ``t1``
    and ``t2`` attributes containing the intersection point, time on first
    segment and time on second segment respectively.

Examples::

    >>> a = lineLineIntersections( (310,389), (453, 222), (289, 251), (447, 367))
    >>> len(a)
    1
    >>> intersection = a[0]
    >>> intersection.pt
    (374.44882952482897, 313.73458370177315)
    >>> (intersection.t1, intersection.t2)
    (0.45069111555824465, 0.5408153767394238)
r  r   r   )r8   iscloser   r  r  )s1e1s2e2s1xs1ye1xe1ys2xs2ye2xe2yr5   slope34r   r  slope12s   &&&&             r   lineLineIntersectionsr"    sE   . HCHCHCHCS4<<#9#9$,,sBXBX	S4<<#9#9$,,sBXBX	||C$,,s"8"8	||C$,,s"8"8	||C9+3w#%V-3bb8Q
 	

 ||C9+qw#%V-3bb8Q
 	
 ySY'GySY'G||GW%%		3	w}	,s	2w7HIA17c!A
B.
 
1""
=
=-3bb8Q
 	

 Ir   c                    V ^ ,          pV R,          p\         P                  ! V^,          V^,          ,
          V^ ,          V^ ,          ,
          4      p\        P                  ! V) 4      P	                  V^ ,          ) V^,          ) 4      # )r   r   )r8   atan2r   rotate	translate)segmentstartendangles   &   r   _alignment_transformationr+    sj     AJE
"+CJJs1va(#a&58*;<E??E6",,eAhYq	BBr   c                 |   \        V4      P                  V 4      p\        V 4      ^8X  d0   \        V!  w  r4p\	        V^,          V^,          V^,          4      pMR\        V 4      ^8X  d8   \        V!  w  r4rW\        V^,          V^,          V^,          V^,          4      pM\        R4      h\        R V 4       4      # )r   r   c              3   P   "   T F  pR Tu;8:  d
   ^8:  g   K  M K  Vx  K  	  R# 5i)rL   Nr   )r   r   s   & r   r   ._curve_line_intersections_t.<locals>.<genexpr>  s     <]cQm!m!m!]r   )	r+  transformPointsr   rV   rm   rl   r   r   r   )curvelinealigned_curverF   rG   r   intersectionsrB   s   &&      r   _curve_line_intersections_tr4    s    -d3CCEJM
5zQ)=9a&qtQqT1Q48	Uq(-8
a"1Q41qtQqT:/00<]<<<r   c           	     &   \        V 4      ^8X  d   \        pM"\        V 4      ^8X  d   \        pM\        R4      h. p\	        W4       FF  pV! . V OVN5!  p\        . VOVN5!  p\        . VOVN5!  pVP                  \        WTVR7      4       KH  	  V# )a  Finds intersections between a curve and a line.

Args:
    curve: List of coordinates of the curve segment as 2D tuples.
    line: List of coordinates of the line segment as 2D tuples.

Returns:
    A list of ``Intersection`` objects, each object having ``pt``, ``t1``
    and ``t2`` attributes containing the intersection point, time on first
    segment and time on second segment respectively.

Examples::
    >>> curve = [ (100, 240), (30, 60), (210, 230), (160, 30) ]
    >>> line  = [ (25, 260), (230, 20) ]
    >>> intersections = curveLineIntersections(curve, line)
    >>> len(intersections)
    3
    >>> intersections[0].pt
    (84.9000930760723, 189.87306176459828)
r   r  )	r   r   r   r   r4  r  r   rW   r   )r0  r1  pointFinderr3  ra   r  line_ts   &&     r   curveLineIntersectionsr8    s    * 5zQ'	Uq#/00M(5#%## ))b)(4((\R&AB 6 r   c                 |    \        V 4      ^8X  d
   \        V !  # \        V 4      ^8X  d
   \        V !  # \        R4      h)r   r   )r   rc   rv   r   )r   s   &r   _curve_boundsr:    s:    
1v{"A&&	Q1""
+
,,r   c                     \        V 4      ^8X  d   V w  r#\        W#V4      pW$3WC3.# \        V 4      ^8X  d   \        . V OVN5!  # \        V 4      ^8X  d   \        . V OVN5!  # \	        R4      hr   )r   r   r   r   r   )r   ra   r  r  midpoints   &&   r   _split_segment_at_tr=    sw    
1v{a(}--
1v{ '!'Q''	Q1#a###
+
,,r   c           
      B  a \        V 4      p\        V4      pV'       g   RpV'       g   Rp\        WV4      w  rxV'       g   . # R p	\        V4      S8  d"   \        V4      S8  d   V	! V4      V	! V4      3.# \        V R4      w  rV^ ,          V	! V4      3pV	! V4      V^,          3p\        VR4      w  rV^ ,          V	! V4      3pV	! V4      V^,          3p. pVP	                  \        WSVVR7      4       VP	                  \        WSVVR7      4       VP	                  \        WSVVR7      4       VP	                  \        WSVVR7      4       V3R lp\        4       p. pV F6  pV! V4      pVV9   d   K  VP                  V4       VP                  V4       K8  	  V# )rL   c                 >    R V ^ ,          V ^,          ,           ,          # r#   r   )rs   &r   r<  ._curve_curve_intersections_t.<locals>.midpoint1  s    adQqTk""r   r   )range1range2c                 h   < \        V ^ ,          S,          4      \        V ^,          S,          4      3# )r   )int)r   	precisions   &r   <lambda>._curve_curve_intersections_t.<locals>.<lambda>V  s&    SA!23SA9J5KLr   )rL   r+   )	r:  r   r   r=  extend_curve_curve_intersections_tsetaddrW   )curve1curve2rF  rB  rC  bounds1bounds2
intersects_r<  c11c12	c11_range	c12_rangec21c22	c21_range	c22_rangefound
unique_keyseenunique_valuesr   keys   &&f&&                   r   rJ  rJ  !  s    F#GF#G W.MJ	# 9$'):Y)F&!8F#3455"63/HCHV,-I&!6!9-I"63/HCHV,-I&!6!9-IE	LL$i	)	

 
LL$i	)	

 
LL$i	)	

 
LL$i	)	
 MJ5DMn$;R   r   c                     \        V 4      P                  V 4      p\        ;QJ d    R  V 4       F  '       d   K   R# 	  R# ! R  V 4       4      # )c              3   ^   "   T F#  p\         P                  ! V^,          R4      x  K%  	  R# 5i)r   rL   N)r8   r  )r   ps   & r   r   _is_linelike.<locals>.<genexpr>f  s"     :	1t||AaD#&&	s   +-FT)r+  r/  all)r'  	maybelines   & r   _is_linelikerf  d  s@    )'2BB7KI3:	:33:3:3:	:::r   c           
     6   \        V 4      '       d   V ^ ,          V R,          3p\        V4      '       d!   V^ ,          VR,          3p\        . VOVO5!  # \        W4      pV Uu. uF/  p\        VP                  VP
                  VP                  R7      NK1  	  up# \        V4      '       d   V^ ,          VR,          3p\        W4      # \        W4      pV Uu. uF/  p\        \        W^ ,          4      V^ ,          V^,          R7      NK1  	  up# u upi u upi )a  Finds intersections between a curve and a curve.

Args:
    curve1: List of coordinates of the first curve segment as 2D tuples.
    curve2: List of coordinates of the second curve segment as 2D tuples.

Returns:
    A list of ``Intersection`` objects, each object having ``pt``, ``t1``
    and ``t2`` attributes containing the intersection point, time on first
    segment and time on second segment respectively.

Examples::
    >>> curve1 = [ (10,100), (90,30), (40,140), (220,220) ]
    >>> curve2 = [ (5,150), (180,20), (80,250), (210,190) ]
    >>> intersections = curveCurveIntersections(curve1, curve2)
    >>> len(intersections)
    3
    >>> intersections[0].pt
    (81.7831487395506, 109.88904552375288)
r  r   )	rf  r"  r8  r   r  r   r   rJ  r   )rM  rN  line1line2hitsr5   intersection_tsr   s   &&      r   curveCurveIntersectionsrl  i  s   * Fq	6":%1Ivbz)E(8%8%88)&8D FJJTLADDQTTadd;TJJ	f		q	6":%%f4426BO "!B 	162a5RUK!  Ks   $5D5Dc           	        Rp\        V4      \        V 4      8  d   YrRp\        V 4      ^8  d)   \        V4      ^8  d   \        W4      pMF\        W4      pM:\        V 4      ^8X  d    \        V4      ^8X  d   \        . V OVO5!  pM\	        R4      hV'       g   V# V Uu. uF/  p\        VP                  VP                  VP                  R7      NK1  	  up# u upi )a  Finds intersections between two segments.

Args:
    seg1: List of coordinates of the first segment as 2D tuples.
    seg2: List of coordinates of the second segment as 2D tuples.

Returns:
    A list of ``Intersection`` objects, each object having ``pt``, ``t1``
    and ``t2`` attributes containing the intersection point, time on first
    segment and time on second segment respectively.

Examples::
    >>> curve1 = [ (10,100), (90,30), (40,140), (220,220) ]
    >>> curve2 = [ (5,150), (180,20), (80,250), (210,190) ]
    >>> intersections = segmentSegmentIntersections(curve1, curve2)
    >>> len(intersections)
    3
    >>> intersections[0].pt
    (81.7831487395506, 109.88904552375288)
    >>> curve3 = [ (100, 240), (30, 60), (210, 230), (160, 30) ]
    >>> line  = [ (25, 260), (230, 20) ]
    >>> intersections = segmentSegmentIntersections(curve3, line)
    >>> len(intersections)
    3
    >>> intersections[0].pt
    (84.9000930760723, 189.87306176459828)

FTz4Couldn't work out which intersection function to user  )	r   rl  r8  r"  r   r   r  r   r   )seg1seg2swappedr3  r   s   &&   r   segmentSegmentIntersectionsrq    s    < G
4y3t9d
4y1}t9q=3D?M24>M	TaCIN-;t;d;OPP=JK]LADDQTTadd3]KKKs    5Cc                     \        V 4      pRRP                  R V 4       4      ,          #   \         d    RT ,          u # i ; i)zk
>>> _segmentrepr([1, [2, 3], [], [[2, [3, 4], [0.1, 2.2]]]])
'(1, (2, 3), (), ((2, (3, 4), (0.1, 2.2))))'
z(%s)z, c              3   8   "   T F  p\        V4      x  K  	  R # 5ir0   )_segmentrepr)r   r5   s   & r   r   _segmentrepr.<locals>.<genexpr>  s     !>2a,q//2s   z%g)iterjoin	TypeError)objits   & r   rt  rt    sG    
?#Y 		!>2!>>>>  czs   , AAc                @    V  F  p\        \        V4      4       K  	  R# )zdHelper for the doctests, displaying each segment in a list of
segments on a single line as a tuple.
N)printrt  )r   r'  s   & r   printSegmentsr}    s     l7#$ r   __main__r  )rf   re   rP   rO   r   r
   r?   r=   rv   rc   r   r   r   r   r   r   r   rm   r   r   r   r   r   r   r"  r8  rl  rq  )g{Gzt?)gMbP?NN)X__doc__fontTools.misc.arrayToolsr   r   r   fontTools.misc.transformr   r8   collectionsr   r   AttributeErrorImportErrorfontTools.misccompiledCOMPILEDr%   r   __all__r   r   returnsdoublelocalsr   r&   r
   r   rM   cfuncinliner3   r;   r?   r=   rP   rO   rc   rf   re   rv   r   r   r   r   r   r   r   r   r   r   r9   r   r   r   rm   r   rV   rl   r   r   r   r   r   r   r   r   r   r  r  r"  r+  r4  r8  r:  r=  rJ  rf  rl  rq  rt  r}  __name__sysdoctestexittestmodfailedr   r   r   <module>r     sS   E D -  "& ??  .*<=@& ~~~~~~~~	 FMM6==I	
 J 	
 	 mm	A	 A 
 &..V^^4& 5   & ;     ; PF ~~~~nnnn 
--]]mmmm}}}} &@W" 
 }}}}}}
 BD< 	 }}}}}}}}}}!" !"H#L6r*3Z"2J,0> nnnnnnnn	0	0 mm^^			 }}6==D	  D46 F nnnnnnnn}}}}
--MMMM~~~~~~~~##6 % $ "& BYB(2 nnnnnn  
(2  nnnnnnnn~~~~~~  
N4 mm &--fmmFMMJY K  Y -%/K\C
=#L-	-@F;
'T-L`
?% zHHW__%%&	 Y. 	$ &%%&s   b. .c c