Ë
    vl�j8m  ã                   ó¤  — U d dl Z d dlZd dlZd dlZd dlZd dlmZ d dlmZm	Z	m
Z
mZmZmZmZmZmZmZ ddlmZmZmZmZmZmZ ddlmZ ddlmZ dd	lmZ  ej>                  e «      Z!d
Z"d
Z#dZ$dZ%dZ&ee'd<   dZ(ee'd<   ddddddddœZ)dede	egef   fd„Z*dede	egeeef   f   fd„Z+ ed«       ed
«       ed «       ed«      dœZ, ed«       ed«       ed «       ed!«      dœZ-d;deded"e.ddfd#„Z/ G d$„ d%«      Z0 G d&„ d'«      Z1 G d(„ d)«      Z2	 d<d*ed+e3d,edefd-„Z4 e jj                  e1jl                  «      jn                  jq                  «       Z9 e jj                  e2«      jn                  jq                  «       Z:d*ed,ede0fd.„Z;	 	 d=d*ed/ee   d0ee   d,ede.f
d1„Z<e"fd2ed3ede.fd4„Z=e"e#fd*ed5ed6ede.fd7„Z>	 	 d>d*ed3ed8eee.d9f      defd:„Z?y)?é    N)Ú
itemgetter)
ÚAnyÚCallableÚDictÚ	GeneratorÚListÚMatchÚOptionalÚPatternÚTupleÚUnioné   )ÚT_bboxÚT_dirÚT_numÚT_objÚ
T_obj_iterÚ
T_obj_listé   )Úcluster_objects)Úto_list)Úobjects_to_bboxé   g      @é   ÚttbÚDEFAULT_LINE_DIRÚltrÚDEFAULT_CHAR_DIRÚffÚffiÚfflÚfiÚflÚst)u   ï¬€u   ï¬ƒu   ï¬„u   ï¬�u   ï¬‚u   ï¬†u   ï¬…Úline_dirÚreturnc                 ó   — d„ d„ d„ d„ dœ|    S )Nc                 ó   — | d   S )NÚtop© ©Úxs    úK/var/www/html/pp/venv/lib/python3.12/site-packages/pdfplumber/utils/text.pyú<lambda>z&get_line_cluster_key.<locals>.<lambda>/   s
   € ˜˜5™€ ó    c                 ó   — | d    S )NÚbottomr*   r+   s    r-   r.   z&get_line_cluster_key.<locals>.<lambda>0   s   € ˜!˜H™+˜€ r/   c                 ó   — | d   S ©NÚx0r*   r+   s    r-   r.   z&get_line_cluster_key.<locals>.<lambda>1   s
   € ˜˜4™€ r/   c                 ó   — | d    S )NÚx1r*   r+   s    r-   r.   z&get_line_cluster_key.<locals>.<lambda>2   s   € ˜!˜D™'˜€ r/   ©r   Úbttr   Úrtlr*   )r%   s    r-   Úget_line_cluster_keyr:   -   s"   € á!Ù%Ù Ù!ñ	ð
 ñð r/   Úchar_dirc                 ó   — d„ d„ d„ d„ dœ|    S )Nc                 ó   — | d   | d   fS )Nr)   r1   r*   r+   s    r-   r.   z#get_char_sort_key.<locals>.<lambda>8   s   € ˜!˜E™( A h¡KÐ0€ r/   c                 ó&   — | d   | d   z    | d    fS )Nr)   Úheightr*   r+   s    r-   r.   z#get_char_sort_key.<locals>.<lambda>9   s!   € ˜A˜e™H q¨¡{Ñ2Ð3°a¸±h°YÐ?€ r/   c                 ó   — | d   | d   fS r3   r*   r+   s    r-   r.   z#get_char_sort_key.<locals>.<lambda>:   s   € ˜!˜D™' 1 T¡7Ð+€ r/   c                 ó   — | d    | d    fS )Nr6   r4   r*   r+   s    r-   r.   z#get_char_sort_key.<locals>.<lambda>;   s   € ˜1˜T™7˜( Q t¡W HÐ-€ r/   r7   r*   )r;   s    r-   Úget_char_sort_keyrB   6   s"   € á0Ù?Ù+Ù-ñ	ð
 ñð r/   r7   r)   r1   r4   r6   Úsuffixc           
      óú   — t        t        j                  «       «      }| |vrt        d|› d|› d| › �«      ‚||vrt        d|› d|› d|› �«      ‚t        | «      t        |«      k(  rt        d|› d| › d|› d|› �«      ‚y )Nr%   z must be one of z, not r;   ú=z is incompatible with char_dir)ÚsetÚPOSITION_KEYSÚkeysÚ
ValueError)r%   r;   rC   Ú
valid_dirss       r-   Úvalidate_directionsrK   N   sµ   € Ü”]×'Ñ'Ó)Ó*€JØ�zÑ!ÜØ�v�hÐ.¨z¨l¸&ÀÀ
ÐKó
ð 	
ð �zÑ!ÜØ�v�hÐ.¨z¨l¸&ÀÀ
ÐKó
ð 	
ô ˆ8ƒ}œ˜H›Ò%ÜØ�v�h˜a ˜zð *Ø"˜8 1 X Jð0ó
ð 	
ð &r/   c                   óö   — e Zd ZdZdeeeee   f      de	de	ddfd„Z
defd„Z	 	 	 dd	ee   d
edededeeef   f
d„Z	 	 	 	 	 ddeeee   f   dedededed
edeeeef      fd„Z	 ddededeeeef      fd„Zy)ÚTextMapz–
    A TextMap maps each unicode character in the text to an individual `char`
    object (or, in the case of layout-implied whitespace, `None`).
    ÚtuplesÚline_dir_renderÚchar_dir_renderr&   Nc                 ór   — t        ||d«       || _        || _        || _        | j	                  «       | _        y )NÚ_render)rK   rN   rO   rP   Ú	to_stringÚ	as_string)ÚselfrN   rO   rP   s       r-   Ú__init__zTextMap.__init__e   s5   € ô 	˜O¨_¸iÔHØˆŒØ.ˆÔØ.ˆÔØŸ™Ó)ˆ�r/   c           	      ó¨  ‡— | j                   }| j                  }dj                  t        t	        d«      | j
                  «      «      }|dk(  r|dk(  r|S |j                  d«      Š|dv rt        t        ‰«      «      Š|dk(  r(‰D �cg c]  }dj                  t        |«      «      ‘Œ c}Š|dv r†t        t        t        ‰«      «      }|d	k(  r#‰D �cg c]  }d
|t        |«      z
  z  |z   ‘Œ c}Šn"‰D �cg c]  }|d
