
    Cjj                       S SK Jr  S SKrS SKJr  S SKJr  S SKJr  S SK	J
r
Jr  S SKJrJrJrJrJr  S SKrS SKJrJrJrJr  S S	KJr  S S
KJr  S SKJr  S SKJ r   S SK!J"r"  S SK#J$r$  S SK%J&r&  S SK'J(r(  S SK)J*r*  S SK+J,r,J-r-  S SK.J/r/J0r0  S SK1J2r2  S SK3J4r4J5r5J6r6  S SK7J8r8  S SK9J:r:  S SK;J<r<  S SK=J>r>  \-" 5       r? " S S\$5      r@ " S S5      rA " S S\5      rB\R                  R                  S S!9 " S" S#5      5       rEg)$    )annotationsN)defaultdict)chain)
itemgetter)PathPurePath)FinalIterable
NamedTupleSequencecast)ConsoleConsoleOptionsRenderableTypeRenderResult)render)Padding)Panel)Text)LRUCache)StylesheetError)_check_selectors)RuleSet)parse)RulesMapStyles)Tokentokenize_values)
TokenError)CSSLocationSpecificity3Specificity6)DOMNode)parse_style)Style)Widgetc                  ,    \ rS rSrSrSS jrSS jrSrg)	StylesheetParseError"   z/Raised when the stylesheet could not be parsed.c                    Xl         g Nerrors)selfr-   s     h/home/rurouni/.local/share/pipx/venvs/strix-agent/lib/python3.13/site-packages/textual/css/stylesheet.py__init__StylesheetParseError.__init__%   s        c                    U R                   $ r+   r,   r.   s    r/   __rich__StylesheetParseError.__rich__(   s    {{r2   r,   N)r-   StylesheetErrorsreturnNone)r8   r   )__name__
__module____qualname____firstlineno____doc__r0   r5   __static_attributes__ r2   r/   r(   r(   "   s    9r2   r(   c                  L    \ rS rSrSrSS jr\S	S j5       r      S
S jrSr	g)r7   ,   z#A renderable for stylesheet errors.c                    Xl         0 U l        g r+   rules	variables)r.   rE   s     r/   r0   StylesheetErrors.__init__/   s    
)+r2   c                P    SSK Jn  U" USSSS[        SUS-
  5      US-   4U1S9nU$ )Nr   )Syntaxscss
