
\c           @   s  d  Z  d d l Z d d l Z d d l Z 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 d d l Z d d l m Z m Z m Z m Z d d	 l m Z d d
 l m Z d d l m Z e r/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$ n  e j% d e j&  Z' d   Z( d   Z) d e* f d     YZ+ d e, f d     YZ- d e j. e j/ f d     YZ0 d e f d     YZ1 d   Z2 d   Z3 d   Z4 d   Z5 d   Z6 d   Z7 d S(    s[  
    sphinx.ext.inheritance_diagram
    ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

    Defines a docutils directive for inserting inheritance diagrams.

    Provide the directive with one or more classes or modules (separated
    by whitespace).  For modules, all of the classes in that module will
    be used.

    Example::

       Given the following classes:

       class A: pass
       class B(A): pass
       class C(A): pass
       class D(B, C): pass
       class E(B): pass

       .. inheritance-diagram: D E

       Produces a graph like the following:

                   A
                  / \
                 B   C
                / \ /
               E   D

    The graph is inserted as a PNG+image map into HTML and a PDF in
    LaTeX.

    :copyright: Copyright 2007-2019 by the Sphinx team, see AUTHORS.
    :license: BSD, see LICENSE for details.
iN(   t   md5(   t   nodes(   t
   directives(   t	   text_type(   t   builtins(   t   render_dot_htmlt   render_dot_latext   render_dot_texinfot   figure_wrapper(   t   ModuleAnalyzer(   t   force_decode(   t   SphinxDirective(   t   Anyt   Dictt   Listt   TupleR   t   Optional(   t   Sphinx(   t   BuildEnvironments   ^(?:([\w.]*)\.)?  # module names
                           (\w+)  \s* $          # class/final module name
                           c         C   s   y t  |   t j j |   SWn t t f k
 r t j |   } | sM d S| j	   \ } } | d k ro d Sy* t  |  t
 t j j |  | d  SWq t t f k
 r d SXn Xd S(   s   Import a object or module using *name* and *currentmodule*.
    *name* should be a relative name from *currentmodule* or
    a fully-qualified name.

    Returns imported object or module.  If failed, returns None value.
    N(   t
   __import__t   syst   modulest   gett   ImportErrort
   ValueErrort   module_sig_ret   matcht   Nonet   groupst   getattr(   t   objnamet   matchedt   modnamet   attrname(    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyt
   try_importD   s    

 c         C   s   d } | r# t | d |   } n  | d k r> t |   } n  | d k r] t d |    n  t j |  rs | g St j |  r g  } xH | j j   D]7 } t j |  r | j | j	 k r | j
 |  q q W| St d |    d S(   s0   Import a class using its fully-qualified *name*.t   .sE   Could not import class or module %r specified for inheritance diagrams=   %r specified for inheritance diagram is not a class or moduleN(   R   R"   t   InheritanceExceptiont   inspectt   isclasst   ismodulet   __dict__t   valuest
   __module__t   __name__t   append(   t   namet
   currmodulet   targett   classest   cls(    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyt   import_classes`   s&    !R$   c           B   s   e  Z RS(    (   R+   R*   (    (    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyR$      s   t   InheritanceGraphc           B   s   e  Z d  Z e e d d g  d  Z d   Z d   Z d d d  Z d   Z	 i d d 6d	 d
 6Z
 i d d 6d d 6d d 6d d 6d d 6Z i d d 6d d 6Z d   Z d   Z i  d i  i  i  d  Z RS(   s   
    Given a list of classes, determines the set of classes that they inherit
    from all the way to the root "object", and then is able to generate a
    graphviz dot graph from them.
    i    c   	      C   sX   | |  _  |  j | |  } |  j | | | | | |  |  _ |  j sT t d   n  d S(   s   *class_names* is a list of child classes to show bases from.

        If *show_builtins* is True, then Python builtins will be shown
        in the graph.
        s(   No classes found for inheritance diagramN(   t   class_namest   _import_classest   _class_infot
   class_infoR$   (	   t   selfR4   R.   t   show_builtinst   private_basest   partst   aliasest   top_classesR0   (    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyt   __init__   s    		c         C   s1   g  } x$ | D] } | j  t | |   q W| S(   s   Import a list of classes.(   t   extendR2   (   R8   R4   R.   R0   R-   (    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyR5      s    c      	      sj   i   t  t  j              f	 d    x | D] }  |  qF Wt  j    S(   sY  Return name and bases for all classes that are ancestors of
        *classes*.

        *parts* gives the number of dotted name parts that is removed from the
        displayed node names.

        *top_classes* gives the name(s) of the top most ancestor class to traverse
        to. Multiple names can be specified separated by comma.
        c            s   r |   k r d  S r4 |  j  j d  r4 d  S j |      }  j |  d    } d  } y |  j r t j |  j  j } |  j j	   j
 d  d } t | t  s t | |  } n  | r d | j d d  } q n  Wn t k
 r n Xg  } | | | | f  |  <|  k r%d  Sx~ |  j D]s }  rN|  k rNq/n   rm| j  j d  rmq/n  | j  j |      |  k r/ |  q/q/Wd  S(   Nt   _i    s   
s   "%s"t   "s   \"(   R+   t
   startswitht
   class_nameR   t   __doc__R	   t
   for_moduleR*   t   encodingt   stript   splitt
   isinstanceR   R
   t   replacet	   Exceptiont	   __bases__R,   (   R1   t   nodenamet   fullnamet   tooltipt   enct   doct   baselistt   base(	   R<   t   all_classesR;   R:   t   py_builtinst   recurseR8   R9   R=   (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyRV      s:    	 (   t   varsR   R)   t   list(   R8   R0   R9   R:   R;   R<   R=   R1   (    (	   R<   RT   R;   R:   RU   RV   R8   R9   R=   s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyR6      s    '&c         C   s   | j  } | d k r! | j } n d | | j f } | d k rI | } n# | j d  } d j | |  } | d k	 r | | k r | | S| S(   s   Given a class object, return a fully-qualified name.

        This works for things I've tested in matplotlib so far, but may not be
        completely general.
        t   __builtin__R   s   %s.%si    R#   (   RY   R   N(   R*   R+   RH   t   joinR   (   R8   R1   R;   R<   t   moduleRN   t   resultt
   name_parts(    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyRC      s    		c         C   s&   g  |  j  D] \ } } } } | ^ q
 S(   s1   Get all of the class names involved in the graph.(   R7   (   R8   R@   RN   (    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyt   get_all_class_names   s    t   LRt   rankdirs   "8.0, 12.0"t   sizet   boxt   shapei
   t   fontsizeg      ?t   heightsA   "Vera Sans, DejaVu Sans, Liberation Sans, Arial, Helvetica, sans"t   fontnames   "setlinewidth(0.5)"t   styleg      ?t	   arrowsizec         C   s0   d j  g  t | j    D] } d | ^ q  S(   Nt   ,s   %s=%s(   RZ   t   sortedt   items(   R8   t   attrst   x(    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyt   _format_node_attrs  s    c         C   s0   d j  g  t | j    D] } d | ^ q  S(   Nt    s   %s=%s;
(   RZ   Rj   Rk   (   R8   Rl   Rm   (    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyt   _format_graph_attrs  s    c         C   s  |  j  j   } |  j j   } |  j j   }	 | j |  | j |  |	 j |  | r | j | j j  | j | j j  |	 j | j j  n  g  }
 |
 j	 d |  |
 j	 |  j
 |   x t |  j  D] \ } } } } | j   } | | k rd | | | d <d | d <n  | r/| | d <n  |
 j	 d | |  j |  f  x1 | D]) } |
 j	 d | | |  j |	  f  qVWq W|
 j	 d	  d
 j |
  S(   sV  Generate a graphviz dot graph from the classes that were passed in
        to __init__.

        *name* is the name of the graph.

        *urls* is a dictionary mapping class names to HTTP URLs.

        *graph_attrs*, *node_attrs*, *edge_attrs* are dictionaries containing
        key/value pairs to pass on as graphviz properties.
        s   digraph %s {
s   "%s"t   URLs   "_top"R/   RO   s     "%s" [%s];
s     "%s" -> "%s" [%s];
s   }
Ro   (   t   default_graph_attrst   copyt   default_node_attrst   default_edge_attrst   updatet   configt   inheritance_graph_attrst   inheritance_node_attrst   inheritance_edge_attrsR,   Rp   Rj   R7   Rn   RZ   (   R8   R-   t   urlst   envt   graph_attrst
   node_attrst
   edge_attrst   g_attrst   n_attrst   e_attrst   resRN   t   basesRO   t   this_node_attrst	   base_name(    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyt   generate_dot  s8    "		N(   R+   R*   RD   t   FalseR   R>   R5   R6   RC   R^   Rr   Rt   Ru   Rn   Rp   R   (    (    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyR3      s.   		9	


		t   inheritance_diagramc           B   s   e  Z d  Z RS(   sN   
    A docutils node to use as a placeholder for the inheritance diagram.
    (   R+   R*   RD   (    (    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyR   ?  s   t   InheritanceDiagramc           B   s]   e  Z d  Z e Z d Z d Z e Z i e	 j
 d 6e	 j d 6e	 j d 6e	 j d 6Z d   Z RS(   sJ   
    Run when the inheritance_diagram directive is first encountered.
    i   i    R;   s   private-basest   captions   top-classesc         C   s  t    } |  j j | _ |  j d j   } |  j j d  j d  } |  j j	 d d  | d <d j
 |  | d <g  | d <xL |  j j	 d d  j d	  D], } | j   } | r | d j |  q q WyQ t | |  j j j	 d
  d | d d d |  j k d |  j j d | d } Wn6 t k
 rT} | j j j | j d d |  j g SXxF | j   D]8 } | d d | | d |  j  \ } }	 | j |  qbW| | d <|  j j	 d  }
 |
 rt |  | |
  } n  | g S(   Ni    t   pyt   classR;   s   , t   contents   top-classesRo   Ri   s	   py:moduleR:   s   private-basesR<   R=   t   lines   :class:`%s`t   graphR   (   R   t   statet   documentt	   argumentsRH   R|   t
   get_domaint   rolet   optionsR   RZ   RG   R,   R3   t   ref_contextRw   t   inheritance_aliasR$   t   reportert   warningt   argst   linenoR^   R?   R   (   R8   t   nodeR4   t
   class_roleR1   R   t   errR-   t   refnodesRm   R   (    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyt   runU  s<    	
%
"
(   R+   R*   RD   R   t   has_contentt   required_argumentst   optional_argumentst   Truet   final_argument_whitespaceR   t   nonnegative_intt   flagt	   unchangedt   unchanged_requiredt   option_specR   (    (    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyR   F  s   


c         C   s5   |  d t  |  d  j d  } t |  j   d S(   NR   R;   s   utf-8i(   t   strt   encodeR    t	   hexdigest(   R   t   encoded(    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyt   get_graph_hash  s    !c   
      C   su  | d } t  |  } d | } |  j j j j j   } |  j j |  j j } i  } x | D] } | j d  d k	 r | d k r d | j d  | | d <q| j d  | | d <q[ | j d  d k	 r[ | d k rd | d | j d  | | d <qd | j d  | | d <q[ q[ W| j
 | | d	 |  j j }	 t |  | |	 i  d
 d
 d d | d t j  d S(   sZ   
    Output the graph for HTML.  This will insert a PNG with clickable
    image map.
    R   s   inheritance%st   refurit   SVGs   ../t   reftitlet   refidt   #R|   t   inheritancet   alts   Inheritance diagram of R   N(   R   t   builderR|   Rw   t   graphviz_output_formatt   uppert   current_docnamet
   out_suffixR   R   R   R   R   t   SkipNode(
   R8   R   R   t
   graph_hashR-   R   t   current_filenameR{   t   childt   dotcode(    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyt   html_visit_inheritance_diagram  s&    

&"c         C   sk   | d } t  |  } d | } | j | d |  j j d i d d 6} t |  | | i  d  t j  d S(	   s>   
    Output the graph for LaTeX.  This will insert a PDF.
    R   s   inheritance%sR|   R}   s	   "6.0,6.0"Ra   R   N(   R   R   R   R|   R   R   R   (   R8   R   R   R   R-   R   (    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyt   latex_visit_inheritance_diagram  s    

c         C   sk   | d } t  |  } d | } | j | d |  j j d i d d 6} t |  | | i  d  t j  d S(	   s@   
    Output the graph for Texinfo.  This will insert a PNG.
    R   s   inheritance%sR|   R}   s	   "6.0,6.0"Ra   R   N(   R   R   R   R|   R   R   R   (   R8   R   R   R   R-   R   (    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyt!   texinfo_visit_inheritance_diagram  s    

c         C   s   t  j  d  S(   N(   R   R   (   R8   R   (    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyt   skip  s    c         C   s   |  j  d  |  j t d t d  f d t d  f d t d  f d t d  f d t d  f |  j d t	  |  j
 d i  t  |  j
 d	 i  t  |  j
 d
 i  t  |  j
 d i  t  i t j d 6t d 6S(   Ns   sphinx.ext.graphvizt   latext   htmlt   textt   mant   texinfos   inheritance-diagramRx   Ry   Rz   R   t   versiont   parallel_read_safe(   t   setup_extensiont   add_nodeR   R   R   R   R   R   t   add_directiveR   t   add_config_valueR   t   sphinxt   __display_version__R   (   t   app(    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyt   setup  s    (8   RD   R%   t   reR   t   hashlibR    t   docutilsR   t   docutils.parsers.rstR   t   sixR   t	   six.movesR   R   t   sphinx.ext.graphvizR   R   R   R   t   sphinx.pycodeR	   t   sphinx.utilR
   t   sphinx.util.docutilsR   R   t   typingR   R   R   R   R   t   sphinx.applicationR   t   sphinx.environmentR   t   compilet   VERBOSER   R"   R2   RK   R$   t   objectR3   t   Generalt   ElementR   R   R   R   R   R   R   R   (    (    (    s=   lib/python2.7/site-packages/sphinx/ext/inheritance_diagram.pyt   <module>%   s>   ".		 =		!			