o
    jd                     @   s  d dl mZ d dlmZ d dlm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 ddlmZmZ dd	lmZ e	rXdd
lmZm Z m!Z! G dd deZ"eee" ee"ee#e$f f ee"e#e#f f Z%e G dd deZ&G dd dZ'G dd dZ(e)dkrd dl*mZ d dl+m,Z, d dl-m.Z. dZ/e.0dZ1e Ze2d e3d e3d e3e,e/ddd e3  e3d e4e5e1Z6e3e6 e3  e3d  e3e1 e3d! d"S d"S )#    )IntEnum)	lru_cache)filterfalse)
attrgetter)
TYPE_CHECKINGDictIterableList
NamedTupleOptionalSequenceTupleTypeUnion   )_is_single_cell_widthscached_cell_lencell_lenget_character_cell_sizeset_cell_size)Result	rich_repr)Style)ConsoleConsoleOptionsRenderResultc                   @   sP   e Zd ZdZdZdZdZdZdZdZ	dZ
d	Zd
ZdZdZdZdZdZdZdZdS )ControlTypezDNon-printable control codes which typically translate to ANSI codes.r                        	   
                     N)__name__
__module____qualname____doc__BELLCARRIAGE_RETURNHOMECLEARSHOW_CURSORHIDE_CURSORENABLE_ALT_SCREENDISABLE_ALT_SCREEN	CURSOR_UPCURSOR_DOWNCURSOR_FORWARDCURSOR_BACKWARDCURSOR_MOVE_TO_COLUMNCURSOR_MOVE_TOERASE_IN_LINESET_WINDOW_TITLE r@   r@   R/var/www/html/fyndo/pharma/fyndo/venv/lib/python3.10/site-packages/rich/segment.pyr       s$    r   c                   @   s  e Zd ZU dZeed< dZee ed< dZ	ee
e  ed< edefddZdefd	d
ZdefddZedefddZeeddd deded fddZdeded fddZedJddZe		dKded  dee dee ded  fddZe	dLded  deded  fdd Zeded  deed   fd!d"Zeded  deeed  ef  fd#d$Ze		%	%dMded  d&edee d'ed(edeed   fd)d*Z e		%dNd+ed  d&edee d'eded  f
d,d-Z!ed+ed  defd.d/Z"ed0eed   deeef fd1d2Z#e			dOd0eed   d3ed4ee dee d5edeed   fd6d7Z$e	dLd8e%d  d0eed   d3ed4eded5edeed   fd9d:Z&e	dLd8e%d  d0eed   d3ed4eded5edeed   fd;d<Z'e	dLd8e%d  d0eed   d3ed4eded5edeed   fd=d>Z(eded  ded  fd?d@Z)eded  ded  fdAdBZ*eded  ded  fdCdDZ+eded  ded  fdEdFZ,eded  dGee deed   fdHdIZ-dS )PSegmenta  A piece of text with associated style. Segments are produced by the Console render process and
    are ultimately converted in to strings to be written to the terminal.

    Args:
        text (str): A piece of text.
        style (:class:`~rich.style.Style`, optional): An optional style to apply to the text.
        control (Tuple[ControlCode], optional): Optional sequence of control codes.

    Attributes:
        cell_length (int): The cell length of this Segment.
    textNstylecontrolreturnc                 C   s   | \}}}|r	dS t |S )zzThe number of terminal cells required to display self.text.

        Returns:
            int: A number of cells.
        r   )r   )selfrC   _stylerE   r@   r@   rA   cell_lengthN   s   
zSegment.cell_lengthc                 c   sB    | j V  | jd u r| jd ur| jV  d S d S | jV  | jV  d S N)rC   rE   rD   rG   r@   r@   rA   __rich_repr__X   s   

zSegment.__rich_repr__c                 C   s
   t | jS )z#Check if the segment contains text.)boolrC   rK   r@   r@   rA   __bool__a   s   
zSegment.__bool__c                 C   s
   | j duS )z,Check if the segment contains control codes.N)rE   rK   r@   r@   rA   