ansi_lightT   )lexerthemeline_numbersindent_guides
line_rangehighlight_lines)rich.syntaxrI   max)clscodeline_norI   syntaxs        r/   _get_snippetStylesheetErrors._get_snippet3   sA    &Aw{+Wq[9$I
 r2   c              #  p  #    Sn[        [        R                  [        R                  " S U R
                   5       5      5      5      nU GHF  u  pVUS-  nUR                  (       a  UR                  R                  u  pxOUR                  u  pxUS-   US-   pUR                  u  pU(       a8  [        [        U5      R                  5       5      n[        U5      R                  nOSnSnU(       a  U=(       d    UnSU SU	 SU
 3nOU=(       d    U SU	 SU
 3nSn[        R                  " SUUS	S
9nSv   [        U R!                  UR                  (       a  UR                  R"                  OUR"                  U	5      USSS9v   [%        USS9v   GMI     Sv   ['        SU SUS:w  a  SOS S35      v   g 7f)Nr   c              3  8   #    U  H  oR                   v   M     g 7fr+   r,   ).0_rules     r/   	<genexpr>4StylesheetErrors.__rich_console__.<locals>.<genexpr>G   s     -S
ull
       z	<unknown>z in :z	Error at zbold red)styleleftred)titletitle_alignborder_style)r   r   rb      )padz  [b][red]CSS parsing failed:[/] z errorsz[/] found in stylesheet)listdictfromkeysr   from_iterablerE   referenced_bylocation	read_fromstrr   absolutenamer   assembler   rY   rV   r   r   )r.   consoleoptionserror_countr-   tokenmessageline_idxcol_idxrW   col_nodisplay_path
widget_var	link_pathfilenamepath_stringwidget_stringrh   s                     r/   __rich_console__!StylesheetErrors.__rich_console__B   s     MM%---S

-SST
 %NE1K""$)$7$7$@$@!'$)NN!&lGaKV',$L\ 2 ; ; =>		?//	& '38"&zl!G9AfX F!*!6h 7q	6(K "MM[-zE H!!050C0CE'',, ""  '|44S %V .{m6XYIY#_aAbbyz
 	
s   F4F6rD   N)rE   list[RuleSet]r8   r9   )rV   ru   rW   intr8   r   )ry   r   rz   r   r8   r   )
r:   r;   r<   r=   r>   r0   classmethodrY   r   r?   r@   r2   r/   r7   r7   ,   s;    -,  6
6
)76
	6
r2   r7   c                  J    \ rS rSr% SrS\S'   S\S'   SrS\S	'   S
rS\S'   Srg)	CssSource{   ay  Contains the CSS content and whether or not the CSS comes from user defined stylesheets
vs widget-level stylesheets.

Args:
    content: The CSS as a string.
    is_defaults: True if the CSS is default (i.e. that defined at the widget level).
        False if it's user CSS (which will override the defaults).
    tie_breaker: Specificity tie breaker.
    scope: Scope of CSS.
ru   contentboolis_defaultsr   r   tie_breakerrc   scoper@   N)	r:   r;   r<   r=   r>   __annotations__r   r   r?   r@   r2   r/   r   r   {   s'    	 LKE3Or2   r   T)angularc                     \ rS rSr% SrSS.S!S jjrS"S jr\S#S j5       r\S$S j5       r	\S%S	 j5       r
\S&S
 j5       rS'S jrS(S jrS)S jr   S*           S+S jjrS,S jrS-S jrS.S/S jjr    S0           S1S jjrS2S jrS2S jr\      S3S j5       r1 SkrS\S'   SSS.       S4S jjrS5S jr\ S6       S7S jj5       rS6S8S jjrS6S9S jjrS rg):
Stylesheet   z(A Stylesheet generated from Textual CSS.NrF   c                   / U l         S U l        U=(       d    0 U l        S U l        0 U l        SU l        [        5       U l        [        S5      U l	        [        S5      U l
        g )NF@   i   )_rules
_rules_map
_variables_Stylesheet__variable_tokenssource_require_parseset_invalid_cssr   _parse_cache_style_parse_cacher.   rF   s     r/   r0   Stylesheet.__init__   sU    %';?#/r@D46#&)e<DRL8@8Jr2   c              #  V   #    [        U R                  R                  5       5      v   g 7fr+   )rn   r   keysr4   s    r/   __rich_repr__Stylesheet.__rich_repr__   s     4;;##%&&s   ')c                h    U R                   c  [        U R                  5      U l         U R                   $ r+   )r   r   r   r4   s    r/   _variable_tokensStylesheet._variable_tokens   s+    !!)%4T__%ED"%%%r2   c                    U R                   (       a  U R                  5         SU l         U R                  c   eU R                  $ )zIList of rule sets.

Returns:
    List of rules sets for this stylesheet.
F)r   r   r   r4   s    r/   rE   Stylesheet.rules   s8     JJL"'D{{&&&{{r2   c                    U R                   cX  [        [        5      nU R                   H)  nUR                   H  nX   R                  U5        M     M+     [        U5      U l         U R                   $ )zfStructure that maps a selector on to a list of rules.

Returns:
    Mapping of selector to rule sets.
)r   r   rn   rE   selector_namesappendro   )r.   	rules_maprulerw   s       r/   r   Stylesheet.rules_map   s]     ??"2=d2CI

 //DO**40 0 # #9oDOr2   c                F    SR                  S U R                   5       5      $ )zThe equivalent TCSS for this stylesheet.

Note that this may not produce the same content as the file(s) used to generate the stylesheet.
z

c              3  8   #    U  H  oR                   v   M     g 7fr+   )css)r]   rule_sets     r/   r_   !Stylesheet.css.<locals>.<genexpr>   s     C
H<<
ra   )joinrE   r4   s    r/   r   Stylesheet.css   s     {{C

CCCr2   c                    [        U R                  R                  5       S9nU R                  R                  5       Ul        U$ )z@Create a copy of this stylesheet.

Returns:
    New stylesheet.
r   )r   r   copyr   )r.   
stylesheets     r/   r   Stylesheet.copy   s6      $//*>*>*@A
 KK,,.
