Ë
    :vžj!0  ã                   ó*  — d Z ddlZddlmZmZ ddlmZ ddlm	Z	m
Z
 ddlmZ ddlmZmZ 	 ddlZ	 dd
lmZ d„ Zddefd„Zdd„Zdd„Zddefd„Zdd„Zy# e$ rZdd	lmZ  ee«      ZY dZ[Œ=dZ[ww xY w# e$ rZdd	lmZ  ee«      ZY dZ[ŒVdZ[ww xY w)zL
repair.py
-------------

Fill holes and fix winding and normals of meshes.
é    Né   )ÚgraphÚ	triangles)Úlog)Úfaces_to_edgesÚtriangulate_quads)Úconnected_components)Ú
group_rowsÚhashable_rows)ÚExceptionWrapper)Úfaces_to_pathc                 ó"  — | j                   ryt        j                  | j                  «      }d}| j                  j                  t        j                  «      j                  «       }t        j                  |«      D ]Ù  }|j                  |«      }t        t        |j                  «       «      «      }t        j                  ||«      D ]‹  }t        j                  |«      }||   }t!        |«      }	t#        t        j$                  |	d¬«      d¬«      }
t'        |
«      dk(  rŒY|	|
d      }|d   d   |d   d   k(  sŒs|dz  }||d      ddd…   ||d   <   Œ� ŒÛ |dkD  r|| _        t)        j*                  d|t'        | j                  «      d	z  «       y)
zì
    Traverse and change mesh faces in-place to make sure
    winding is correct with edges on adjacent faces in
    opposite directions.

    Parameters
    -------------
    mesh : Trimesh
      Source geometry to alter in-place.
    Nr   r   ©Úaxisé   ©Úrequire_countéÿÿÿÿzflipped %d/%d edgesé   )Úis_winding_consistentÚnxÚfrom_edgelistÚface_adjacencyÚfacesÚviewÚnpÚndarrayÚcopyr	   ÚsubgraphÚnextÚiterÚnodesÚ	bfs_edgesÚravelr   r
   ÚsortÚlenr   Údebug)ÚmeshÚ	graph_allÚflippedr   Ú
componentsÚgÚstartÚ	face_pairÚpairÚedgesÚoverlapÚ	edge_pairs               ú_/workspace/moltex-experiments/.pixi/envs/default/lib/python3.12/site-packages/trimesh/repair.pyÚfix_windingr4   !   se  € ð ×!Ò!Øä× Ñ  ×!4Ñ!4Ó5€IØ€Gà�J‰J�O‰OœBŸJ™JÓ'×,Ñ,Ó.€Eô ×-Ñ-¨iÖ8ˆ
à×Ñ˜zÓ*ˆô ”T˜!Ÿ'™'›)“_Ó%ˆô Ÿ™ a¨Ö/ˆIô
 Ÿ™ Ó+ˆIà˜Ñ#ˆDä" 4Ó(ˆEÜ ¤§¡¨°QÔ!7ÀqÔIˆGÜ�7‹|˜qÒ àØ˜g a™jÑ)ˆIØ˜‰|˜A‰ )¨A¡,¨q¡/Ó1à˜1‘�Ø&+¨I°a©LÑ&9¹$¸B¸$Ñ&?��i ‘lÒ#ñ% 0ð 9ð: �‚{ØˆŒ
ä‡I�IÐ# W¬c°$·*±*«oÀÑ.AÕBó    Ú	multibodyc                 ó@  — |s,| j                   r| j                  dk  r| j                  «        yt        | j                  «      }t        j                  t        | j                  «      t        ¬«      }| j                  }| j                  }| j                  j                  d«      }|D ]s  }t        |«      dk  rŒt        j                   ||   j                  d«      «      \  }}	|r|	sŒAt        j                  ||   ||   d¬«      j                  }
|
dk  sŒod||<   Œu |j!                  «       rrd	| j"                  v r(| j$                  j'                  «       }||xx   d
z  cc<   nd}t        j(                  | j                  |   «      | j                  |<   |�|| _        yyy)zÞ
    Check to see if a mesh has normals pointing "out."

    Parameters
    -------------
    mesh : trimesh.Trimesh
      Mesh to fix in-place.
    multibody : bool
      If True will try to fix normals on every body
    g        N©Údtype)r   é   é   )r   r   T)ÚcrossesÚskip_inertiaÚface_normalsg      ð¿)Úis_watertightÚvolumeÚinvertr	   r   r   Úzerosr&   r   Úboolr   Útriangles_crossr0   Úreshaper   Úmass_propertiesÚanyÚ_cacher>   r   Úfliplr)r(   r6   ÚgroupsÚflipÚtriÚcrossÚ
face_edgesÚ
face_indexÚis_tightÚis_woundr@   Únormalss               r3   Úfix_inversionrS   Z   s}  € ñ Ø×Ò $§+¡+°Ò"3à�K‰KŒMØô " $×"5Ñ"5Ó6€Fô �8‰8”C˜Ÿ
™
“O¬4Ô0€Dð �.‰.€CØ× Ñ €Eà—‘×#Ñ# GÓ,€Jó ˆ
ô ˆz‹?˜QÒØä"×0Ñ0°¸JÑ1G×1OÑ1OÐPWÓ1XÓYÑˆ�(ñ ™XØô ×*Ñ*Ø�
‰O U¨:Ñ%6ÀTô
ç
‰&ð 	ð
 �C‹<Ø#ˆD�Òð' ð, ‡x�x„zØ˜TŸ[™[Ñ(à×'Ñ'×,Ñ,Ó.ˆGØ�D‹M˜TÑ!ŒMàˆGäŸ9™9 T§Z¡Z°Ñ%5Ó6ˆ�
‰
�4ÑàÐØ 'ˆDÕð ð r5   c                 ó4   — t        | «       t        | |¬«       y)a  
    Fix the winding and direction of a mesh face and
    face normals in-place.

    Really only meaningful on watertight meshes but will orient all
    faces and winding in a uniform way for non-watertight face
    patches as well.

    Parameters
    -------------
    mesh : trimesh.Trimesh
      Mesh to fix normals on
    multibody : bool
      if True try to correct normals direction
      on every body rather than just one

    Notes
    --------------
    mesh.faces : will flip columns on inverted faces
    )r6   N)r4   rS   )r(   r6   s     r3   Úfix_normalsrU   Ÿ   s   € ô, �Ôä�$ )Ö,r5   c                 óº  — t        j                  | j                  «      }t        |j	                  «       «      j                  «       D ��cg c]  \  }}|dk7  sŒ|‘Œ }}}t        j                  |«      }|�_|j                  dk7  rPt        j                  |«      }|j                  dk(  s|j                  dk(  sg d¢}|| j                  j                  |<   |S c c}}w )al  
    Return the index of faces in the mesh which break the
    watertight status of the mesh.

    Parameters
    --------------
    mesh : trimesh.Trimesh
      Mesh to check broken faces on
    color: (4,) uint8 or None
      Will set broken faces to this color if not None

    Returns
    ---------------
    broken : (n, ) int
      Indexes of mesh.faces
    r   r   )r;   )r   )éÿ   r   r   rW   )r   r   r   ÚdictÚdegreeÚitemsr   ÚarrayÚsizeÚshapeÚvisualÚface_colors)r(   ÚcolorÚ	adjacencyÚkÚvÚbrokens         r3   Úbroken_facesre   º   s¸   € ô" × Ñ  ×!4Ñ!4Ó5€IÜ  ×!1Ñ!1Ó!3Ó4×:Ñ:Ô<ÔGÑ<‘D�A�qÀÀQÃŠaÐ<€FÑGÜ�X‰X�fÓ€FØÐ˜VŸ[™[¨AÒ-ä—‘˜“ˆØ—‘˜tÒ# u§{¡{°dÒ':Ú$ˆEØ*/ˆ�‰×Ñ Ñ'Ø€Mùó Hs   Á
CÁCÚuse_fanc                 ó\  — t        | j                  «      dk  ry| j                  ryt        | j                  d¬«      }t        |«      dk  ry| j
                  |   }t        j                  t        j                  |«      «      }t        ||¬«      }t        |«      dk(  ryt        |«      }t        |«      }t        |«      }t        j                  ||«      j                  d«      j                  d¬	«      }	t        j                   ||	   «      ||	<   | j#                  |«       | j                  S )
a³  
    Fill boundary holes in-place using fans, which may result
    in bad answers if the holes are non convex!

    Face colors and attributes will be padded with default values
    so shapes match.

    Parameters
    ----------
    mesh : trimesh.Trimesh
        Mesh will be repaired in-place.
    use_fan
      If passed, holes larger than quads will be triangulated
      using fans which are only valid for non-convex holes.
    r   FTr   r   )rf   r   )r   r   r   )r&   r   r?   r
   Úedges_sortedr0   r   Úcycle_basisr   r   r   r   r   ÚisinrE   rG   rI   Úextend_faces)
r(   rf   Úboundary_groupsÚboundaryÚholesÚ	new_facesÚ	new_edgesÚhashable_newÚhashable_oldÚneeds_reverses
             r3   Ú
fill_holesrt   ×   s  € ô  ˆ4�:‰:ƒ˜ÒØØ×ÒØô ! ×!2Ñ!2À!ÔD€Oä
ˆ?Ó˜aÒØð �z‰z˜/Ñ*€Hô �N‰Nœ2×+Ñ+¨HÓ5Ó6€Eô " %°Ô9€IÜ
ˆ9ƒ~˜ÒØô ˜yÓ)€Iô ! Ó+€LÜ  Ó*€Lô —G‘G˜L¨,Ó7×?Ñ?ÀÓH×LÑLÐRSÐLÓT€Mô  "Ÿy™y¨°=Ñ)AÓB€IˆmÑð 	×Ñ�iÔ à×ÑÐr5   c                 ó
  — |€(t        j                  t        | j                  «      «      }t	        | |«      d   D �cg c]E  }t        |j
                  «      dkD  r+|j
                  d   |j
                  d   k(  r|j
                  ‘ŒG }}| j                  }| j                  }| j                  }| j                  }|r½t        j                  |D �	cg c]  }	||	   j                  d¬«      ‘Œ c}	«      }
