
    Le=B                         d Z ddlmZ ddlZddlZddlZddlm	Z	m
Z
mZ ddlmZ ddlmZ dd	lmZ d
ZdZ G d dej                  Z ed          Z G d d          Z G d de          Z G d de          ZdS )a  
The magics offered by the HoloViews IPython extension are powerful and
support rich, compositional specifications. To avoid the the brittle,
convoluted code that results from trying to support the syntax in pure
Python, this file defines suitable parsers using pyparsing that are
cleaner and easier to understand.

Pyparsing is required by matplotlib and will therefore be available if
HoloViews is being used in conjunction with matplotlib.
    )groupbyN   )CycleOptionsPalette)merge_option_dicts)
Compositor   )dimABCDEFGHIJKLMNOPQRSTUVWXYZz\0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ!#$%&\()*+,-./:;<=>?@\\^_`{|}~c                       e Zd ZdS )ParserWarningN)__name__
__module____qualname__     5lib/python3.11/site-packages/holoviews/util/parser.pyr   r      s          r   r   Warning)namec                   ~    e Zd ZdZeeeedZdZ	e
d             Ze
d             Ze
d             Ze
d
d	            ZdS )Parserza
    Base class for magic line parsers, designed for forgiving parsing
    of keyword lists.
    )npr   r   r   Fc                 b    |d         dk    r
|dd         n|}|d         dk    r
|dd         n|S )z4Strip out any leading/training commas from the token,Nr   r
   r   )clskws     r   _strip_commaszParser._strip_commas+   s?     2RWWAr!""vv+r   c                     g }|D ]g}t          |t                    r; fd|D             }|                    d                    |          z             R|                    |           hd                    |          z  S )Nc                 v    g | ]5}t          |t                    r                    |          n|gD ]}|6S r   )
isinstancelistrecurse_token).0tsr   inners      r   
<listcomp>z(Parser.recurse_token.<locals>.<listcomp>6   sb     > > >)!T22<C--a7779:> >a1 > > > >r    )r"   r#   appendjoin)r   tokenr(   recursedtoknew_toks   ` `   r   r$   zParser.recurse_token1   s     	% 	%C#t$$ %> > > > >c > > > (8(8 89999$$$$rwwx((((r   c                 J   |dk    rdnd}|g S g }|                                 D ]}}t          |t                    r%|                     ||          }|d         |z   |d<   <|                                dk    rU|                    |                     |                     ~|S )zN
        Collect the tokens from a (potentially) nested parse result.
        parensz(%s)z[%s]Nr   r   )asListr"   r#   r$   stripr+   r   )r   parseresultmoder(   tokensr-   s         r   collect_tokenszParser.collect_tokens>   s    
 ..fr	 '')) 	8 	8E%&& 8))%77#BZ%/r

;;==C''c//667777r   r2   Nc                    |i }g i }}|                      ||          }t          |d           D ]s}|\  }}	|du r|t          |	          z  }|du rRt          |	          }
t          d |
D                       rdnd}|dxx         ||                    |
          z   z  cc<   t|D ]}d	D ]\  }}|                    ||          }	 |                    t          d