|t        |«      z
  z  z   ‘Œ c}Šdj                  ˆfd„t        |«      D «       «      S dj                  ‰«      S c c}w c c}w c c}w )NÚ r   r   r   ú
©r8   r9   r9   )r9   r   r8   ú c              3   óT   •‡K  — | ]  Šd j                  ˆfd„‰D «       «      –— Œ  y­w)rX   c              3   ó(   •K  — | ]	  }|‰   –— Œ y ­w©Nr*   )Ú.0ÚlineÚis     €r-   ú	<genexpr>z.TextMap.to_string.<locals>.<genexpr>.<genexpr>Œ   s   øè ø€ Ò6¨˜D �GÑ6ùs   ƒN©Újoin)r_   ra   Úliness    @€r-   rb   z$TextMap.to_string.<locals>.<genexpr>‹   s%   ùè ø€ ò !Ø;<�B—G‘GÓ6°Ô6×6ñ!ùs   „$()rP   rO   rd   Úmapr   rN   ÚsplitÚlistÚreversedÚmaxÚlenÚrange)rU   ÚcdÚldÚbaser`   Úmax_line_lengthre   s         @r-   rS   zTextMap.to_stringq   sI  ø€ Ø×!Ñ!ˆØ×!Ñ!ˆà�w‰w”sœ: a›=¨$¯+©+Ó6Ó7ˆà�Š;˜2 š;ØˆKà—J‘J˜tÓ$ˆEØ�^Ñ#ÜœX e›_Ó-�à�UŠ{Ø=BÖC°T˜Ÿ™¤¨$£Õ0ÒC�à�^Ñ#Ü"%¤c¬#¨u£oÓ"6�Ø˜’;àQVöØIM˜ ´#°d³)Ñ ;Ñ<ÀÓDò‘Eð
 RWöØIM˜  ¼¸T»Ñ'BÑ CÓDò�Eð —y‘yó !Ü@EÀoÓ@Vô!ó ð ð —y‘y Ó'Ð'ùò! Dùò
ùòs   Â!EÃE
Ã3EÚmÚ
main_groupÚreturn_groupsÚreturn_charsc                 ó   — | j                   |j                  |«      |j                  |«       }|D ��cg c]
  \  }}|€Œ	|‘Œ }}}t        |«      \  }	}
}}|j	                  |«      |	|
||dœ}|r|j                  «       |d<   |r||d<   |S c c}}w )N)Útextr4   r)   r6   r1   ÚgroupsÚchars)rN   ÚstartÚendr   Úgrouprw   )rU   rq   rr   rs   rt   Úsubsetrv   Úcrx   r4   r)   r6   r1   Úresults                 r-   Úmatch_to_dictzTextMap.match_to_dict‘   s    € ð —‘˜QŸW™W ZÓ0°1·5±5¸Ó3DÐEˆØ$*×<‘y˜˜a¨a©m’Ð<ˆÑ<Ü-¨eÓ4ÑˆˆC��Vð —G‘G˜JÓ'ØØØØñ
ˆñ Ø Ÿx™x›zˆF�8ÑáØ#ˆF�7‰Oàˆùó# =s
   ³
B
¾B
ÚpatternÚregexÚcasec           	      óž  ‡— t        |t        «      r!|du rt        d«      ‚|du rt        d«      ‚|}nE|du rt        j                  |«      }|du rt        j
                  nd}t        j                  ||«      }t        j                  || j                  «      }	t        ˆfd„|	«      }
|
D �cg c]  }| j                  |||‰¬«      ‘Œ c}S c c}w )NFzACannot pass a compiled search pattern *and* regex=False together.z@Cannot pass a compiled search pattern *and* case=False together.r   c                 óT   •— t        | j                  ‰«      j                  «       «      S r^   )Úboolr{   Ústrip)rq   rr   s    €r-   r.   z TextMap.search.<locals>.<lambda>É   s   ø€ ¤D¨¯©°Ó)<×)BÑ)BÓ)DÓ$E€ r/   )rs   rt   rr   )Ú
isinstancer   rI   ÚreÚescapeÚIÚcompileÚfinditerrT   Úfilterr   )rU   r€   r�   r‚   rs   rt   rr   ÚcompiledÚflagsÚgenÚfilteredrq   s         `     r-   ÚsearchzTextMap.search¬   sß   ø€ ô �gœwÔ'Ø˜‰~Ü ØWóð ð �u‰}Ü ØVóð ð ‰Hà˜‰~ÜŸ)™) GÓ,�à  E™M”B—D’D¨qˆEÜ—z‘z '¨5Ó1ˆHä�k‰k˜( D§N¡NÓ3ˆô ÓEÀsÓKˆð ö
ð ð ×ÑØØ+Ø)Ø%ð	 õ ò
ð 	
ùò 
s   Â+C
r†   c                 ó:   — |rd}nd}| j                  |d|d¬«      S )af  
        `strip` is analogous to Python's `str.strip()` method, and returns
        `text` attributes without their surrounding whitespace. Only
        relevant when the relevant TextMap is created with `layout` = True

        Setting `return_chars` to False will exclude the individual
        character objects from the returned text-line dicts.
        z *([^\n]+?) *(\n|$)z([^\n]+)r   F)rr   rt   rs   )r’   )rU   r†   rt   Úpats       r-   Úextract_text_lineszTextMap.extract_text_linesÔ   s0   € ñ Ø(‰CàˆCà�{‰{Ø˜A¨LÈð ó 
ð 	
r/   )r   TT)TTTTr   )TT)Ú__name__Ú
__module__Ú__qualname__Ú__doc__r   r   Ústrr
   r   r   rV   rS   r	   Úintr…   r   r   r   r   r   r’   r•   r*   r/   r-   rM   rM   _   sC  „ ñð