t        |«      }t        j                  ||
f«      }t        |«      D ��	cg c]N  \  }}	t        j                  t        j                  t        |	«      dz
  t         ¬«      ||z   z  |	dd |	dd f«      ‘ŒP }}}	nV|D �	cg c]K  }	t        j                  t        j                  t        |	«      dz
  t         ¬«      |	d   z  |	dd	 |	d
d f«      ‘ŒM }}	t#        t%        t        |«      «      |«      D ]å  \  }}|dd…dd…f   j'                  «       }|j)                  d¬«       |j+                  |d¬«      }t        |«      dk(  rŒSt        j,                  |«      }|||      }t/        j0                  ||dd    «      \  }}|j3                  «       sŒŸ|d   }t        j4                  ||«      }|j                  «       dk  sŒÎt        j6                  |«      ||<   Œç t        j                  |«      }|r|
fS |S c c}w c c}	w c c}	}w c c}	w )aC  
    Create a fan stitch over the boundary of the specified
    faces. If the boundary is non-convex a triangle fan
    is going to be extremely wonky.

    Parameters
    -----------
    mesh : trimesh.Trimesh
      Mesh to create fan stitch on.
    faces : (n,) int
      Face indexes to stitch with triangle fans.
    insert_vertices : bool
      Allow stitching to insert new vertices?

    Returns
    ----------
    fan : (m, 3) int
      New triangles referencing mesh.vertices.
    vertices : (p, 3) float
      Inserted vertices (only returned `if insert_vertices`)
    NÚentitiesr   r   r   r   r   r8   éþÿÿÿr   é
   g»½×Ùß|Û=)Úr)r   Úaranger&   r   r   ÚpointsÚverticesr>   Ú
edges_faceÚedges_sorted_treer[   ÚmeanÚvstackÚ	enumerateÚcolumn_stackÚonesÚintÚzipÚranger   r%   Úquery_ball_pointÚconcatenater   rR   rG   ÚdotrI   )r(   r   Úinsert_verticesÚer{   r|   rR   r}   Ú	tree_edgeÚpÚ	centroidsÚcountÚiÚfanÚtÚqueryÚ
edge_indexÚoriginalÚcheckÚvalidÚsigns                        r3   Ústitchr™     sÜ  € ð, €}Ü—	‘	œ#˜dŸj™j›/Ó*ˆô ˜t UÓ+¨JÒ7óá7ˆAÜˆq�x‰x‹=˜1Ò §¡¨!¡°·±¸±Ò!<ð 	
�‹Ø7ð ð ð �}‰}€HØ×Ñ€Gð —‘€JØ×&Ñ&€Iáä—H‘HÁÓGÁ¸1˜h q™k×.Ñ.°AÐ.Õ6ÀÑGÓHˆ	ä�H“ˆä—9‘9˜h¨	Ð2Ó3ˆô
 " &Ô)ô
á)‘��1ô �O‰OœRŸW™W¤S¨£V¨a¡Z´sÔ;¸uÀq¹yÑIÈ1ÈSÈbÈ6ÐSTÐUVÐUWÐSXÐYÕZØ)ð 	ò 
ñ ó
á�ô �O‰OœRŸW™W¤S¨£V¨a¡Z´sÔ;¸aÀ¹dÑBÀAÀaÈÀGÈQÈqÐQSÈWÐUÕVØð 	ð 
ô ”Eœ#˜c›(“O SÖ)‰ˆˆ1ð ˆcˆrˆc�1‘2ˆg‰J�O‰OÓˆØ	�‰�AˆŒð
 ×*Ñ*¨1°Ð*Ó6ˆÜˆu‹:˜Š?Øä—^‘^ EÓ*ˆ
ð ˜: jÑ1Ñ2ˆô !×(Ñ(¨°!°B°Q°%©Ó9‰ˆˆuØ�y‰yŒ{Øà�a‘ˆô �v‰v�h Ó&ˆØ�9‰9‹;˜‹?Ü—Y‘Y˜q“\ˆC�ŠFð; *ô> �)‰)�C‹.€CáØ�Iˆ~ÐØ€JùòQùò  Hùó
ùò
s   ¼A
K0ÃK5Ä AK:Å;AL )F)N)NF)Ú__doc__Únumpyr   Ú r   r   Ú	constantsr   Úgeometryr   r   r	   Úgroupingr
   r   Únetworkxr   ÚBaseExceptionÚEÚ
exceptionsr   Úpath.exchange.miscr   r4   rC   rS   rU   re   rt   r™   © r5   r3   Ú<module>r¦      s¡   ðñó ç Ý ß 7Ý 'ß /ðÛð(Ý1ò6CñrB( 4ó B(óJ-ó6ñ:=˜dó =ô@døðK ò õ -á	˜!Ó	…Bûðûð ò (Ý,á$ QÓ'…Mûð(ús.   ¬A ±A5 ÁA2ÁA-Á-A2Á5BÁ:BÂB