r2   c                    Xl         SU l        [        5       U l        U R                  R                  5         U R                  R                  5         g)zHSet CSS variables.

Args:
    variables: A mapping of name to variable.
N)r   r   r   r   r   clearr   r   s     r/   set_variablesStylesheet.set_variables   s?     $!%E!%%'r2   c                    [        U[        5      (       a  U$ XR                  ;   a  U R                  U   $ [        U5      nX R                  U'   U$ )zParse a (visual) Style.

Args:
    style_text: Visual style, such as "bold white 90% on $primary"

Returns:
    New Style instance.
)
isinstancer%   r   r$   )r.   
style_textre   s      r/   r$   Stylesheet.parse_style   sQ     j%((000**:66J'.3
+r2   Fc                   XX4U4n U R                   U   $ ! [         a     Of = f [        [        UUUU R                  UUS95      nO+! [
         a    e [         a  n[        SU 35      SeSnAff = fXpR                   U'   U$ )a  Parse CSS and return rules.

Args:
    css: String containing Textual CSS.
    read_from: Original CSS location.
    is_default_rules: True if the rules we're extracting are
        default (i.e. in Widget.DEFAULT_CSS) rules. False if they're from user defined CSS.
    scope: Scope of rules, or empty string for global scope.

Raises:
    StylesheetError: If the CSS is invalid.

Returns:
    List of RuleSets.
)variable_tokensis_default_rulesr   zfailed to parse css; N)r   KeyErrorrn   r   r   r   	Exceptionr   )	r.   r   rt   r   r   r   	cache_keyrE   errors	            r/   _parse_rulesStylesheet._parse_rules   s    . %5EJ		$$Y// 			M$($9$9%5 +	E  	 	M!$9%"ABL	M (-)$s#    
##!A	 	A1A,,A1c                   [         R                  R                  U5      n [        USSS9 nUR	                  5       nSSS5        [         R                  R                  U5      n[        WSS5      U R                  [        U5      S4'   S	U l        g! , (       d  f       NZ= f! [         a    [        SU< 35      Sef = f)
zRead Textual CSS file.

Args:
    filename: Filename of CSS.

Raises:
    StylesheetError: If the CSS could not be read.
    StylesheetParseError: If the CSS is invalid.
rtzutf-8)encodingNzunable to read CSS file Fr   rc   T)ospath
expanduseropenreadabspathr   r   r   r   ru   r   )r.   r   css_filer   r   s        r/   r   Stylesheet.read   s     77%%h/	Uhw78mmo 877??8,D (1eQ'?SYO$" 87  	U!$<XL"IJPTT	Us!   B" B'B" 
BB" "B=c                8    U H  nU R                  U5        M     g)zRead multiple CSS files, in order.

Args:
    paths: The paths of the CSS files to read, in order.

Raises:
    StylesheetError: If the CSS could not be read.
    StylesheetParseError: If the CSS is invalid.
N)r   )r.   pathsr   s      r/   read_allStylesheet.read_all4  s     DIIdO r2   c                "    X4U R                   ;   $ )a  Check if the stylesheet has this CSS source already.

Args:
    path: The file path of the source in question.
    class_var: The widget class variable we might be reading the CSS from.

Returns:
    Whether the stylesheet is aware of this CSS source or not.
)r   )r.   r   	class_vars      r/   
has_sourceStylesheet.has_sourceA  s      DKK//r2   c                >   Uc  S[        [        U5      5      4nX R                  ;   aN  U R                  U   R                  U:X  a1  U R                  U   u  pgpX:  a  [	        XgXE5      U R                  U'   g[	        XXE5      U R                  U'   SU l        SU l        g)a-  Parse CSS from a string.

Args:
    css: String with CSS source.
    read_from: The original source location of the CSS.
    path: The path of the source if a file, or some other identifier.
    is_default_css: True if the CSS is defined in the Widget, False if the CSS is defined
        in a user stylesheet.
    tie_breaker: Integer representing the priority of this source.
    scope: CSS type name to limit scope or empty string for no scope.

Raises:
    StylesheetError: If the CSS could not be read.
    StylesheetParseError: If the CSS is invalid.