*à�U˜3 ¨¡Ð/Ñ0Ñ1ð
*ð ð
*ð ð	
*ð
 
ó
*ð(˜3ó (ðF Ø"Ø!ñà�‰:ðð ðð ð	ð
 ðð 
ˆc�3ˆh‰óð< ØØ"Ø!Øñ&
à�s˜G C™LÐ(Ñ)ð&
ð ð&
ð ð	&
ð
 ð&
ð ð&
ð ð&
ð 
ˆd�3˜�8‰nÑ	ó&
ðR 8<ñ
Øð
Ø04ð
à	ˆd�3˜�8‰nÑ	ô
r/   rM   c            +       óÎ   — e Zd ZdZdeeeef      ddfd„Zdddddde	e
ddeeeddddddd	fd
edededededededededededededee   dee   dee   dee   dedededef*d„Zy)ÚWordMapz&
    A WordMap maps words->chars.
    rN   r&   Nc                 ó   — || _         y r^   )rN   )rU   rN   s     r-   rV   zWordMap.__init__î   s	   € Øˆ�r/   Fr   )r   r   r   r   TÚlayoutÚlayout_widthÚlayout_heightÚlayout_width_charsÚlayout_height_charsÚlayout_bboxÚ	x_densityÚ	y_densityÚx_shiftÚy_shiftÚy_tolerancer%   r;   Úline_dir_rotatedÚchar_dir_rotatedrP   rO   Úuse_text_flowÚ	presortedÚexpand_ligaturesc                 ó²  ‡2‡3— g }t        | j                  «      st        ||xs ||xs |¬«      S |rt        ni }|rS|r|r"t	        d«      ‚t        t        ||z  «      «      }|r|r"t	        d«      ‚t        t        ||z  «      «      }dg|z  }ng }d}t        |«      Š3t        |«      Š2t        |   }t        |   }t        |   |«      }t        |   |«      }|s|r| j                  nt        | j                  ˆ3fd„¬«      }t        |ˆ3fd„||xs |¬	«      }t        |«      D �][  \  }} |r' || d   d   «      }!|!||
z   z
  }"|d
v rdnd}#|"|#z  |z  }$nd}$t        t        |dkD  «      t        |$«      |z
  «      }%t        |%«      D ].  }t        |«      r|d   d   dk(  r||z  }|j!                  d«       Œ0 ||%z  }d}&|s|r| nt        | ˆ2fd„¬«      }'|'D ]˜  \  }(})|r! ||(«      }*|*||	z   z
  }+|d
v rdnd}#|+|#z  |z  },nd},t        t#        d|&«      t        |,«      |&z
  «      }-|dg|-z  z  }|&|-z  }&|)D ]9  }.|j%                  |.d   |.d   «      }/|/D ]  }0|j!                  |0|.f«       |&dz  }&Œ Œ; Œš |s�ŒP|dg||&z
  z  z  }�Œ^ |r@||dz   z
  }1t        |1«      D ]  }|dkD  r||z  }|j!                  d«       Œ |d   dk(  r|dd }t        ||xs ||xs |¬«      S )a¹  
        Given a list of (word, chars) tuples (i.e., a WordMap), return a list of
        (char-text, char) tuples (i.e., a TextMap) that can be used to mimic
        the structural layout of the text on the page(s), using the following
        approach for top-to-bottom, left-to-right text:

        - Sort the words by (top, x0) if not already sorted.

        - Cluster the words by top (taking `y_tolerance` into account), and
          iterate through them.

        - For each cluster, divide (top - y_shift) by `y_density` to calculate
          the minimum number of newlines that should come before this cluster.
          Append that number of newlines *minus* the number of newlines already
          appended, with a minimum of one.

        - Then for each cluster, iterate through each word in it. Divide each
          word's x0, minus `x_shift`, by `x_density` to calculate the minimum
          number of characters that should come before this cluster.  Append that
          number of spaces *minus* the number of characters and spaces already
          appended, with a minimum of one. Then append the word's text.

        - At the termination of each line, add more spaces if necessary to
          mimic `layout_width`.

        - Finally, add newlines to the end if necessary to mimic to
          `layout_height`.

        For other line/character directions (e.g., bottom-to-top,
        right-to-left), these steps are adjusted.
        ©rO   rP   z;`layout_width` and `layout_width_chars` cannot both be set.z=`layout_height` and `layout_height_chars` cannot both be set.)r[   Nr   c                 ó   •—  ‰| d   «      S ©Nr   r*   ©r,   Úline_cluster_keys    €r-   r.   z$WordMap.to_textmap.<locals>.<lambda>U  s   ø€ Ñ3CÀAÀaÁDÓ3I€ r/   ©Úkeyc                 ó   •—  ‰| d   «      S r²   r*   r³   s    €r-   r.   z$WordMap.to_textmap.<locals>.<lambda>Z  s   ø€ Ñ& q¨¡tÓ,€ r/   )Úpreserve_orderrZ   éÿÿÿÿr   rY   )rY   Nc                 ó   •—  ‰| d   «      S r²   r*   )r,   Úchar_sort_keys    €r-   r.   z$WordMap.to_textmap.<locals>.<lambda>z  s   ø€ ±}ÀQÀqÁTÓ7J€ r/   rv   N)rk   rN   rM   Ú	LIGATURESrI   r›   Úroundr:   rB   rG   ÚBBOX_ORIGIN_KEYSÚsortedr   Ú	enumeraterj   rl   ÚappendÚminÚget)4rU   rŸ   r    r¡   r¢   r£   r¤   r¥   r¦   r§   r¨   r©   r%   r;   rª   r«   rP   rO   r¬   r­   r®   Ú_textmapÚ