is_controle   s   
zSegment.is_controli @  segmentcut)rB   rB   c                 C   s>  |\}}}t }|j}||kr||d||fS t}t|| t| }		 |d|	 }
t|
}|| }|sC||
|||||	d ||fS |dkri|||	 dkri||d|	 d |||d||	d d  ||fS |dkr|||	d  dkr||d|	d  d |||d||	d  ||fS ||k r|	d7 }	n|	d8 }	q#)a\  Split a segment in to two at a given cell position.

        Note that splitting a double-width character, may result in that character turning
        into two spaces.

        Args:
            segment (Segment): A segment to split.
            cut (int): A cell position to cut on.

        Returns:
            A tuple of two segments.
         TNr    r   )rB   rI   r   intlenr   )clsrP   rQ   rC   rD   rE   _SegmentrI   	cell_sizeposbeforecell_posout_byr@   r@   rA   _split_cellsj   s6   


zSegment._split_cellsc                 C   sn   | \}}}|dksJ t |r1|t|kr| td||fS t|d| ||t||d ||fS | | |S )ax  Split segment in to two segments at the specified column.

        If the cut point falls in the middle of a 2-cell wide character then it is replaced
        by two spaces, to preserve the display width of the parent segment.

        Args:
            cut (int): Offset within the segment to cut.

        Returns:
            Tuple[Segment, Segment]: Two segments.
        r   rR   N)r   rV   rB   r^   )rG   rQ   rC   rD   rE   r@   r@   rA   split_cells   s   
zSegment.split_cellsc                 C   s   | dS )zMake a new line segment.
r@   )rW   r@   r@   rA   line   s   zSegment.linesegments
post_stylec                    s>   |}|r|j   fdd|D }rfdd|D }|S )a  Apply style(s) to an iterable of segments.

        Returns an iterable of segments where the style is replaced by ``style + segment.style + post_style``.

        Args:
            segments (Iterable[Segment]): Segments to process.
            style (Style, optional): Base style. Defaults to None.
            post_style (Style, optional): Style to apply on top of segment style. Defaults to None.

        Returns:
            Iterable[Segments]: A new iterable of segments (possibly the same iterable).
        c                 3   s.    | ]\}}}||rd n ||V  qd S rJ   r@   .0rC   rH   rE   )applyrW   r@   rA   	<genexpr>   s
    
z&Segment.apply_style.<locals>.<genexpr>c                 3   s6    | ]\}}} ||rd n|r| n|V  qd S rJ   r@   rd   )rW   rc   r@   rA   rg      s    

)__add__)rW   rb   rD   rc   result_segmentsr@   )rf   rW   rc   rA   apply_style   s   
zSegment.apply_styleFrO   c                 C   s    |r	t td|S ttd|S )a2  Filter segments by ``is_control`` attribute.

        Args:
            segments (Iterable[Segment]): An iterable of Segment instances.
            is_control (bool, optional): is_control flag to match in search.

        Returns:
            Iterable[Segment]: And iterable of Segment instances.

        rE   )filterr   r   )rW   rb   rO   r@   r@   rA   filter_control   s   zSegment.filter_controlc           
      c   s    g }|j }|D ]3}d|jv r7|js7|\}}}|r6|d\}}	}|r*|| || |	r4|V  g }|j }|sq|| q|rC|V  dS dS )a   Split a sequence of segments in to a list of lines.

        Args:
            segments (Iterable[Segment]): Segments potentially containing line feeds.

        Yields:
            Iterable[List[Segment]]: Iterable of segment lists, one per line.
        r`   NappendrC   rE   	partition
rW   rb   ra   rn   rP   rC   rD   __textnew_liner@   r@   rA   split_lines   s(   


	
zSegment.split_linesc           
      c   s    g }|j }|D ]5}d|jv r9|js9|\}}}|r8|d\}}	}|r*|| || |	r6|dfV  g }|j }|sq|| q|rG|dfV  dS dS )a2  Split a sequence of segments in to a list of lines and a boolean to indicate if there was a new line.

        Args:
            segments (Iterable[Segment]): Segments potentially containing line feeds.

        Yields:
            Iterable[List[Segment]]: Iterable of segment lists, one per line.
        r`   TFNrm   rp   r@   r@   rA   split_lines_terminator  s(   


	zSegment.split_lines_terminatorTlengthpadinclude_new_linesc                 c   s    g }|j }| j}| d}	|D ]A}