| dt          | j	        fi |                     Y# t          $ r; | j        rt          d|          d}t                              ||z             Y w xY w|S )a  
        Helper function to return dictionary given the parse results
        from a pyparsing.nestedExpr object (containing keywords).

        The ns is a dynamic namespace (typically the IPython Notebook
        namespace) used to update the class-level namespace.
        Nc                 
    d| v S )N=r   )els    r   <lambda>zParser.todict.<locals>.<lambda>^   s
    r	 r   TFc              3   &   K   | ]}d |v pd|v V  dS ))}Nr   r%   r<   s     r   	<genexpr>z Parser.todict.<locals>.<genexpr>f   sC       "6 "6&( %(2I#=3"9 "6 "6 "6 "6 "6 "6r   r   r*   r   ))z(,()z{,{)z=,r;   )z,::)z:,rE   )z,,r   )z,..zdict(r?   zCould not evaluate keyword: z2Ignoring keyword pair that fails to evaluate: '%s')r8   r   r#   anyr,   replaceupdateevaldict	namespace	Exceptionabort_on_eval_failureSyntaxErrorparsewarningwarning)r   r5   r6   nsgroupedkwargsr7   groupvalitemselementsjoinerkeywordfstsndmsgs                   r   todictzParser.todictP   s    :Bb##K66V%9%9:: 
	> 
	>E LS%d{{4;;&e||u++ " "6 "6,4"6 "6 "6 6 6 >ss;= vH(=(=== 	4 	4G+ 4 4	S "//#s334d#57#5#5#5#'#<#<#<#<> > ? ? ? ? 4 4 4, R%&PW&P&PQQQJ$$S7]33333	4 s   7C??AEE)r2   N)r   r   r   __doc__r   r   r   r   rL   rN   classmethodr   r$   r8   r^   r   r   r   r   r       s          EgcJJI!, , [,
 
) 
) [
)   [" ) ) ) [) ) )r   r   c                      e Zd ZdZ ej        dd ej         ej        e          ej	        z                      
                    d          Z ej        dd ej         ej        e          ej	        z                      
                    d          Zeez  Z ej        dd	d
          
                    d          Z ej        dd	d
          
                    d          Zeez  Z ej        ddd
          
                    d          Z ej        ddd
          
                    d          Zeez  Z ej        d ej        D                       Z ej         ej        ed           ej        ej        dz             z             Zeez  
                    d          Z ej        e ej        e           ej        e          z   ej        e          z  z             Z ej        e          Z dddddddddd d!
Z!g Z"e#d"             Z$e#d#             Z%e#d$             Z&e#d'd%            Z'e#d'd&            Z(d
S )(OptsSpeca.  
    An OptsSpec is a string specification that describes an
    OptionTree. It is a list of tree path specifications (using dotted
    syntax) separated by keyword lists for any of the style, plotting
    or normalization options. These keyword lists are denoted
    'plot(..)', 'style(...)' and 'norm(...)'  respectively.  These
    three groups may be specified even more concisely using keyword
    lists delimited by square brackets, parentheses and braces
    respectively.  All these sets are optional and may be supplied in
    any order.

    For instance, the following string:

    Image (interpolation=None) plot(show_title=False) Curve style(color='r')

    Would specify an OptionTree where Image has "interpolation=None"
    for style and 'show_title=False' for plot options. The Curve has a
    style set such that color='r'.

    The parser is fairly forgiving; commas between keywords are
    optional and additional spaces are often allowed. The only
    restriction is that keywords *must* be immediately followed by the
    '=' sign (no space).
    [])contentplot_optionszplot[)openercloserre   rC   r?   Nrg   rh   
ignoreExprstyle_optionszstyle(rD   r@   norm_optionsznorm{c                 N    g | ]"}|j         	t          j        |j                   #S r   )rU   ppLiteralrA   s     r   r)   zOptsSpec.<listcomp>   s+    KKK""(KBH		KKKr   r
   )exactz._pathspechspacevspacez    fig_alpha
fig_bounds
fig_inches	fig_latexfig_rcparamsfig_sizexaxisyaxis)
horizontal_spacingvertical_spacingfigure_alphafigure_boundsfigure_inchesfigure_latexfigure_rcparamsfigure_size
show_xaxis
show_yaxisc                    d|vrdS |d         d                                          g k    rdS g dD ]-}                    |          dk    rt          d|z            .t          fdD                       s%t          dd	                                         d
dg}|D ]>}t          fd|D                       r!t          d|d          d|d                    ?t                    dk    r&d                             d          rd}dv rdnd}nIt                    dk    r&d                             d          rd}dv rdnd}ndv rdnd}dv rdnd}t          ||          S )z
        Given a normalization parse group (i.e. the contents of the
        braces), validate the option list and compute the appropriate
        integer value for the normalization plotting option.
        rl   Nr   )
+framewise
-framewise	+axiswise	-axiswiser
   z8Normalization specification must not contain repeated %rc              3       K   | ]}|v V  	d S Nr   )r%   optoptionss     r   rB   z1OptsSpec.process_normalization.<locals>.<genexpr>   s'      22c3'>222222r   z Normalization option not one of z, )r   r   )r   r   c              3       K   | ]}|v V  	d S r   r   )r%   excludeoptss     r   rB   z1OptsSpec.process_normalization.<locals>.<genexpr>   s'      77w7d?777777r   z0Normalization specification cannot contain both z and 	framewiseFr   Taxiswiser   )r   r   )r3   countrO   allr,   lenendswithrK   )	r   parse_groupnormoptexcludedpairr   r   r   r   s	          @@r   process_normalizationzOptsSpec.process_normalization   s.    +--tt>*1-44662::ddHHH 	D 	DGzz'""Q&&! #9;B#C D D D ' 2222T22222 	WU7ASASUUVVV02LM 	L 	LD7777$77777 L! #K377#K #KAEa#K #K L L LL
 t99>>d1g..{;;>H , 4 4%IIYY!^^Q 0 0 < <^I*d22ttHH*d22ttH , 4 4%IX') ) ) 	)r   c              #      K   t                      }|D ]?}|                    |d                    d|v pd|v pd|v }|r||fV  t                      }@|r|i fV  dS dS )a9  
        Given a parsed options specification as a list of groups, combine
        groups without options with the first subsequent group which has
        options.
        A line of the form
            'A B C [opts] D E [opts_2]'
        results in
            [({A, B, C}, [opts]), ({D, E}, [opts_2])]
        rq   rl   rf   rk   N)setadd)r   line_parse_resultactive_pathspecsrU   has_optionss        r   _group_paths_without_optionsz%OptsSpec._group_paths_without_options  s       55& 
	) 
	)E  z!2333 %' )%')5( 
  )&----#&55  	'"B&&&&&&	' 	'r   c                 
   |                     d          }d}| j        D ]c\  }}|d         |k    rRt                              |                    ||                     d                    |g|dd         z             c S d|S )zGConvert any potentially deprecated paths and issue appropriate warningsrF   z,Element {old} deprecated. Use {new} instead.r   )oldnewr
   N)splitdeprecationsrP   rQ   formatr,   )r   pathr   r]   r   r   s         r   apply_deprecationszOptsSpec.apply_deprecations#  s     