expansionsÚ
blank_lineÚnum_newlinesÚline_position_keyÚchar_position_keyÚy_originÚx_originÚwords_sorted_line_dirÚtuples_by_linera   Úline_tuplesÚline_positionÚ
y_dist_rawÚadjÚy_distÚnum_newlines_prependÚline_lenÚline_tuples_sortedÚwordrx   Úchar_positionÚ
x_dist_rawÚx_distÚnum_spaces_prependr}   ÚlettersÚletterÚnum_newlines_appendr»   r´   s4                                                     @@r-   Ú
to_textmapzWordMap.to_textmapñ   s°  ù€ ðl 79ˆä�4—;‘;ÔÜØØ /Ò ;°8Ø /Ò ;°8ôð ñ #3•Y¸ˆ
áÙ!ÙÜ$ØUóð ô &)¬¨|¸iÑ/GÓ)HÓ%IÐ"á"Ù Ü$ØWóð ô '*¬%°À	Ñ0IÓ*JÓ&KÐ#à%˜Ð);Ñ;‰JàˆJàˆä/°Ó9ÐÜ)¨(Ó3ˆä)¨(Ñ3ÐÜ)¨(Ñ3Ðä# HÑ-¨kÓ:ˆÜ# HÑ-¨kÓ:ˆñ ™Mð �KŠKä˜Ÿ™Ó)IÔJð 	ô )Ø!Û,ØØ$Ò5¨ô	
ˆô (¨Ó7ó 3	L‰NˆAˆ{ÙÙ 1°+¸a±.ÀÑ2CÓ D�Ø*¨h¸Ñ.@ÑA�
Ø$¨Ñ6‘b¸A�Ø# cÑ)¨IÑ5‘à�Ü#&ä�A˜‘E“
ä�f“ Ñ,ó	$Ð ô Ð/Ó0ò .�Ü˜8”}¨°©°Q©¸4Ò(?Ø 
Ñ*�HØ—‘ Õ-ð.ð
 Ð0Ñ0ˆLàˆHñ ¡ñ ä˜KÓ-JÔKð ð  2ò &‘��eÙÙ$5°dÓ$;�MØ!.°(¸WÑ2DÑ!E�JØ (¨NÑ :™"À�CØ'¨#Ñ-°	Ñ9‘Fà�Fä%(¬¨Q°Ó)9¼5À»=È8Ñ;SÓ%TÐ"Ø˜[˜MÐ,>Ñ>Ñ>�ØÐ.Ñ.�àò &�AØ(Ÿn™n¨Q¨v©Y¸¸&¹	ÓB�GØ")ò &˜Ø Ÿ™¨°¨Ô4Ø  A™™ñ&ñ&ð&ó( Ø˜[˜MÐ-?À(Ñ-JÑKÑK’ðg3	Lñl Ø"5¸ÈÑ9IÑ"JÐÜÐ.Ó/ò .�Ø�q’5Ø 
Ñ*�HØ—‘ Õ-ð.ð ˜‰|˜|Ò+Ø# C R˜=�äØØ+Ò7¨xØ+Ò7¨xô
ð 	
r/   )r–   r—   r˜   r™   r   r   r   r   rV   ÚDEFAULT_X_DENSITYÚDEFAULT_Y_DENSITYÚDEFAULT_Y_TOLERANCEr   r   r…   r   r›   r   r   r
   rM   rÞ   r*   r/   r-   r�   r�   é   sb  „ ñð˜t E¨%°Ð*;Ñ$<Ñ=ð À$ó ð
 ØØ Ø"#Ø#$Ø*Ø,Ø,ØØØ0Ø*Ø*Ø,0Ø,0Ø+/Ø+/Ø#ØØ!%ñ+s
àðs
ð ðs
ð ð	s
ð
  ðs
ð !ðs
ð ðs
ð ðs
ð ðs
ð ðs
ð ðs
ð ðs
ð ðs
ð ðs
ð # 5™/ðs
ð  # 5™/ð!s
ð" " %™ð#s
ð$ " %™ð%s
ð& ð's
ð( ð)s
ð* ð+s
ð, 
ô-s
r/   r�   c                   ó~  — e Zd Zeeddddddeedddddfdededee	e
df   dee	e
df   ded	ed
ededededee   dee   deee      deeef   defd„Zde	defd„Zdedefd„Zdedededededefd„Zdededeeddf   fd„Zdedeeeef   ddf   fd„Zdedeeeef   ddf   fd „Zdedefd!„Z	 d$ded"edefd#„Zy)%ÚWordExtractorNFTÚx_tolerancer©   Úx_tolerance_ratioÚy_tolerance_ratioÚkeep_blank_charsr¬   Úvertical_ttbÚhorizontal_ltrr%   r;   rª   r«   Úextra_attrsÚsplit_at_punctuationr®   c                 ó   — || _         || _        || _        || _        || _        || _        || _        || _        |du rt        j                  d«       |du rt        j                  d«       |	| _
        |
| _        |xs |
| _        |xs |	| _        t        | j                  | j                  «       t        | j                  | j                  d«       |€g n|| _        |du rt         j"                  n|xs d| _        |rt&        | _        y i | _        y )NFzNvertical_ttb is deprecated and will be removed; use line_dir/char_dir instead.zPhorizontal_ltr is deprecated and will be removed; use line_dir/char_dir instead.Ú_rotatedTrX   )rä   r©   rå   ræ   rç   r¬   ré   rè   ÚloggerÚwarningr%   r;   rª   r«   rK   rê   ÚstringÚpunctuationrë   r¼   rÅ   )rU   rä   r©   rå   ræ   rç   r¬   rè   ré   r%   r;   rª   r«   rê   rë   r®   s                   r-   rV   zWordExtractor.__init__¨  s  € ð$ 'ˆÔØ&ˆÔØ!2ˆÔØ!2ˆÔØ 0ˆÔØ*ˆÔØ,ˆÔØ(ˆÔØ˜5Ñ Ü�N‰Nð2ôð ˜UÑ"Ü�N‰Nð2ôð !ˆŒØ ˆŒà 0Ò <°HˆÔØ 0Ò <°HˆÔÜ˜DŸM™M¨4¯=©=Ô9Ü˜D×1Ñ1°4×3HÑ3HÈ*ÔUØ!,Ð!4™2¸+ˆÔð
 $ tÑ+ô ×Òà&Ò,¨"ð 	Ô!ñ (8œ)ˆ�¸Rˆ�r/   Úuprightr&   c                 ór   — |s| j                   sy|r| j                  sy|r| j                  S | j                  S )Nr8   r9   )rè   ré   r;   r«   )rU   rò   s     r-   Úget_char_dirzWordExtractor.get_char_dirÞ  s7   € ñ ˜t×0Ò0Øá˜T×0Ò0Øá 'ˆt�}‰}ÐB¨T×-BÑ-BÐBr/   Úordered_charsc                 ó  ‡ — t        |«      \  }}}}|d   d   |d   d   z
  }|d   d   }‰ j                  |«      }dj                  ˆ fd„|D «       «      |||||z   ||||z
  ||z
  |dœ
}	‰ j                  D ]  }
|d   |
   |	|