d|
jv rL|
jsL|
\}}}|rK|d\}}}|r1|| || |rI|||||d}|rB| |	 |V  |  |s q||
 q|r^|||||dV  dS dS )a  Split segments in to lines, and crop lines greater than a given length.

        Args:
            segments (Iterable[Segment]): An iterable of segments, probably
                generated from console.render.
            length (int): Desired line length.
            style (Style, optional): Style to use for any padding.
            pad (bool): Enable padding of lines that are less than `length`.

        Returns:
            Iterable[List[Segment]]: An iterable of lines of segments.
        r`   )rD   rw   N)rn   adjust_line_lengthrC   rE   ro   clear)rW   rb   rv   rD   rw   rx   ra   rn   ry   new_line_segmentrP   rC   segment_stylerq   rr   rs   cropped_liner@   r@   rA   split_and_crop_lines2  s4   


zSegment.split_and_crop_linesra   c                 C   s   t dd |D }||k r%|r|| d||  |g }|S |dd }|S ||krag }|j}d}|D ],}|j}	||	 |k s@|jrI|| ||	7 }q2|\}
}}t|
|| }
|| |
|  |S |S |dd }|S )a  Adjust a line to a given width (cropping or padding as required).

        Args:
            segments (Iterable[Segment]): A list of segments in a single line.
            length (int): The desired width of the line.
            style (Style, optional): The style of padding if used (space on the end). Defaults to None.
            pad (bool, optional): Pad lines with spaces if they are shorter than `length`. Defaults to True.

        Returns:
            List[Segment]: A line of segments with the desired length.
        c                 s   s    | ]}|j V  qd S rJ   )rI   )re   rP   r@   r@   rA   rg   t  s    z-Segment.adjust_line_length.<locals>.<genexpr>rT   Nr   )sumrn   rI   rE   r   )rW   ra   rv   rD   rw   line_lengthrs   rn   rP   segment_lengthrC   r|   rq   r@   r@   rA   ry   a  s.   

zSegment.adjust_line_lengthc                    s   t  t fdd|D S )zGet the length of list of segments.

        Args:
            line (List[Segment]): A line encoded as a list of Segments (assumes no '\\n' characters),

        Returns:
            int: The length of the line.
        c                 3   s"    | ]\}}}|s |V  qd S rJ   r@   )re   rC   rD   rE   	_cell_lenr@   rA   rg     s     z*Segment.get_line_length.<locals>.<genexpr>)r   r   )rW   ra   r@   r   rA   get_line_length  s   
zSegment.get_line_lengthlinesc                    s0   | j  |rt fdd|D nd}|t|fS )zGet the shape (enclosing rectangle) of a list of lines.

        Args:
            lines (List[List[Segment]]): A list of lines (no '\\n' characters).

        Returns:
            Tuple[int, int]: Width and height in characters.
        c                 3   s    | ]} |V  qd S rJ   r@   re   ra   r   r@   rA   rg     s    z$Segment.get_shape.<locals>.<genexpr>r   )r   maxrV   )rW   r   	max_widthr@   r   rA   	get_shape  s   
zSegment.get_shapewidthheight	new_linesc           	         s   |pt |}|r| d d gn| d g}| j |d| } fdd|D |dd< t ||k rD||g|t |   |S )a  Set the shape of a list of lines (enclosing rectangle).

        Args:
            lines (List[List[Segment]]): A list of lines.
            width (int): Desired width.
            height (int, optional): Desired height or None for no change.
            style (Style, optional): Style of any padding added.
            new_lines (bool, optional): Padded lines should include "
". Defaults to False.

        Returns:
            List[List[Segment]]: New list of lines.
        rT   r`   Nc                    s   g | ]	} |d qS ))rD   r@   r   ry   rD   r   r@   rA   