3<( 	3 	3HCQx3$$SZZCSZ%A%ABBBxxabb	 122222  r   c                     |i }d  j                             |          D             }t          |          dk    rt          d          |d         d         }|d|         }|                                |                                k    rt          d||d                                         j                             |                    }i }|D ]\  }}	i }
                     |	          }|||
d<   d	|	v rI|	d	         d         }                     |d
|          } fd|	                                D             |
d<   d|	v rI|	d         d         }                     |d|          } fd|	                                D             |
d<   |D ])}t          |                    |i           |
          ||<   * fd|	                                D             S )z
        Parse an options specification, returning a dictionary with
        path keys and {'plot':<options>, 'style':<options>} values.
        Nc                     g | ]}|S r   r   r%   ps     r   r)   z"OptsSpec.parse.<locals>.<listcomp>7  s    ===1===r   r
   Invalid specification syntax.r   r   %Failed to parse remainder of string: normrf   bracketsrR   c                 N    i | ]!\  }}j                             ||          |"S r   aliasesgetr%   kvr   s      r   
<dictcomp>z"OptsSpec.parse.<locals>.<dictcomp>L  s/    "R"R"Rca3;??1Q#7#7"R"R"Rr   plotrk   r2   c                 N    i | ]!\  }}j                             ||          |"S r   r   r   s      r   r   z"OptsSpec.parse.<locals>.<dictcomp>Q  s/    #S#S#SsqCKOOAa$8$8#S#S#Sr   stylec                 z    i | ]7\  }}                     |          d  |                                D             8S )c                 .    i | ]\  }}|t          d i |S )r   )r   )r%   option_typeoption_pairss      r   r   z-OptsSpec.parse.<locals>.<dictcomp>.<dictcomp>W  s<     + + +-K W44|44+ + +r   )r   rW   )r%   r   r   r   s      r   r   z"OptsSpec.parse.<locals>.<dictcomp>V  sa     
 
 

 g	 ""4(( + +18+ + +
 
 
r   )	opts_spec
scanStringr   rO   r4   r   parseStringr   r^   rW   r   r   )r   linerR   parsese	processedgrouped_pathsparse	pathspecsrU   r   normalizationplotoptsr   	styleoptsrq   s   `               r   r   zOptsSpec.parse/  s*    :B==cm66t<<===v;;!=>>>q	!ARaRI!!TZZ\\11!"V$qrr("V"VWWW889R9RSW9X9XYY - 	W 	WIuG55e<<M("/&&!.1!4zz(J2z>>"R"R"R"RTZZ\\"R"R"R%''!/215	zz)X"z==#S#S#S#Sdjjll#S#S#S % W W"4UYYx5L5Lg"V"VhW
 
 
 

 "'
 
 
 	
r   c                 .   |i }|                      ||          }g }t          |                                          D ]U}||         }i }|                                D ]}t	          |j        fi |}|                    t          |fi |           V|S )zr
        Similar to parse but returns a list of Options objects instead
        of the dictionary format.
        Nr   )r   sortedkeysvaluesrK   rT   r+   r   )	r   r   rR   parsedoptions_listspecr   mergedrU   s	            r   parse_optionszOptsSpec.parse_options^  s     :B4B''6;;==)) 	9 	9DTlGF )) 6 6el55f55 7 7 7 78888r   r   ))r   r   r   r_   rn   
nestedExpr	OneOrMoreWordallowedquotedStringsetResultsNameplot_options_shortplot_options_longrf   style_options_shortstyle_options_longrk   norm_options_shortnorm_options_longrl   
MatchFirstr	   definitionscompositor_opsCombineascii_uppercase	alphanumsdotted_pathrq   GroupOptional
spec_groupr   r   r   r`   r   r   r   r   r   r   r   r   rb   rb   ~   si        2 's'*/;r|GBGG<L<Lr<^/_/_% % % &4^N%C%C 
 &W-0.:bl7277;K;Kbo;].^.^$ $ $ %3N>$B$B 
 ')::L'"-s/237& & & '5n_&E&E 
 'h.126% % % &4^O%D%D 
 )+==M 'c.126% % % &4^N%C%C 
 &W-015$ $ $ %3N>$B$B 
 ')::L"R]KK