<   Œ |	S )Nr   Údoctopr)   rò   rX   c              3   ój   •K  — | ]*  }‰j                   j                  |d    |d    xs d«      –— Œ, y­w)rv   rX   N)rÅ   rÃ   )r_   r}   rU   s     €r-   rb   z,WordExtractor.merge_chars.<locals>.<genexpr>ñ  s3   øè ø€ ò ØDE�—‘×#Ñ# A f¡I¨q°©yª¸B×?ñùs   ƒ03)
rv   r4   r6   r)   r÷   r1   rò   r?   ÚwidthÚ	direction)r   rô   rd   rê   )rU   rõ   r4   r)   r6   r1   Ú
doctop_adjrò   r;   rÖ   r¶   s   `          r-   Úmerge_charszWordExtractor.merge_charsê  sÐ   ø€ Ü-¨mÓ<ÑˆˆC��VØ" 1Ñ% hÑ/°-ÀÑ2BÀ5Ñ2IÑIˆ
Ø Ñ" 9Ñ-ˆØ×$Ñ$ WÓ-ˆð —G‘Gó ØIVôó ð ØØØ˜JÑ&ØØØ˜s‘lØ˜"‘WØ!ñ
ˆð ×#Ñ#ò 	.ˆCØ% aÑ(¨Ñ-ˆD�ŠIð	.ð ˆr/   Ú	prev_charÚ	curr_charrú   c                 ó6  — |dv r6|}|}|d   }|d   }	|dk(  r|d   }
|d   }|d   }nH|d    }
|d    }|d    }n5|}|}|d   }|d   }	|dk(  r|d   }
|d   }|d   }n|d    }
|d    }|d    }t        ||
k  xs |||z   kD  xs t        |	|z
  «      |kD  «      S )a”  This method takes several factors into account to determine if
        `curr_char` represents the beginning of a new word:

        - Whether the text is "upright" (i.e., non-rotated)
        - Whether the user has specified that horizontal text runs
          left-to-right (default) or right-to-left, as represented by
          self.horizontal_ltr
        - Whether the user has specified that vertical text the text runs
          top-to-bottom (default) or bottom-to-top, as represented by
          self.vertical_ttb
        - The x0, top, x1, and bottom attributes of prev_char and
          curr_char
        - The self.x_tolerance and self.y_tolerance settings. Note: In
          this case, x/y refer to those directions for non-rotated text.
          For vertical text, they are flipped. A more accurate terminology
          might be "*intra*line character distance tolerance" and
          "*inter*line character distance tolerance"

        An important note: The *intra*line distance is measured from the
        *end* of the previous character to the *beginning* of the current
        character, while the *inter*line distance is measured from the
        *top* of the previous character to the *top* of the next
        character. The reasons for this are partly repository-historical,
        and partly logical, as successive text lines' bounding boxes often
        overlap slightly (and we don't want that overlap to be interpreted
        as the two lines being the same line).

        The upright-ness of the character determines the attributes to
        compare, while horizontal_ltr/vertical_ttb determine the direction
        of the comparison.
        )r   r9   r)   r   r4   r6   r   r1   )r…   Úabs)rU   rý   rþ   rú   rä   r©   r,   ÚyÚayÚcyÚaxÚbxÚcxs                r-   Úchar_begins_new_wordz"WordExtractor.char_begins_new_word  s  € ðR ˜Ñ&ØˆAØˆAØ˜5Ñ!ˆBØ˜5Ñ!ˆBØ˜EÒ!Ø˜t‘_�Ø˜t‘_�Ø˜t‘_‘à ‘oÐ%�Ø ‘oÐ%�Ø ‘oÐ%‘ð ˆAØˆAØ˜4‘ˆBØ˜4‘ˆBØ˜EÒ!Ø˜uÑ%�Ø˜xÑ(�Ø˜uÑ%‘à Ñ)Ð)�Ø Ñ&Ð&�Ø Ñ)Ð)�äà�"‰Wò  Ø�R˜!‘V‘ò ô �2˜‘7‹|˜aÑó
ð 	
r/   c           
   #   óT  ‡
K  — g Š
dt         t           dt        t        d d f   fˆ
fd„}| j                  }| j
                  }| j                  }| j                  }|D ]º  }|d   }	| j                  s!|	j                  «       r |d «      E d {  –—†  Œ5|	| j                  v r! ||«      E d {  –—†   |d «      E d {  –—†  Œd‰
rD| j                  ‰
d   |||€|n
|‰
d   d   z  |€|n
|‰
d   d   z  ¬«      r ||«      E d {  –—†  Œª‰
j                  |«       Œ¼ ‰
r‰
–— y y 7 Œ•7 Œx7 Œj7 Œ&­w)NÚnew_charr&   c              3   ó*   •K  — ‰r‰–— | €g Šy | gŠy ­wr^   r*   )r	  Úcurrent_words    €r-   Ústart_next_wordz:WordExtractor.iter_chars_to_words.<locals>.start_next_wordX  s"   øè ø€ ñ
 Ø"Ò"à!)Ð!1˜2‰L¸°z‰Lùs   ƒrv   r¹   Úsize)rä   r©   )r
   r   r   r   rä   rå   r©   ræ   rç   Úisspacerë   r  rÁ   )rU   rõ   rú   r  ÚxtÚxtrÚytÚytrÚcharrv   r  s             @r-   Úiter_chars_to_wordsz!WordExtractor.iter_chars_to_wordsQ  s]  øè ø€ ð
 $&ˆð	BÜœu‘oð	Bä”z 4¨Ð-Ñ.õ	Bð ×ÑˆØ×$Ñ$ˆØ×ÑˆØ×$Ñ$ˆà!ò 	*ˆDØ˜‘<ˆDà×(Ò(¨T¯\©\¬^Ù*¨4Ó0×0Ñ0à˜×2Ñ2Ñ2Ù*¨4Ó0×0Ð0Ù*¨4Ó0×0Ñ0á $×";Ñ";Ø˜RÑ ØØØ#& ;™R°C¸,ÀrÑ:JÈ6Ñ:RÑ4RØ#& ;™R°C¸,ÀrÑ:JÈ6Ñ:RÑ4Rð #<ô #ñ +¨4Ó0×0Ñ0ð ×#Ñ# DÕ)ð)	*ñ. ØÓð ð' 1øð 1øØ0øð 1úsI   ƒBD(Â
D ÂD(Â)D"Â*D(Â9D$Â:AD(Ã?D&Ä !D(Ä"D(Ä$D(Ä&D(rx   c              #   ó6  K  — t        |«      }|d   d   }|r| j                  n| j                  }| j                  |«      }t	        |«      }t        |«      }t        |||dv r| j                  n| j                  «      }|D ]  }t        ||¬«      }	|	|f–— Œ y ­w)Nr   rò   ©r   r8   rµ   )
rh   r%   rª   rô   r:   rB   r   r©   rä   r¿   )
rU   rx   rò   r%   r;   r´   r»   ÚsubclustersÚscÚchars_sorteds
             r-   Úiter_chars_to_linesz!WordExtractor.iter_chars_to_lines�  s©   è ø€ ô �U“ˆØ˜‘(˜9Ñ%ˆÙ$+�4—=’=°×1FÑ1FˆØ×$Ñ$ WÓ-ˆä/°Ó9ÐÜ)¨(Ó3ˆô &ØØØ!)¨^Ñ!;ˆT×ÒÀ×AQÑAQó
ˆð ò 	+ˆBä! "¨-Ô8ˆLØ Ð*Ó*ñ	+ùs   ‚BBc              #   ó<  K  — t        dg| j                  ¢­Ž }t        j                  ||«      }|D ]g  \  }}| j                  r|| j
                  fgn| j                  |«      }|D ]1  \  }}| j                  ||«      D ]  }	| j                  |	«      |	f–— Œ Œ3 Œi y ­w)Nrò   )	r   rê   Ú	itertoolsÚgroupbyr¬   r;   r  r  rü   )
rU   rx   Úgrouping_keyÚgrouped_charsÚkeyvalsÚ
char_groupÚline_groupsÚ
line_charsrú   Ú
word_charss
             r-   Úiter_extract_tuplesz!WordExtractor.iter_extract_tuples˜  sÀ   è ø€ ô " )Ð?¨d×.>Ñ.>Ò?ˆÜ!×)Ñ)¨%°Ó>ˆà#0ò 	EÑˆG�Zð ×%Ò%ð ˜dŸm™mÐ,Ñ-à×-Ñ-¨jÓ9ð ð
 *5ò EÑ%�
˜IØ"&×":Ñ":¸:ÀyÓ"Qò E�JØ×+Ñ+¨JÓ7¸ÐDÓDñEñEñ	Eùs   ‚BBc                 óH   — t        t        | j                  |«      «      «      S r^   )r�   rh   r%  )rU   rx   s     r-   Úextract_wordmapzWordExtractor.extract_wordmap¨  s   € Ü”t˜D×4Ñ4°UÓ;Ó<Ó=Ð=r/   rt   c                 óŠ   — |r!t        d„ | j                  |«      D «       «      S t        d„ | j                  |«      D «       «      S )Nc              3   ó2   K  — | ]  \  }}i |¥d |i¥–— Œ y­w)rx   Nr*   ©r_   rÖ   r$  s      r-   rb   z.WordExtractor.extract_words.<locals>.<genexpr>¯  s(   è ø€ ò á$�D˜*ð .�4Ð-˜ *Õ-ñùs   ‚c              3   ó&   K  — | ]	  \  }}|–— Œ y ­wr^   r*   r*  s      r-   rb   z.WordExtractor.extract_words.<locals>.<genexpr>´  s   è ø€ ÒUÑ!1  zœÑUùó   ‚)rh   r%  )rU   rx   rt   s      r-   Úextract_wordszWordExtractor.extract_words«  sJ   € ñ Üñ à(,×(@Ñ(@ÀÓ(Gôó ð ô
 ÑU°T×5MÑ5MÈeÓ5TÔUÓUÐUr/   ©F)r–   r—   r˜   ÚDEFAULT_X_TOLERANCErá   r   r   r   r   r›   Úfloatr…   r   r
   r   rš   rV   rô   r   r   rü   r  r   r   r  r   r  r%  r�   r'  r-  r*   r/   r-   rã   rã   §  s=  „ ð 1Ø0Ø59Ø59Ø!&Ø#Ø!Ø#Ø*Ø*Ø,0Ø,0Ø+/Ø16Ø!%ñ!4@àð4@ð ð4@ð !  e¨TÐ!1Ñ2ð	4@ð
 !  e¨TÐ!1Ñ2ð4@ð ð4@ð ð4@ð ð4@ð ð4@ð ð4@ð ð4@ð # 5™/ð4@ð # 5™/ð4@ð ˜d 3™iÑ(ð4@ð $ D¨# IÑ.ð4@ð  ó!4@ðl
C Cð 
C¨Eó 
Cð¨ð ¸ó ð4K
àðK
ð ðK
ð ð	K
ð
 ðK
ð ðK
ð 
óK
ðZ.à!ð.ð ð.ð 
�:˜t TÐ)Ñ	*ó	.ð`+Øð+à	�5˜ UÐ*Ñ+¨T°4Ð7Ñ	8ó+ð.EØðEà	�5˜ 
Ð*Ñ+¨T°4Ð7Ñ	8óEð > Zð >°Gó >ð 7<ñ	VØð	VØ/3ð	Và	ô	Vr/   rã   rx   rt   Úkwargsc                 ó8   — t        di |¤Žj                  | |«      S )Nr*   )rã   r-  )rx   rt   r1  s      r-   r-  r-  ·  s   € ô Ñ"˜6Ñ"×0Ñ0°¸ÓEÐEr/   c           
      óB  — |j                  d|j                  d«      xs t        | «      dœ«       t        di t        D �ci c]  }||v sŒ|||   “Œ c}¤Ž}|j                  | «      } |j                  di t        D �ci c]  }||v sŒ|||   “Œ c}¤Ž}|S c c}w c c}w )NTr¤   )r­   r¤   r*   )ÚupdaterÃ   r   rã   ÚWORD_EXTRACTOR_KWARGSr'  rÞ   ÚTEXTMAP_KWARGS)rx   r1  ÚkÚ	extractorÚwordmapÚtextmaps         r-   Úchars_to_textmapr;  Á  s±   € Ø