<listcomp>  s    z%Segment.set_shape.<locals>.<listcomp>)rV   ry   extend)	rW   r   r   r   rD   r   _heightblankshaped_linesr@   r   rA   	set_shape  s   &zSegment.set_shaperW   c                 C   s`   |t | }|s|dd S |d| }|r| d| d |n| d| |}||gg|  }|S )a  Aligns lines to top (adds extra lines to bottom as required).

        Args:
            lines (List[List[Segment]]): A list of lines.
            width (int): Desired width.
            height (int, optional): Desired height or None for no change.
            style (Style): Style of any padding added.
            new_lines (bool, optional): Padded lines should include "
". Defaults to False.

        Returns:
            List[List[Segment]]: New list of lines.
        NrT   r`   rV   rW   r   r   r   rD   r   extra_linesr   r@   r@   rA   	align_top     $zSegment.align_topc                 C   s`   |t | }|s|dd S |d| }|r| d| d |n| d| |}|gg| | }|S )a  Aligns render to bottom (adds extra lines above as required).

        Args:
            lines (List[List[Segment]]): A list of lines.
            width (int): Desired width.
            height (int, optional): Desired height or None for no change.
            style (Style): Style of any padding added. Defaults to None.
            new_lines (bool, optional): Padded lines should include "
". Defaults to False.

        Returns:
            List[List[Segment]]: New list of lines.
        NrT   r`   r   r   r@   r@   rA   align_bottom  r   zSegment.align_bottomc           
      C   s|   |t | }|s|dd S |d| }|r| d| d |n| d| |}|d }|| }	|gg| | |gg|	  }|S )a  Aligns lines to middle (adds extra lines to above and below as required).

        Args:
            lines (List[List[Segment]]): A list of lines.
            width (int): Desired width.
            height (int, optional): Desired height or None for no change.
            style (Style): Style of any padding added.
            new_lines (bool, optional): Padded lines should include "