(>KKKM MN "*gbgoQ??? 'T(9 : :; < <K n,<<ZHHH (&2;|44(R[667(R[7789 : :J
 Z((I %-$,-"."."-"0",")")	+ 	+G L%) %) [%)P ' ' [':   [ ,
 ,
 ,
 [,
\    [  r   rb   c                   d   e Zd ZdZ ej        ej        ej        z   dz                                 d          Z	 ej        ej        ej        z   dz                                 d          Z
 ej        ddd                              d	          Z ej        ej        ej        z   dz                                 d
          Z ej        ddd                              d          Z ej         ej        e	e
z   ez   ez    ej        e          z                       Zedd            ZdS )CompositorSpeca1  
    The syntax for defining a set of compositor is as follows:

    [ mode op(spec) [settings] value ]+

    The components are:

    mode      : Operation mode, either 'data' or 'display'.
    group     : Value identifier with capitalized initial letter.
    op        : The name of the operation to apply.
    spec      : Overlay specification of form (A * B) where A and B are
                 dotted path specifications.
    settings  : Optional list of keyword arguments to be used as
                parameters to the operation (in square brackets).
    _r6   oprC   r?   Nri   r   valuerc   rd   op_settingsc           	         |i }g }d | j                             |          D             }t          |          dk    rt          d          |d         d         }|d|         }|                                |                                k    rt          d||d                   d t
          j        D             }| j                             |          D ]}d	|vs
|d	         d
vrt          d          |d	         }	i }
||d                  }d                    |d         	                                d                   }|d         |vrt          d|d         z            d|v r$| 
                    |d         d         d|          }
t          t          |          |t          |d                   |	fi |
}|                    |           |S )zO
        Parse compositor specifications, returning a list Compositors
        Nc                     g | ]}|S r   r   r   s     r   r)   z(CompositorSpec.parse.<locals>.<listcomp>  s    CCC1CCCr   r
   r   r   r   r   c                     i | ]
}|j         |S r   )r   )r%   r   s     r   r   z(CompositorSpec.parse.<locals>.<dictcomp>  s    @@@BR@@@r   r6   )datadisplayz.Either data or display mode must be specified.r    r   z4Operation %s not available for use with compositors.r   r   r   r   )compositor_specr   r   rO   r4   r	   
operationsr   r,   r3   r^   strr+   )r   r   rR   r   r   r   r   opmaprU   r6   rT   	operationr   
definitions                 r   r   zCompositorSpec.parse  s   
 :BCCc1<<TBBCCCv;;!=>>>q	!ARaRI!!TZZ\\11!"V$qrr("V"VWWW@@**?@@@(44T:: 	+ 	+Ee##f=P(P(P!"RSSS=DFeDk*I88E&M00221566Dd5((!"X$)$K#0 1 1 1&&E-$8$;ZBOO#CIIy#eGn:M:Mt^^W]^^Jz****r   r   )r   r   r   r_   rn   r   alphasnumsr   r6   r   r   overlay_specr   r   r   r   r   r   r`   r   r   r   r   r   r   s  s{          2729RW$S())88@@D	27"3&	'	'	6	6t	<	<B 2=(+,0    .~f55 
 BGBIbg%c)**99'BBE"-s'*+/   -n];; 
 #bl828D2I,Du,L.9bk+.F.F-G $H $H I IO # # # [# # #r   r   )r_   	itertoolsr   numpyr   param	pyparsingrn   core.optionsr   r   r   	core.utilr   r   r	   	transformr   r   r   Parameterizedr   rP   r   rb   r   r   r   r   <module>r     su  	 	                2 2 2 2 2 2 2 2 2 2 * * * * * * " " " " " "      .
i . - - - -E' - - -}),,,Z Z Z Z Z Z Z Z|p p p p pv p p pjI I I I IV I I I I Ir   