‡M�MàØ!Ÿ:™: mÓ4ÒN¼ÈÓ8Nñ	
ôô ñ Ü!6Ö
F˜A¸!¸vº+ˆ1ˆf�Q‰i‰<Ò
Fñ€Ið ×'Ñ'¨Ó.€GØ ˆg× Ñ ñ Ü!/Ö
?˜A°1¸²;ˆ1ˆf�Q‰i‰<Ò
?ñ€Gð €Nùò Gùò @s   Á 	BÁ
BÁ>	BÂBrO   rP   c           
      ó|  — t        | «      } t        | «      dk(  ry|j                  d«      ri |¥||dœ¥}t        | fi |¤Žj                  S t        d
i t        D �ci c]  }||v sŒ|||   “Œ c}¤Ž}|j                  | «      }|xs |j                  }|xs |j                  }t        |j                  «      }|j                  dt        «      }	|j                  dt        «      }
t        |||dv r|
n|	«      }t        dj                  d	„ |D «       «      D �cg c]  }|d f‘Œ c}||¬«      j                  S c c}w c c}w )Nr   rX   rŸ   r°   rä   r©   r  rY   c              3   óL   K  — | ]  }d j                  d„ |D «       «      –— Œ y­w)r[   c              3   ó&   K  — | ]	  }|d    –— Œ y­w)rv   Nr*   )r_   rÖ   s     r-   rb   z)extract_text.<locals>.<genexpr>.<genexpr>û  s   è ø€ Ò&E¸ t¨F¥|Ñ&Eùr,  Nrc   )r_   r`   s     r-   rb   zextract_text.<locals>.<genexpr>û  s   è ø€ ÒXÈ$˜cŸh™hÑ&EÀÔ&E×EÑXùs   ‚"$r*   )r   rk   rÃ   r;  rT   rã   r5  r-  r%   r;   r:   r/  rá   r   rM   rd   )rx   rO   rP   r1  Útextmap_kwargsr7  r8  Úwordsr´   rä   r©   re   r  s                r-   Úextract_textrA  Ó  s\  € ô �E‹N€EÜ
ˆ5ƒz�Q‚Øà‡z�z�(Ôð
Øð
à"1ÀoÑVð
ˆô   Ñ8¨Ñ8×BÑBÐBä!ñ 
Ü%:ÖJ ¸aÀ6ºkˆq�&˜‘)‰|ÒJñ
ˆ	ð ×'Ñ'¨Ó.ˆà)Ò?¨Y×-?Ñ-?ˆØ)Ò?¨Y×-?Ñ-?ˆä/°	×0BÑ0BÓCÐà—j‘j Ô0CÓDˆØ—j‘j Ô0CÓDˆäØØØ*¨nÑ<‰KÀ+ó
ˆô ð —I‘IÑXÐRWÔXÓXöàð �t’òð ,Ø+ô	
÷ ‰)ð		ùò% Kùò&s   Á	D4Á$D4ÄD9r#  Ú	tolerancec                 ó‚   — d}d }t        | t        d«      ¬«      D ]!  }|�|d   ||z   kD  r|dz  }|d   }||d   z  }Œ# |S )NrX   r4   rµ   r[   r6   rv   )r¿   r   )r#  rB  ÚcollÚlast_x1r  s        r-   Úcollate_linerF    sf   € ð €DØ€GÜ�z¤z°$Ó'7Ô8ò ˆØÐ d¨4¡j°G¸iÑ4GÒ&HØ�C‰KˆDØ�t‘*ˆØ��V‘Ñ‰ð	ð
 €Kr/   rä   r©   c                 ód   ‡— t        | t        d«      |«      }dj                  ˆfd„|D «       «      S )Nr÷   rY   c              3   ó6   •K  — | ]  }t        |‰«      –— Œ y ­wr^   )rF  )r_   r}   rä   s     €r-   rb   z&extract_text_simple.<locals>.<genexpr>  s   øè ø€ ÒE°a”\ ! [×1ÑEùs   ƒ)r   r   rd   )rx   rä   r©   Ú	clustereds    `  r-   Úextract_text_simplerJ    s-   ø€ ô
   ¤z°(Ó';¸[ÓI€IØ�9‰9ÓE¸9ÔEÓEÐEr/   rê   .c                 óÌ   ‡‡‡— t        g d¢|xs
 t        «       ¢­Ž Št        dd«      Šdt        dt        t        ddf   fˆˆˆfd„} || «      }t        || j                  ¬«      S )	uç   
    Removes duplicate chars â€”Â those sharing the same text and positioning
    (within `tolerance`) as other characters in the set. Use extra_args to
    be more restrictive with the properties shared by the matching chars.
    )rò   rv   r÷   r4   rx   r&   Nc              3   ó  •K  — t        | ‰¬«      }t        j                  |‰¬«      D ]V  \  }}t        t	        |«      t        d«      ‰«      D ]/  }t        |t        d«      ‰«      D ]  }t        |‰¬«      d   –— Œ Œ1 ŒX y ­w)Nrµ   r÷   r4   r   )r¿   r  r  r   rh   r   )	rx   Úsorted_charsÚgrpÚ	grp_charsÚ	y_clusterÚ	x_clusterr¶   Úpos_keyrB  s	         €€€r-   Úyield_unique_charsz(dedupe_chars.<locals>.yield_unique_chars'  s�   øè ø€ Ü˜e¨Ô-ˆÜ'×/Ñ/°À#ÔFò 	<‰NˆC�Ü,Ü�Y“¤¨HÓ!5°yóò <�	ô "1Øœz¨$Ó/°ó"ò <�Iô ! °Ô8¸Ñ;Ó;ñ<ñ<ñ	<ùs   ƒA?Brµ   )r   Útupler   r   r   r¿   Úindex)rx   rB  rê   rS  Údedupedr¶   rR  s    `   @@r-   Údedupe_charsrW    sg   ú€ ô Ð
EÐ)Ð
E¨[Ò-C¼E»GÒ
E€CÜ˜ 4Ó(€Gð	<¤*ð 	<´¼5À$ÈÐ;LÑ1M÷ 	<ñ ! Ó'€GÜ�'˜uŸ{™{Ô+Ð+r/   )rX   r.  )NN)r   )Úfontnamer  )@Úinspectr  Úloggingrˆ   rð   Úoperatorr   Útypingr   r   r   r   r   r	   r
   r   r   r   Ú_typingr   r   r   r   r   r   Ú