". Defaults to False.

        Returns:
            List[List[Segment]]: New list of lines.
        NrT   r`   r   r   )
rW   r   r   r   rD   r   r   r   	top_linesbottom_linesr@   r@   rA   align_middle  s   $zSegment.align_middlec                 c   sv    t |}zt|}W n
 ty   Y dS w t}|D ]}|j|jkr0|js0||j|j |j}q|V  |}q|V  dS )a)  Simplify an iterable of segments by combining contiguous segments with the same style.

        Args:
            segments (Iterable[Segment]): An iterable of segments.

        Returns:
            Iterable[Segment]: A possibly smaller iterable of segments that will render the same way.
        N)iternextStopIterationrB   rD   rE   rC   )rW   rb   iter_segmentslast_segmentrX   rP   r@   r@   rA   simplify&  s    

zSegment.simplifyc                 c   sL    |D ] }|j s|jdu r|V  q|\}}}| ||r|dndV  qdS )zRemove all links from an iterable of styles.

        Args:
            segments (Iterable[Segment]): An iterable segments.

        Yields:
            Segment: Segments with link removed.
        N)rE   rD   update_link)rW   rb   rP   rC   rD   _controlr@   r@   rA   strip_linksA  s   

zSegment.strip_linksc                 c   s$    |D ]\}}}| |d|V  qdS )zRemove all styles from an iterable of segments.

        Args:
            segments (Iterable[Segment]): An iterable segments.

        Yields:
            Segment: Segments with styles replace with None
        Nr@   )rW   rb   rC   rH   rE   r@   r@   rA   strip_stylesR  s   
zSegment.strip_stylesc                 c   s\    i }|D ]&\}}}|r$| |}|du r|j}|||< | |||V  q| |d|V  qdS )zRemove all color from an iterable of segments.

        Args:
            segments (Iterable[Segment]): An iterable segments.

        Yields:
            Segment: Segments with colorless style.
        N)getwithout_color)rW   rb   cacherC   rD   rE   colorless_styler@   r@   rA   remove_color_  s   
zSegment.remove_colorcutsc                 c   sF   g }|j }t|}	 t|d}|dkrdS |dkrng V  qd}|j}|j}	t}
|D ]q}|\}}}|r|r8|n||
| }||k rI|| |}nS||krm|| |	 V  |  |}t|d}|dkrl|ri|	 V   dS n/||| \}}|\}}}|| |	 V  |  |}t|d}|dkr|r|	 V   dS |s4q+|	 V  dS )zDivides an iterable of segments in to portions.

        Args:
            cuts (Iterable[int]): Cell positions where to divide.

        Yields:
            [Iterable[List[Segment]]]: An iterable of Segments in List.
        TrS   Nr   )rn   r   r   rz   copyr   r_   )rW   rb   r   split_segmentsadd_segment	iter_cutsrQ   rZ   segments_clearsegments_copyr   rP   rC   rH   rE   end_posr[   r@   r@   rA   divideu  sb   




#zSegment.divide)rF   rB   )NNF)NTT)NT)NNF).r,   r-   r.   r/   str__annotations__rD   r   r   rE   r   ControlCodepropertyrU   rI   r   rL   rM   rN   rO   classmethodr   r   r^   r_   ra   r   rj   rl   r	   rt   ru   r~   ry   r   r   r   r   r   r   r   r   r   r   r   r   r@   r@   r@   rA   rB   <   sJ  
 		/( 
.,$

#






rB   c                   @   sB   e Zd ZdZddee deddfddZ			
				dddZdS )Segmentsa=  A simple renderable to render an iterable of segments. This class may be useful if
    you want to print segments outside of a __rich_console__ method.

    Args:
        segments (Iterable[Segment]): An iterable of segments.
        new_lines (bool, optional): Add new lines between segments. Defaults to False.
    Frb   r   rF   Nc                 C   s   t || _|| _d S rJ   )listrb   r   )rG   rb   r   r@   r@   rA   __init__  s   

zSegments.__init__consoler   optionsr   r   c                 c   s<    | j rt }| jD ]}|V  |V  qd S | jE d H  d S rJ   )r   rB   ra   rb   )rG   r   r   ra   rP   r@   r@   rA   __rich_console__  s   
zSegments.__rich_console__r   r   r   r   r   rF   r   )	r,   r-   r.   r/   r   rB   rM   r   r   r@   r@   r@   rA   r     s    r   c                   @   sB   e Zd Zddeee  deddfddZ				
			dddZdS )SegmentLinesFr   r   rF   Nc                 C   s   t || _|| _dS )a=  A simple renderable containing a number of lines of segments. May be used as an intermediate
        in rendering process.

        Args:
            lines (Iterable[List[Segment]]): Lists of segments forming lines.
            new_lines (bool, optional): Insert new lines after each line. Defaults to False.
        N)r   r   r   )rG   r   r   r@   r@   rA   r     s   

zSegmentLines.__init__r   r   r   r   r   c                 c   sJ    | j rt }| jD ]
}|E d H  |V  qd S | jD ]}|E d H  qd S rJ   )r   rB   ra   r   )rG   r   r   rs   ra   r@   r@   rA   r     s   


zSegmentLines.__rich_console__r   r   )	r,   r-   r.   r   r	   rB   rM   r   r   r@   r@   r@   rA   r     s     r   __main__)r   )Syntax)Textzfrom rich.console import Console
console = Console()
text = Text.from_markup("Hello, [bold magenta]World[/]!")
console.print(text)zHello, [bold magenta]World[/]!zrich.Segmentz]A Segment is the last step in the Rich render process before generating text with ANSI codes.z
Consider the following code:
pythonT)line_numberszRWhen you call [b]print()[/b], Rich [i]renders[/i] the object in to the following:
zAThe Segments are then processed to produce the following output:
zS
You will only need to know this if you are implementing your own Rich renderables.N)7enumr   	functoolsr   	itertoolsr   operatorr   typingr   r   r   r	   r
   r   r   r   r   r   cellsr   r   r   r   r   reprr   r   rD   r   r   r   r   r   r   rU   r   r   rB   r   r   r,   rich.consolerich.syntaxr   	rich.textr   codefrom_markuprC   ruleprintr   render	fragmentsr@   r@   r@   rA   <module>   sh    0     