Nrc   T)ru   hashr   r   r   r   r   )	r.   r   rt   is_default_cssr   r   r   r   source_tie_breakers	            r/   
add_sourceStylesheet.add_sourceM  s    0 Sc^,I#I(>(F(F#(M>Bkk)>T;G"4!/)2+*I& !*3!SI"r2   c           	        / nUR                   nU R                  R                  5        H  u  nu  nnnnX@R                  ;   a  M   U R	                  UUUUUS9n[        S U 5       5      (       a1  [        U5      n	U R                  R                  U5        [        U	5      eU" U5        M     Xl
        SU l        SU l        g! [
         a    U R                  R                  U5        e f = f)zlParse the source in the stylesheet.

Raises:
    StylesheetParseError: If there are any CSS related errors.
)rt   r   r   r   c              3  8   #    U  H  oR                   v   M     g 7fr+   r,   )r]   r   s     r/   r_   #Stylesheet.parse.<locals>.<genexpr>  s     594;;9ra   FN)extendr   itemsr   r   r   addanyr7   r(   r   r   r   )
r.   rE   	add_rulesrt   r   r   r   r   	css_ruleserror_renderables
             r/   r   Stylesheet.parset  s      "LL	 [[ 
I 
'''
 --'%5 + . 	 59555#3I#> !!%%c**+;<<i % !& #  !!%%c*s   C'C)c           	        [        U R                  S9nU R                  R                  5        H  u  nu  p4pVUR	                  UUUUUS9  M      UR                  5         UR                  U l        SU l        UR                  U l        SU l	        g! [         a'    U R                  R                  UR                  5        e f = f)zRe-parse source, applying new variables.

Raises:
    StylesheetError: If the CSS could not be read.
    StylesheetParseError: If the CSS is invalid.
r   )rt   r   r   r   NF)r   r   r   r   r   r   rE   r   r   r   r   r   update)r.   r   rt   r   r   r   r   s          r/   reparseStylesheet.reparse  s      $//:
AEARARAT=I=+!!#*' "  BU	( %**DK"DO$++DK"'D  	 $$Z%<%<=	s   B 1Cc              #     #    UR                    H.  n[        UR                  U5      (       d  M   UR                  v   M0     g7f)zCheck a rule set, return specificity of applicable rules.

Args:
    rule_set: A rule set.
    css_path_nodes: A list of the nodes from the App to the node being checked.

Yields:
    Specificity of any matching selectors.
N)selector_setr   	selectorsspecificity)rU   r   css_path_nodesr   s       r/   _check_ruleStylesheet._check_rule  s6      %11L 6 6GG"... 2s
   )AA>   oddevenempty
last-childfirst-childfocus-withinlast-of-typefirst-of-typezFinal[set[str]]"_EXCLUDE_PSEUDO_CLASSES_FROM_CACHEanimatecachec                  [        [        5      nU R                  nUR                  5       UR                  -   VVs1 s H  nXV     H  nUiM     M     nnn[        [        UR                  [        U R                  5      5      5      n	[        5       R                  " U	 Vs/ s H  owR                  PM     sn6 n
SU
;   Ul        SU
;   Ul        U
R                  1 Sk5      (       + Ul        SU
;   =(       d    SU
;   Ul        SnUb  U
R                  U R"                  5      (       a  UR$                  UR&                  c  SO SUR&                   3U;   a  UR&                  OSUR(                  UR*                  UR,                  4nUR/                  U5      nUb"  U R1                  XUS9  U R3                  U5        gU R4                  nUR6                  n[        5       n[        5       nU	 H  nUR8                  nUR:                  nU" X~5       Hn  nUR<                  R?                  UUU5       HJ  u  nnnUc*  U(       a  URA                  U5        OURA                  U5        UU   RC                  UU45        ML     Mp     M     U(       Ga#  [E        S	5      n[G        [H        URK                  5        VVs0 s H  u  nnU[M        UUS
9S   _M     snn5      nU H[  nUU   b  M  UU    Vs/ s H  nUS	   S	   (       a  M  UPM     nnU(       a  [M        UUS
9S   nUUU'   MJ  URA                  U5        M]     U HY  nUU   b  M  UU    Vs/ s H  nUS	   S	   (       d  M  UPM     nnU(       a  [M        UUS
9S   nO[O        [P        U5      nUUU'   M[     Ub  UX;'   U R1                  UUUS9  U R3                  U5        gs  snnf s  snf s  snnf s  snf s  snf )a  Apply the stylesheet to a DOM node.

Args:
    node: The `DOMNode` to apply the stylesheet to.
        Applies the styles defined in this `Stylesheet` to the node.
        If the same rule is defined multiple times for the node (e.g. multiple
        classes modifying the same CSS property), then only the most specific
        rule will be applied.
    animate: Animate changed rules.
    cache: An optional cache when applying a group of nodes.
hoverr  >   r  r  r  r  r	  r  r  N#r  r   )keyrb   ))r   rn   r   r   _selector_namesfilter__contains__reversedrE   r   unionpseudo_classes_has_hover_style_has_focus_within
isdisjoint_has_order_style_has_odd_or_evenr
  _parent_idclasses_pseudo_classes_cache_key_css_type_namegetreplace_rules_process_component_classesr   r   r   r   stylesextract_rulesr   r   r   r   r   r   rT   getattr_DEFAULT_STYLES)r.   noder  r  rule_attributesr   rw   r   limit_rulesrE   all_pseudo_classesr   cached_resultr   r   initialinitial_defaultsr   r   base_specificityr  rule_specificityvalueget_first_itemspecificity_rules
node_rulesinitial_rule_namedefault_rules	new_value
rule_values                                 r/   applyStylesheet.apply  s   0 &d+NN	
 "(4+?+??
?! ' ? 	 

 VK44htzz6JKL U[[5*Q54+>+>5*QR '+= =!/3E!E$6$A$AS%
 !
 ''G65G+G 	 #'	!3!>!>33"
 "
  xx' ()$((n	&A$((t..##
I .3YYy-AM(""4"H//5&&,,  E%(UD#44**K$/$E 48KK4M4M$&650C)5 }+,005#KK,#C(//1A50IJ5 %F  ']N#' 4C3H3H3J3J// #/^DQGG3J$J &-!/08
 %44E$F%$FD#Awqz $F " %
 %$'>$J1$M	8A
#45 ),,->?! &-& &6!/08 %44E$F%$FD71: $F " %
 %%(N%KA%N
%,_>O%P
4>J01 &6 $#- tZA''-Y
 +Rv% %s)   N=!O0O'O<OOOc                   UR                  5       nU(       a  SnUR                  R                  5       nUR                  R                  5         [	        U5       Hn  n[        US9nUR                  U5        U R                  USS9  U(       d!  UR                  U5      UR                  :w  a  SnUR                  UR                  U'   Mp     U(       a  UR                  5         ggg)zKProcess component classes for the given node.

Args:
    node: A DOM Node.
F)r   r  TN)_get_component_classes_component_stylesr   r   sortedr#   _attachr;  r#  r&  refresh)r.   r*  component_classesrefresh_nodeold_component_styles	componentvirtual_nodes          r/   r%  %Stylesheet._process_component_classesa  s     !779 L#'#9#9#>#>#@ ""((*#$56	&y9$$T*

<
7$,00;|?R?RR $(L4@4G4G&&y1 7  ! r2   c                ,   UR                   nUR                  nUR                  R                  5       UR                  5       -  nU(       Ga  [	        X5      nXu:X  a  gUR                  5       nUR                  n	UR                  n
UR                  5       nUR                  nUR                  R                  nUR                   R                  nU H  nU
" U5      nU" U5      nUR                  U5      nU	" U5      (       aM  UU:w  d  UR                  X5      (       a1  UR                  U5      nUb  Uu  nnnUR                  UUUUUUUS9  M~  [        X_U5        M     O'UR                  nU H  n[        X_U" U5      5        M     UR                  5         g)zReplace style rules on a node, animating as required.

Args:
    node: A DOM node.
    rules: Mapping of rules.
    animate: Enable animation.
N)final_valuedurationdelayeasing)r&  baser   r   r   get_render_rulesis_animatabler#  appanimatoris_being_animated_get_transitionr  setattrnotify_style_update)rU   r*  rE   r  r&  base_stylesmodified_rule_keys
new_stylescurrent_render_rulesrP  get_current_render_rulenew_render_rulesget_new_render_rulerR  rN  r  old_render_valuenew_render_valuer9  
transitionrK  rM  rL  get_rules                           r/   r$  Stylesheet.replace_rules{  s    kk )//446E,J(#)#:#:#< "00M&:&>&>#)::<"2"6"6xx((H;;##D)#:3#? #6s#; !IIcN	
 !%%$(8811$<<!+!;!;C!@J!-2</&% (( ,(1%-"'#) )  !)49 *> yyH)(3-8 *  "r2   c                >    U R                  UR                  SS9US9  g)zqUpdate styles on node and its children.

Args:
    root: Root note to update.
    animate: Enable CSS animation.
T)	with_selfr  N)update_nodeswalk_children)r.   rootr  s      r/   r   Stylesheet.update  s%     	$,,t,<gNr2   c                   0 nU R                   nU H  nU" XRUS9  [        U[        5      (       d  M!  UR                  (       d  M4  UR                  =(       a    UR
                  nUR                  =(       a    UR                  nU(       a  U" UR                  US9  U(       a  U" UR                  US9  U(       d  M  U(       d  M  U" UR                  US9  M     g)z_Update styles for nodes.

Args:
    nodes: Nodes to update.
    animate: Enable CSS animation.
r  )r  N)r;  r   r&   is_scrollableshow_vertical_scrollbarscrollbar_size_verticalshow_horizontal_scrollbarscrollbar_size_horizontalvertical_scrollbarhorizontal_scrollbarscrollbar_corner)r.   nodesr  r  r;  r*  rk  rm  s           r/   re  Stylesheet.update_nodes  s     (*

D$u5$''D,>,>,>00QT5Q5Q ( 22Ut7U7U * +$11?,$335A,,1H1H$//u= r2   )	__variable_tokensr   r   r   r   r   r   r   r   )rF   zdict[str, str] | Noner8   r9   )r8   zrich.repr.Result)r8   zdict[str, list[Token]])r8   r   )r8   zdict[str, list[RuleSet]])r8   ru   )r8   r   )rF   zdict[str, str]r8   r9   )r   zstr | Styler8   r%   )Fr   rc   )r   ru   rt   r    r   r   r   r   r   ru   r8   r   )r   zstr | PurePathr8   r9   )r   zSequence[PurePath]r8   r9   )rc   )r   ru   r   ru   r8   r   )NFr   rc   )r   ru   rt   zCSSLocation | Noner   r   r   r   r   ru   r8   r9   )r8   r9   )r   r   r   zlist[DOMNode]r8   zIterable[Specificity3])r*  r#   r  r   r  zdict[tuple, RulesMap] | Noner8   r9   )r*  r#   r8   r9   )F)r*  r#   rE   r   r  r   r8   r9   )rg  r#   r  r   r8   r9   )rr  zIterable[DOMNode]r  r   r8   r9   ) r:   r;   r<   r=   r>   r0   r   propertyr   rE   r   r   r   r   r$   r   r   r   r   r   r   r   r   r   r
  r   r;  r%  r$  r   re  r?   r@   r2   r/   r   r      s   2=A 	K' & &
 
 
   D D
(* "'.. . 	.
 . . 
.`#(
0 )-$%% &% 	%
 % % 
%N#J(> //0=/	/ /$	;& 	 .2I.I. 	I.
 ,I. 
I.V4 =BA#A##+A#6:A#	A# A#FO> >r2   r   )F
__future__r   r   collectionsr   	itertoolsr   operatorr   pathlibr   r   typingr	   r
   r   r   r   	rich.reprrichrich.consoler   r   r   r   rich.markupr   rich.paddingr   
rich.panelr   	rich.textr   textual.cacher   textual.css.errorsr   textual.css.matchr   textual.css.modelr   textual.css.parser   textual.css.stylesr   r   textual.css.tokenizer   r   textual.css.tokenizerr   textual.css.typesr    r!   r"   textual.domr#   textual.markupr$   textual.styler%   textual.widgetr&   r)  r(   r7   r   reprautor   r@   r2   r/   <module>r     s    " 	 #   " > >  N N      " . . % # / 7 , E E  &  !(? L
 L
^
 $ S	> S	> S	>r2   