
    Ti?                     8   d dl Z d dlZddlmZmZmZ ddlmZm	Z	m
Z
mZmZ ddlmZ 	 d dlZn## e$ rZddlmZ  ee          ZY dZ[ndZ[ww xY wd Zdd	Zd
 ZddZ G d d          Z	 	 	 	 ddedee	         dee         dedede
ej                 fdZd ZdS )    N   )	constantsgroupingutil)	ArrayLikeIntegerNDArrayNumberOptional   )is_ccw)ExceptionWrapperc                     t          j                    }g }t          |           D ]>\  }}|j        r|                    |           "|                    |j        |           ?|t          j        |          fS )a  
    Given a set of entity objects generate a networkx.Graph
    that represents their vertex nodes.

    Parameters
    --------------
    entities : list
       Objects with 'closed' and 'nodes' attributes

    Returns
    -------------
    graph : networkx.Graph
        Graph where node indexes represent vertices
    closed : (n,) int
        Indexes of entities which are 'closed'
    )entity_index)	nxGraph	enumerateclosedappendadd_edges_fromnodesnparray)entitiesgraphr   indexentitys        P/DATA/AppData/hermes/venv/lib/python3.11/site-packages/trimesh/path/traversal.pyvertex_graphr      s    " HJJEF"8,, C Cv= 	CMM%       E BBBB"(6""""    c                 4     fd}||j         d         dk    rd}n6t          |t          j          d                                      }|dz  dz
  }t          j         t          j                   g t          j        t                     dz             D ]f}t          j        t          j        d          |z   t                               } |         }	 |j	        |	 d         }
                    |
           gt          j                  dd|         t                    dk    r*|dk     r"d         }|                                          S t          j        d                   }t          |dd         |dd                   }|D ]d\   |         j                 j                  \  }}|8                             |	                                        |	           et          j                  S )
a  
    Convert a path of vertex indices to a path of entity indices.

    Parameters
    ----------
    vertex_path : (n,) int
        Ordered list of vertex indices representing a path
    graph : nx.Graph
        Vertex connectivity
    entities : (m,) list
        Entity objects
    vertices :  (p, dimension) float
        Vertex points in space

    Returns
    ----------
    entity_path : (q,) int
        Entity indices which make up vertex_path
    c                 D   | d         |d         k    rdS | d         |d         k    rdS | d         |d         k    rdS | d         |d         k    rdS t           j                            d                    g d                   j                 j                   d	S )
a  
        Given two edges, figure out if the first needs to be
         reversed to keep the progression forward.

         [1,0] [1,2] -1  1
         [1,0] [2,1] -1 -1
         [0,1] [1,2]  1  1
         [0,1] [2,1]  1 -1

        Parameters
        ------------
        a : (2,) int
        b : (2,) int

        Returns
        ------------
        a_direction : int
        b_direction : int
        r   r   r   )r$   r$   )r   r   )r   r$   
)zedges not connected!zvertex path %szentity path: %szentity[a]: %s,zentity[b]: %s)NN)r   logdebugjoinpoints)abeaebr   entity_pathvertex_paths     r   edge_directionz-vertex_to_entity_path.<locals>.edge_directionD   s    ( Q41Q4<<5qTQqT\\6qTQqT\\4qTQqT\\5M		    ##    :r    Nr   r   r   dtyper   r$   )	direction)shaper   r   r   
asanyarrayint64arangelenmodget_edge_datar   unique_orderedreversezip
end_pointsr   )r/   r   r   verticesr0   ccw_direction	ccw_checkivertex_path_posvertex_indexr   r   
round_tripdadbr,   r-   r.   s   ` `            @@@r   vertex_to_entity_pathrH   /   s>   *- - - - - - - - -^ 8>!,118BIk;q>$J$JKLL	"Q!+ -28<<<KKYs;''!+,, ) )&1!13{3C3CDD"?3*u*L9.I<(((()+66GK
;11NEUO##%%% ;A77JZ_jn55J / /B 7"9PQQB>RL  2 ...RL  2 ...(;''Kr    c           	      2   t          |           \  }}t          j        |d                                          }t          j                            |          }|D ];}t          |          dk     r|                    t          ||| |                     <|S )a,  
    Paths are lists of entity indices.
    We first generate vertex paths using graph cycle algorithms,
    and then convert them to entity paths.

    This will also change the ordering of entity.points in place
    so a path may be traversed without having to reverse the entity.

    Parameters
    -------------
    entities : (n,) entity objects
        Entity objects
    vertices : (m, dimension) float
        Vertex points in space

    Returns
    -------------
    entity_paths : sequence of (n,) int
        Ordered traversals of entities
    r#   r   )
r   r   reshapetolistr   cyclescycle_basisr8   r   rH   )r   r?   r   r   entity_pathsvertex_pathsr/   s          r   closed_pathsrP      s    , !**ME6:fg..5577L9((//L $ [ [{a1+uhPXYYZZZZr          ?c                 p   t          j        |          }t          |          }|dk    rt          d          |dk    r6t          j        | |d                                      ||                    }ng }t          |          D ]^\  }}| |                             ||          }||dz
  k    r|                    |           A|                    |dd                    _t          j        |          }|j        d         dk    r,t          |          st          j
        |ddd                   }|S )a4  
    Turn a list of entity indices into a path of connected points.

    Parameters
    -----------
    entities : (j,) entity objects
       Objects like 'Line', 'Arc', etc.
    vertices: (n, dimension) float
        Vertex points in space.
    path : (m,) int
        Indexes of entities
    scale : float
        Overall scale of drawing used for
        Number tolerances in certain cases

    Returns
    -----------
    discrete : (p, dimension) float
       Connected points in space that lie on the
       path and can be connected with line segments.
    r   zCannot discretize empty path!r   )scaleNr$   r   )r   r5   r8   
ValueErrordiscreter   r   vstackr4   r   ascontiguousarray)	r   r?   pathrS   path_lenrU   rB   	entity_idcurrents	            r   discretize_pathr\      s9   . }X&&H4yyH1}}89991}}=$q'!2!;!;HE!;!R!RSS %dOO 
	. 
	.LAyy)22852IIGX\""(((( ----9X&&~aAfX&6&6'277Or    c                   n    e Zd ZdefdZ	 ddededeej                 fdZ	de
deej                 fd	Zd
S )
PathSampler)   c                    t          j        |          | _        t          j        | j        d          | _        t          j        | j                  | _        | j        t          j	        j
        k    }| j                                        | _        | j        |xx         | j        |                             d          z  cc<   | j                                        | _        t          j        | j                  | _        d S )Nr   axisr#   )r   r   _pointsdiff_vectorsr   row_norm_normsr   tol_pathzerocopy	_unit_vecrJ   sumlengthcumsum	_cum_norm)selfr)   nonzeros      r   __init__zPathSample.__init__   s    x''1555mDM22+	 2 77++--w4;w#7#?#?#H#HHkoo'' 4;//r    F	distancesinclude_originalreturnc                 l   t          j        | j        |          }t          j        |dt	          | j                  dz
            }t          j        d| j                  |         }||z
  }| j        |         }| j        |         }|||                    d          z  z   }|rt          j	        t          j        | j        d          |           }	|	
                                rPt          j        |t          j        |	          d                   }
t          j        ||
| j        |	         d          }|S )a\  
        Return points at the distances along the path requested.

        Parameters
        ----------
        distances
          Distances along the path to sample at.
        include_original
          Include the original vertices even if they are not
          specified in `distance`. Useful as this will return
          a result with identical area and length, however
          indexes of `distance` will not correspond with result.

        Returns
        --------
        samples : (n, dimension)
          Samples requested.
          `n==len(distances)` if not `include_original`
        r   r   r#   g        r`   )r   searchsortedrn   clipr8   rj   r   rb   rJ   isinanyrp   insert)ro   rr   rs   	positionsoffsets
projectionr3   origin	resampled
uninsertedr   s              r   samplezPathSample.sample  s   0 ODNI>>	GIq#dn*=*=*ABB	)At~..y9(
N9-	i( i**<*<W*E*EEF	 		Z '")DNC"@"@*MMMJ~~ Z	2:j3I3I!3LMMIiZ8PWXYYY	r    distancec                    t          j        | j        |          }|| j        |dz
           z
  }|t          j        j        k     r| j        d|dz            }nt          j        t          j	        | j        t          j
        d          |z            d                              d                    }||z  }| j        |         |z   }t          j        | j        d|dz            |f          }t          j        t          j	        |d                                                    |z
  t          j        j        k     sJ |S )a=  
        Return a truncated version of the path.
        Only one vertex (at the endpoint) will be added.

        Parameters
        ----------
        distance
          Distance along the path to truncate at.

        Returns
        ----------
        path
          Path clipped to `distance` requested.
        r   Nr   r   r`   r$   )r   rv   rn   r   rg   mergerb   r   unitizerc   r7   rJ   rV   re   rk   )ro   r   positionoffset	truncatedvectorendpoints          r   truncatezPathSample.truncate>  s*    ?4>8<<DN8a<88I&,,,^x!|^4II\RYq\\H%<=AFFFNNrRR F fF|H-6H	4<(Q,#?"JKKIM"')!4445599;;hF$% % % % r    N)F)__name__
__module____qualname__r   rq   boolr	   r   float64r   r
   r    r    r   r^   r^      s        0y 0 0 0 0$ >C0 0"06:0		0 0 0 0d GBJ,?      r    r^   TFr)   countstep
step_roundrs   rt   c                    t          j        | t           j                  } ||t          d          ||t          d          t	          |           }|@|r>||j        k    r
| ddg         S t          t          j        |j        |z                      }|t          j        d|j        |          }n|t          j	        d|j        |          }|
                    ||          }t          j        j        rct          j        | ddg         |ddg         z
            }|d         t          j        j        k     sJ ||d         t          j        j        k     sJ |S )	a  
    Given a path along (n,d) points, resample them such that the
    distance traversed along the path is constant in between each
    of the resampled points. Note that this can produce clipping at
    corners, as the original vertices are NOT guaranteed to be in the
    new, resampled path.

    ONLY ONE of count or step can be specified
    Result can be uniformly distributed (np.linspace) by specifying count
    Result can have a specific distance (np.arange) by specifying step


    Parameters
    ----------
    points:   (n, d) float
      Points in space
    count : int,
      Number of points to sample evenly (aka np.linspace)
    step : float
      Distance each step should take along the path (aka np.arange)
    step_round
      Alter `step` to the nearest integer division of overall length.
    include_original
      Include the exact original points in the output.

    Returns
    ----------
    resampled : (j,d) float
        Points on the path
    r1   Nz#Only step OR count can be specifiedz&Either step or count must be specifiedr   r$   )rs   r   )r   r   r   rT   r^   rl   intceillinspacer7   r   r   tolstrictr   re   rg   r   )	r)   r   r   r   rs   samplersamplesr   checks	            r   resample_pathr   `  s`   J XfBJ///F 0>???DLABBB  GJ7>!!1b'?"BGGNT12233+a77		)Aw~t44w9IJJI} 7faWo	1b'0BBCCQx),222228i066666r    c           
      $   t          |           }g }| j        }| j        | j        }| j        }t          | j                  D ]\  }}t          ||                                                   }|	                    |           g }	g }
|D ]c}||         }|		                    t          j        t          |                    t          |
          z              |
                    |           dt          j        | j                  }||d<   t          j        t          |	          dz
  g          }| j        5  |	                     |t          j        | j        |
                   t          j        | j                  |                     |d         j                            |	||         fd|D             |d           |d         j                                         ddd           n# 1 swxY w Y   t          j        |          S )a,  
    Split a Path2D into multiple Path2D objects where each
    one has exactly one root curve.

    Parameters
    --------------
    path : trimesh.path.Path2D
      Input geometry

    Returns
    -------------
    split : list of trimesh.path.Path2D
      Original geometry as separate paths
    split_2Dr   )r   r?   metadatar$   c                      g | ]
}|         S r   r   ).0crU   s     r   
<listcomp>zsplit.<locals>.<listcomp>  s     @ @ @! @ @ @r    )pathspolygons_closedrU   rootN)typer   rU   r   enclosure_directedr   r   listkeysr   r   r7   r8   extendri   deepcopyr   r   _cacher   r?   updateid_set)rX   Path2Dsplitr   r   r   
root_indexr   	connected	new_pathsnew_entitiesr   r   r   new_rootrU   s                  @r   r   r     sZ     $ZZF E JE}H*O0%di00 ,& ,&
D+D1668899	 	 	' 	'E%LERYs5zz22S5F5FFGGG&&&& =//)8S^^a/011 [ 	& 	&LL!]4=+FGG!]4=99%     "I##&'6y'A @ @ @ @i @ @ @$	    "I##%%%)	& 	& 	& 	& 	& 	& 	& 	& 	& 	& 	& 	& 	& 	& 	&, 8E??s   9B,G11G5	8G5	)N)rQ   )NNTF)ri   numpyr    r   r   r   typedr   r   r	   r
   r   r   networkxr   BaseExceptionE
exceptionsr   r   rH   rP   r\   r^   r   r   r   r   r   r    r   <module>r      s        ( ( ( ( ( ( ( ( ( ( A A A A A A A A A A A A A A          .-----		!		BBBBBB# # #8k k k k\$ $ $N3 3 3 3lc c c c c c c cP  $!"@ @@G@ 6
@ 	@
 @ RZ@ @ @ @FJ J J J Js   - AAA