clusteringr   Úgenericr   Úgeometryr   Ú	getLoggerr–   rî   r/  rá   rß   rà   r   Ú__annotations__r   r¼   r:   rB   r¾   rG   rš   rK   rM   r�   rã   r…   r-  Ú	signaturerÞ   Ú
parametersrH   r6  r5  r;  rA  rF  rJ  rW  r*   r/   r-   ú<module>re     så  ðÜ Û Û Û 	Û Ý ÷÷ ÷ ÷ J× IÝ 'Ý Ý %à	ˆ×	Ñ	˜8Ó	$€àÐ ØÐ ØÐ ØÐ ØÐ �%Ó ØÐ �%Ó ð ØØØØØØñ€	ð 5ð ¨X°u°g¸u°nÑ-Eó ð ð ¨(°E°7¸EÀ%ÈÀ,Ñ<OÐ3OÑ*Pó ñ �a‹=Ù�a‹=Ù�a‹=Ù�a‹=ñ	Ð ñ �eÓÙ�hÓÙ�dÓÙ�dÓñ	€ñ
 %ð 
°5ð 
À#ð 
Ètó 
÷"G
ñ G
÷T{
ñ {
÷|MVñ MVðb -2ñFØðFØ%)ðFØ=@ðFàóFð #�×"Ñ" 7×#5Ñ#5Ó6×AÑA×FÑFÓH€Ø)˜×)Ñ)¨-Ó8×CÑC×HÑHÓJÐ ð˜Jð °#ð ¸'ó ð( (,Ø'+ñ-Øð-à˜e‘_ð-ð ˜e‘_ð-ð ð	-ð
 	ó-ðd +ñØðàðð 	óð  -Ø,ñFØðFàðFð ðFð 	ó	Fð Ø-Añ,Øð,àð,ð ˜%  S ™/Ñ*ð,ð ô	,r/   