3
d                 @   s  d Z ddlZddlZddlZddlZ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 ddlmZ ddlmZmZ ddlmZmZ dd	lmZ dd
lmZ ddl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)m*Z*m+Z+m,Z,m-Z-m.Z.m/Z/ ddl0m1Z1m2Z2m3Z3m4Z4m5Z5m6Z6 ddl7m8Z8 ddl9m:Z: ddl;m<Z< ddl=m>Z>m?Z?m@Z@ dZAG dd dejBZCe,e-fZDdZEdZFdZGdZHdZIdZJdZKdZLdqZMdrZNejOd!ZPe" jQ ZRejSe/d"ZTdsd#d$ZUd%d& ZVd'd( ZWd)d* ZXd+d, ZYd-d. ZZd/d0 Z[G d1d2 d2Z\d3d4 Z]d5d6 Z^d7d8 Z_d9d: Z`d;d< ZadZbG d=d> d>ecZdd?d@ ZedAdB ZfdCdDdEdFdGZgdtdHdIZhdJdK ZidudLdMZjdNdO ZkG dPdQ dQeeddRZlelZbG dSdT dTelZmG dUdV dVemZnG dWdX dXelZoG dYdZ dZejpedZqG d[d\ d\eleqdRZrG d]d^ d^erZsG d_d` d`elZtG dadb dbemZuG dcdd ddeoZvG dedf dfemZwe%ewZxG dgdh dheqZyG didj djeleydRZzdkdl Z{dmdn Z|G dodp dpezZ}dS )vzc Defines the HasTraits class, along with several useful subclasses and
    associated metaclasses.
    N)FunctionType   )__version__)AdaptationError)DefaultValue	TraitKind)CTrait
__newobj__)
CHasTraits)api)ForwardPropertyPropertyTraitgeneric_trait)AnyBoolDisallowEventPythonStr) ExtendedTraitChangeNotifyWrapperFastUITraitChangeNotifyWrapperNewTraitChangeNotifyWrapper!StaticAnytraitChangeNotifyWrapperStaticTraitChangeNotifyWrapperTraitChangeNotifyWrapperui_dispatch)SequenceTypesTraitsCache	Undefinedis_none	not_event	not_false)
TraitError)
deprecated)check_traitsui_major_version)check_traitmapped_trait_for	trait_forc               @   s   e Zd ZdS )AbstractViewElementN)__name__
__module____qualname__ r-   r-   3/tmp/pip-build-7vycvbft/traits/traits/has_traits.pyr)   U   s   r)   __base_traits____class_traits____prefix_traits____listener_traits____observer_traits__Z__view_traits____instance_traits__Ztraits_vieweventdelegateconstantpropertyz.*[ :\+\-,\.\*\?\[\]])sameuic             C   sB   t tj}|j|  | jdk	r*| jj |_|dk	r>|jj| |S )z+ Creates a clone of a specified trait.
    N)r   r   traitclone__dict__copyupdate)r<   metadatar;   r-   r-   r.   _clone_trait   s    


rA   c             C   s$   t | |d}|dk	r t|r |S dS )z4 Get the definition of a specified method (if any). N)getattris_unbound_method_type)clsmethodresultr-   r-   r.   _get_method   s    rG   c             C   s   |dd dkr"d| j d|f }|j|}|dk	r`t|r`t|dddkr`t|dddkr`|S xL|D ]D}t||d}|dk	rft|rft|dddkrft|dddkrf|S qfW dS )	z9 Gets the definition of a specified method (if any).
    r      __z_%s%s_Non_trait_change_observe_inputs)lstripgetrC   rB   )
class_name
class_dictbasesrE   rF   baser-   r-   r.   _get_def   s     

rS   c             C   s   t j| pt j| S )z Check for something that looks like an unbound class method.

    This is used in practice to identify magic-named _name_changed
    and _name_fired methods.

    )inspect
isfunctionismethoddescriptor)rE   r-   r-   r.   rC      s    
rC   c             C   s~   t | ttfr,x| D ]}t|sdS qW dS t | trhx,| j D ] \}}t| s\t| r@dS q@W dS t | t p|| jtS )z? Returns whether or not a specified value is serializable.
    FT)	
isinstancelisttuple_is_serializabledictitems	HasTraitshas_traits_interfaceISerializable)valueitemnamer-   r-   r.   rZ      s    

rZ   c             C   s  i }xn|D ]f}x`|j jtj D ]L\}}|j|}|dkrL|dd ||< q x|D ]}||krR|j| qRW q W q
W x| j D ]\}}|dd dkot|r~d}	|jd}
|
dk rd}	|jd}
|
dkr~||
|	 d }|d	kr~||d|
 f}|j|g }||kr~|j| q~W |S )
zX Returns a dictionary of potential 'Instance' or 'List(Instance)'
        handlers.
    Nr   rJ      Z_changed_for_rH      Z_fired_for_ )r=   rN   InstanceTraitsr\   appendrC   find
setdefault)rP   rQ   instance_traitsrR   rb   Zbase_arg_lists	arg_listsarg_listr`   ncolkeyr-   r-   r.   _get_instance_handlers   s0    




rp   c             C   sJ   |j }|dkr| }n(t|dkr<|d dkr<|dd |  }d|j|f S )zb Returns the correct 'delegate' listener pattern for a specified name
    and delegate trait.
    re   r   *Nz %s:%srr   )_prefixlenZ	_delegate)rb   r;   prefixr-   r-   r.   get_delegate_pattern   s    rv   c               @   s   e Zd Zdd Zdd ZdS )_SimpleTestc             C   s
   || _ d S )N)r`   )selfr`   r-   r-   r.   __init__  s    z_SimpleTest.__init__c             C   s
   || j kS )N)r`   )rx   testr-   r-   r.   __call__  s    z_SimpleTest.__call__N)r*   r+   r,   ry   r{   r-   r-   r-   r.   rw     s   rw   c             C   s.   x(|D ] }t |tst|}| j| qW dS )z< Adds a list of handlers to a specified notifiers list.
    N)rW   WrapperTypesr   rg   )	notifiershandlershandlerr-   r-   r.   _add_notifiers  s    

r   c             C   sX   | j }|dk	rTt|tr|g}x4|D ],}|jt|d|  |jt|d|  q$W dS )zG Adds any specified event handlers defined for a trait by a class.
    Nz_%s_changedz	_%s_fired)r5   rW   strrg   rG   )r;   rD   r~   eventsr5   r-   r-   r.   _add_event_handlers  s    

r   c             C   s
   | j |S )zW Returns the method associated with a particular class property
    getter/setter.
    )rN   )rP   rb   r-   r-   r.   _property_method*  s    r   c                s2    fddfdd}t | }t|d|ddS )a   Create the metadata for setting up an observer for Property.

    Parameters
    ----------
    observe : str or list or Expression
        As is accepted by HasTraits.observe expression argument
        This is the value provided in Property(observe=...)
    property_name : str
        The name of the property trait.
    cached : boolean
        Whether the property is cached or not.

    Returns
    -------
    state : dict
        State to be used by _init_traits_observers
    c                s0    rt  }| jj|t}nt}| j| d S )N)r   r=   popr   trait_property_changed)instancer5   Z
cache_nameold)cachedproperty_namer-   r.   r   D  s
    z/_create_property_observe_state.<locals>.handlerc                s   t j | S )N)types
MethodType)r   rb   )r   r-   r.   handler_getterL  s    z6_create_property_observe_state.<locals>.handler_getterr9   F)graphsdispatchr   	post_init)_compile_expressionr[   )observer   r   r   r   r-   )r   r   r   r.   _create_property_observe_state1  s    r   c             C   sP   t | tr| }n| g}g }x0|D ](}|jt |tr<tj|ntj| q W |S )a\   Compile a user-supplied expression or list of expressions.

    Converts a list of strings or ObserverExpressions to a list of
    ObserverGraphs representing the observation patterns to be applied.

    Parameters
    ----------
    expression : str or list or ObserverExpression
        A description of what traits are being observed.
        If this is a list, each item must be a string or an ObserverExpression.

    Returns
    -------
    graphs : list of ObserverGraph
        List of graphs representing the observation patterns to be applied
        to the relevant objects and handlers.
    )rW   rX   extendr   observe_apiZcompile_strZcompile_expr)
expressionZexpressionsr   exprr-   r-   r.   r   Y  s    

r   c               @   s8   e Zd ZdZi Zdd Zed
ddZedddZd	S )MetaHasTraitsa   Controls the creation of HasTraits classes.

    The heavy work is done by the `update_traits_class_dict` function, which
    takes the ``class_dict`` dictionary of class members and extracts and
    processes the trait declarations in it. The trait declarations are then
    added back to the class dictionary and passed off to the __new__ method
    of the type superclass, to be added to the class.

    c             C   sp   t ||| tj| |||}d|j|jf }xtjj|g D ]}|| q<W xtjjdg D ]}|| q\W |S )Nz%s.%sre   )update_traits_class_dicttype__new__r+   r*   r   
_listenersrN   )rD   rO   rQ   rP   klassrb   listenerr-   r-   r.   r     s    zMetaHasTraits.__new__re   c             C   s(   t jdtdd tjj|g j| dS )z Adds a class creation listener.

        If the class name is the empty string then the listener will be called
        when *any* class is created.

        .. deprecated:: 6.3.0
        zadd_listener is deprecatedrH   )
stacklevelN)warningswarnDeprecationWarningr   r   ri   rg   )rD   r   rO   r-   r-   r.   add_listener  s    	zMetaHasTraits.add_listenerc             C   s$   t jdtdd tj| j| dS )zK Removes a class creation listener.

        .. deprecated:: 6.3.0
        zremove_listener is deprecatedrH   )r   N)r   r   r   r   r   remove)rD   r   rO   r-   r-   r.   remove_listener  s    zMetaHasTraits.remove_listenerN)re   )re   )	r*   r+   r,   __doc__r   r   classmethodr   r   r-   r-   r-   r.   r     s   	r   c       .   	   C   s`  i }i }i }i }g }i }i }	dd |D }
dd |
D }xt |j D ]\}}t|}t|t}| rt|trd}t|d| }t|d| }|dkr|dk	rt|dd	rtj	}nt|d
d	rtj
}t|d| }|dkr|j}t|||d|jf|j}|r||= |d'd dkr| ||< ||< |j}|dkr|j}|dk	r|jrt|j |j}|jdkrvd|_|||d < |jrt||||d < nR|dkr|jd	k	rdt||f||< n(|dkr|j}t|trd|f||< n|dd( }|j| |||< qHt|r^t|dd}|dk	r>d|f||< t|dd}|dk	r||	|< qHt|trtt||< qHt|tr|||< ||= qHxR|D ]J}||kr|| }|jt krt!d|j|f ||||< ||= P qW qHW i }x|
D ]}|j}x8|j"t#j D ]&\}}||kr||kr|||< qW x6|t$ j D ]&\}}||krH||krH||	|< qHW x\|j"t%j D ]J\}}||kr|j&}|dk	rt'|}t(|||| ||< }|||< qW xj|j"t)j D ]X\}}||kr|j&}|dk	r.|j"t'|} | dk	r | }nt(||||}|||< qW |j"t*}!x2|!d D ]&}||krP|j| |!| ||< qPW qW |j"ddkr|jd t+ j, |d< ||d< |j-t.dd t/||
}"t0| ||d}#|#dk	rt1|#}#|#|d< t2 }$x*t |j3 D ]}|| }%|#t0| ||d| t0| ||d| g}&|%j}'|'dk	rT||"ks|'dkr|d)d dkr|dd* |"kr|&jtt|' |%j4}(|(dk	rt|(tr|(g}(x>|(D ]6})|&jt0| ||d|)  |&jt0| ||d|)  qW d d |&D }&t0| |g d!| }*t.|&d"ks,|*dk	r||$krP|$j5| t|% ||< }%t.|&d"krnt6|%j7d|& |*dk	r|%j8t9j:|* |%jd#kr|%j;dk	r|%j<}+|+dkrt=| }+|%j;},t|,t>rd$j?|,},nd%|, },d#|+|,f||< |%jd#kr|%j@dk	rtA|%j@||%j<d&}-|-g|	|< qW ||t%< ||t)< |"|tB< ||t*< ||t#< |	|t$< ||tC< dS )+a   Processes all of the traits related data in the class dictionary.

    This is called during the construction of a new HasTraits class. The first
    three parameters have the same interpretation as the corresponding
    parameters of ``type.__new__``. This function modifies ``class_dict``
    in-place.

    Parameters
    ----------
    class_name : str
        The name of the HasTraits class.
    bases : tuple
        The base classes for the HasTraits class.
    class_dict : dict
        A dictionary of class members.
    c             S   s    g | ]}|j jtd k	r|qS )N)r=   rN   ClassTraits).0rR   r-   r-   r.   
<listcomp>  s    z,update_traits_class_dict.<locals>.<listcomp>c             S   s   g | ]}|j jtqS r-   )r=   rN   r   )r   rR   r-   r-   r.   r     s    T_get__set_NsettableF	flushable
_validate_r   rJ   r;   _list_changed_handler_list_items_changed_handler_itemsr6   r5   rK   rE   rL   ziCannot specify a default value for the %s trait '%s'. You must override the the trait definition instead.rq   re   )ro   reverseZ_anytrait_changed@z_%s_changedz	_%s_fired   c             S   s   g | ]}|d k	r|qS )Nr-   )r   hr-   r-   r.   r     s    z_%s_defaultr   r8   , )r   r   r   rr   rr   ii)DrX   r\   r&   rW   r   r   r   rB   r]   _set_traits_cache_flush_traits_cachevalidater   r   r@   r   	has_itemsrA   items_eventr=   instance_handler	is_mappedr'   Z_listenablerv   rK   r   rg   rC   r8   r   r)   CantHaveDefaultValuer#   rN   ListenerTraitsObserverTraits
BaseTraitsZproperty_fieldsidmigrate_propertyr   PrefixTraitsr   	as_ctraitsortrt   rp   rS   r   setkeysr5   addr   
_notifiersZset_default_valuer   callable
depends_onr   r   r   joinr   r   rf   
ViewTraits).rO   rQ   rP   Zbase_traitsclass_traitsprefix_traits	listenersprefix_listview_elementsZ	observershastraits_basesZinherited_class_traitsrb   r`   rcgettersetterr   Z
value_typer   Zitems_traitrK   patternZobserver_statesctZictraitZmigrated_propertiesrR   Z	base_dictstatesproperty_inforo   Z	new_valueZbase_prefix_traitsrj   anytraitZclonedr;   r~   r   r   r5   defaultr   r   Zobserver_stater-   r-   r.   r     s^   


































r   c       
      C   sp   t |d|  }t |d|  }t |d|  }|dk	sB|dk	sB|dk	rl|\}}}	t|pT||pZ||p`|	df|jS |S )zc Migrates an existing property to the class being defined
    (allowing for method overrides).
    r   r   r   NT)r   r   r=   )
rb   r8   r   rP   rN   r   valZold_getZold_setZold_valr-   r-   r.   r     s    
r   Fr9   )r   r   c               s   t |  fdd}|S )a   Marks the wrapped method as being a handler to be called when the
    specified traits change.

    This decorator can be stacked, e.g.::

        @observe("attr1")
        @observe("attr2", post_init=True)
        def updated(self, event):
            ...

    The decorated function must accept one argument which is the event object
    representing the change. See :mod:`traits.observation.events` for details.

    Parameters
    ----------
    expression : str or list or ObserverExpression
        A description of what traits are being observed.
        If this is a list, each item must be a string or Expression.
        See :py:func:`HasTraits.observe` for details on the
        semantics when passing a string.
    post_init : boolean, optional
        Whether the change handler should be attached after
        the state is set when instantiating an object. Default is false, and
        values provided to the instance constructor will trigger the
        change handler to fire if the value is different from the
        default. Set to true to avoid this change event.
    dispatch : str, optional
        A string indicating how the handler should be run. Default is to run
        it on the same thread where the change occurs.
        Possible values are:

        =========== =======================================================
        value       dispatch
        =========== =======================================================
        ``same``    Run notifications on the same thread where the change
                    occurs. The notifications are executed immediately.
        ``ui``      Run notifications on the UI thread. If the current
                    thread is the UI thread, the notifications are executed
                    immediately; otherwise, they are placed on the UI
                    event queue.
        =========== =======================================================

    See Also
    --------
    HasTraits.observe
    c                s   t j| }y|jdd W n$ tk
r>   tjdtdd Y nX y
| j}W n tk
rh   g }|| _Y nX t	 t
d}|j| | S )a   Create input arguments for HasTraits.observe and attach the input
        to the callable.

        The metaclass will then collect this information for calling
        HasTraits.observe with the decorated function.

        Parameters
        ----------
        handler : callable
            Method of a subclass of HasTraits, with signature of the form
            ``my_method(self, event)``.
        rx   r5   zDubious signature for observe-decorated method. The decorated method should be callable with a single positional argument in addition to 'self'. Did you forget to add an 'event' parameter?rH   )r   )r   r   r   r   )rT   	signaturebind	TypeErrorr   r   UserWarningrL   AttributeErrorr[   rB   rg   )r   Zhandler_signatureZobserve_inputsZobserve_input)r   r   r   r-   r.   observe_decoratorA  s(    


z"observe.<locals>.observe_decorator)r   )r   r   r   r   r-   )r   r   r   r.   r     s    0.r   c                s    fdd}|S )a0   Marks the following method definition as being a handler for the
        extended trait change specified by *name(s)*.

        Refer to the documentation for the on_trait_change() method of
        the **HasTraits** class for information on the correct syntax for
        the *name* argument and the semantics of the *dispatch* keyword
        argument.

        A handler defined using this decorator is normally effective
        immediately. However, if *post_init* is **True**, then the handler only
        becomes effective after all object constructor arguments have been
        processed. That is, trait values assigned as part of object
        construction will not cause the handler to be invoked.

        See Also
        --------
        observe : A newer API for defining traits notifications.
    c                s    d| _ | S )N)r   r   r   )rK   )function)r   rb   r   r-   r.   	decorator  s    
z"on_trait_change.<locals>.decoratorr-   )rb   r   r   r   r-   )r   rb   r   r.   rK   r  s    
rK   c                s*   t  jdd   fdd}d|_|S )a   Marks the following method definition as being a "cached property".
        That is, it is a property getter which, for performance reasons, caches
        its most recently computed result in an attribute whose name is of the
        form: *_traits_cache_name*, where *name* is the name of the property. A
        method marked as being a cached property needs only to compute and
        return its result. The @cached_property decorator automatically wraps
        the decorated method in cache management code, eliminating the need to
        write boilerplate cache management code explicitly. For example::

            file_name = File
            file_contents = Property(observe='file_name')

            @cached_property
            def _get_file_contents(self):
                with open(self.file_name, 'rb') as fh:
                    return fh.read()

        In this example, accessing the *file_contents* trait calls the
        _get_file_contents() method only once each time after the **file_name**
        trait is modified. In all other cases, the cached value
        **_file_contents**, which maintained by the @cached_property wrapper
        code, is returned.

        Note the use, in the example, of the **observe** metadata attribute
        to specify that the value of **file_contents** depends on
        **file_name**, so that _get_file_contents() is called only when
        **file_name** changes. For details, see the traits.traits.Property()
        function.
       Nc                s,   | j jt}|tkr( |  | j < }|S )N)r=   rN   r   )rx   rF   )r   rb   r-   r.   r     s    z"cached_property.<locals>.decoratorT)r   r*   cached_property)r   r   r-   )r   rb   r.   r     s    r   c                s    fdd}|S )at   Marks the following method definition as being a "cached property"
        that depends on the specified extended trait names. That is, it is a
        property getter which, for performance reasons, caches its most
        recently computed result in an attribute whose name is of the form:
        *_traits_cache_name*, where *name* is the name of the property. A
        method marked as being a cached property needs only to compute and
        return its result. The @property_depends_on decorator automatically
        wraps the decorated method in cache management code that will cache the
        most recently computed value and flush the cache when any of the
        specified dependencies are modified, thus eliminating the need to write
        boilerplate cache management code explicitly. For example::

            file_name = File
            file_contents = Property

            @property_depends_on( 'file_name' )
            def _get_file_contents(self):
                with open(self.file_name, 'rb') as fh:
                    return fh.read()

        In this example, accessing the *file_contents* trait calls the
        _get_file_contents() method only once each time after the **file_name**
        trait is modified. In all other cases, the cached value
        **_file_contents**, which is maintained by the @cached_property wrapper
        code, is returned.
    c                s<   t  jdd    fdd}d|_|_|_|_|S )Nr   c                s,   | j jt}|tkr( |  | j < }|S )N)r=   rN   r   )rx   rF   )r   rb   r-   r.   wrapper  s    z7property_depends_on.<locals>.decorator.<locals>.wrapperT)r   r*   r   r   r   r   )r   r   )
dependencyr   r   )r   rb   r.   r     s    z&property_depends_on.<locals>.decoratorr-   )r   r   r   r   r-   )r   r   r   r.   property_depends_on  s    r   c                s   t j|   fdd}|S )z Create a weak reference to arg and wrap the function so that the
    dereferenced weakref is passed as the first argument. If arg has been
    deleted then the function is not called.
    c                s    fdd} fdd} fdd} fdd} fd	d
} fdd} j jd }|dkrl|S |dkrx|S |dkr|S |dkr|S |dkr|S |S d S )Nc                 s    } | d k	r | S d S )Nr-   )arg)r   weak_argr-   r.   wrapper0  s    z-weak_arg.<locals>.decorator.<locals>.wrapper0c                s    }|d k	r || S d S )Nr-   )arg1r   )r   r   r-   r.   wrapper1   s    z-weak_arg.<locals>.decorator.<locals>.wrapper1c                s    }|d k	r || |S d S )Nr-   )r   arg2r   )r   r   r-   r.   wrapper2  s    z-weak_arg.<locals>.decorator.<locals>.wrapper2c                s     }|d k	r || ||S d S )Nr-   )r   r   arg3r   )r   r   r-   r.   wrapper3
  s    z-weak_arg.<locals>.decorator.<locals>.wrapper3c                s"    }|d k	r || |||S d S )Nr-   )r   r   r   Zarg4r   )r   r   r-   r.   wrapper4  s    z-weak_arg.<locals>.decorator.<locals>.wrapper4c                 s     }|d k	r |f|   d S )Nr-   )argsr   )r   r   r-   r.   wrappern  s    z-weak_arg.<locals>.decorator.<locals>.wrappernr   r   rH         )__code__co_argcount)r   r   r   r   r   r   r   r   )r   )r   r.   r     s$    zweak_arg.<locals>.decorator)weakrefref)r   r   r-   )r   r.   r     s    
1r   c                   s8  e Zd ZdZedddZeeee	e	dZ
ee Ze Zdd Zedd Zed	d
 ZedddZedddZedd Zdd Zdd Zdd ZdddZdd Zeddd Zeje_ddd Zed!dd"d#Zeje_d$d% Zdd'd(Z d)d* Z!d+d, Z" fd-d.Z#dd/d0Z$dd1d2Z%d3d4 Z&dd6d7Z'd8d9 Z(dd:d;Z)edd<d=Z*ed>d? Z+d@dA Z,edBdC Z-ddDdEZ.dFdG Z/edHdI Z0edJdK Z1ddLdMZ2dNdO Z3edPdQ Z4dRdS Z5edTdU Z6ddVdWZ7ddYdZZ8ddXd[d\d]Z9dd^d_Z:e:Z;dd`daZ<dbdc Z=ddde Z>dfdg Z?dhdi Z@djdk ZAdldm ZBddndoZCdpdq ZDdrds ZEdtdu ZFedvdw ZGdxdy ZHedzd{ ZId|d} ZJd~d ZKdd ZLdddZMdddZNdd ZOdd ZPdd ZQdd ZRdd ZSdd ZTdd ZUdd ZVdd ZWdd ZXdd ZYdd ZZdd Z[dd Z\dd Z]dd Z^  Z_S )r]   a   Enables any Python class derived from it to have trait attributes.

    Most of the methods of HasTraits operated by default only on the trait
    attributes explicitly defined in the class definition. They do not operate
    on trait attributes defined by way of wildcards or by calling
    **add_trait()**.
    For example::

        >>> class Person(HasTraits):
        ...     name = Str
        ...     age  = Int
        ...     temp_ = Any
        >>> bob = Person()
        >>> bob.temp_lunch = 'sandwich'
        >>> bob.add_trait('favorite_sport', Str('football'))
        >>> print(bob.trait_names())
        ['trait_added', 'age', 'name']

    In this example, the trait_names() method returns only the *age* and
    *name* attributes defined on the Person class. (The **trait_added**
    attribute is an explicit trait event defined on the HasTraits class.)
    The wildcard attribute *temp_lunch* and the dynamically-added trait
    attribute *favorite_sport* are not listed.

    Subclass should avoid defining new traits and/or methods with names
    starting with "trait" or "_trait" to avoid overshadowing existing methods,
    unless it has been documented as being safe to do so.
    T)private	transient)r9   extendednewZfast_uir:   c             C   s<   | j |}|jdkr8|dd dkr8| j|dt|| dS )z4 Handles a 'trait_added' event being fired.
        r6   r   Nr   i)r;   r   _init_trait_delegate_listenerrv   )rx   rb   r;   r-   r-   r.   _trait_added_changedc  s    
zHasTraits._trait_added_changedc             G   sn   t |dkrtdt |dkr*t| }nt|d }| j||dd x"| jdD ]}|j||dd qRW dS )a   Adds a named trait attribute to this class.

        Also adds the same attribute to all subclasses.

        Parameters
        ----------
        name : str
            Name of the attribute to add.
        *trait :
            A trait or a value that can be converted to a trait using Trait()
            Trait definition of the attribute. It can be a single value or
            a list equivalent to an argument list for the Trait() function.

        r   z"No trait definition was specified.r   F)is_subclassTN)rt   
ValueErrorr   r(   _add_class_traittrait_subclasses)rD   rb   r;   subclassr-   r-   r.   add_class_traitp  s    
zHasTraits.add_class_traitc       
      C   sx  | j }|t }|dd dkrr|dd }||krF|r:dS td| |||< |d }|j| |jtdd dS |t }|j|dk	r|rdS td| |j}|dk	r|j	r| j
|d	 |j |d
 |jr| j
|d t|||d
 |jdk	r ||t |< t| d| t| d| g}	t|| |	 |	j|jd dd |	D }	t|	dkrlt|}t|jd|	 |||< dS )aB  
        Add a named trait attribute to this class.

        Does not affect subclasses.

        Parameters
        ----------
        name : str
            Name of the attribute to add.
        trait : CTrait
            The trait to be added.
        is_subclass : bool
            True if we're adding the trait to a strict subclass of the
            original class that add_class_trait was called for. This is used
            to decide how to behave if ``cls`` already has a trait named
            ``name``: in that circumstance, if ``is_subclass`` is False, an
            error will be raised, while if ``is_subclass`` is True, no trait
            will be added.

        Raises
        ------
        TraitError
            If a trait with the given name already exists, and is_subclass
            is ``False``.
        r   NrJ   z#The '%s_' trait is already defined.rq   T)ro   r   z"The '%s' trait is already defined.r   )r  Fz_%s_changedz	_%s_firedr   c             S   s   g | ]}|d k	r|qS )Nr-   )r   r   r-   r-   r.   r     s    z.HasTraits._add_class_trait.<locals>.<listcomp>r   rr   rr   )r=   r   r#   rg   r   rt   r   rN   r   r   r  r   r   r'   is_baser   rG   r   rA   r   r   )
rD   rb   r;   r  rP   r   r   r   r   r~   r-   r-   r.   r    sR    
zHasTraits._add_class_traitFc             C   s^   y8t |tr6| r(|| jkr(td| || j|< dS W n tk
rL   Y nX td| dS )z5 Sets a trait notification dispatch handler.
        z8A dispatch handler called '%s' has already been defined.Nz1%s is not a subclass of TraitChangeNotifyWrapper.)
issubclassr   wrappersr#   r   )rD   rb   r   overrider-   r-   r.   set_trait_dispatch_handler  s    

z$HasTraits.set_trait_dispatch_handlerc             C   s   |s| j  S | jg S )a   Returns a list of the immediate (or all) subclasses of this class.

        Parameters
        ----------
        all : bool
            Indicates whether to return all subclasses of this class. If
            False, only immediate subclasses are returned.

        )__subclasses___trait_subclasses)rD   allr-   r-   r.   r	  	  s    zHasTraits.trait_subclassesc             C   s2   x,| j  D ] }||kr
|j| |j| q
W |S )N)r  rg   r  )rD   Z
subclassesr
  r-   r-   r.   r    s
    
zHasTraits._trait_subclassesc             G   s
   t | |S )ak  Returns whether the object implements a specified traits interface.

        Tests whether the object implements one or more of the interfaces
        specified by *interfaces*. Return **True** if it does, and **False**
        otherwise.

        Parameters
        ----------
        *interfaces :
            One or more traits Interface (sub)classes.
        )rW   )rx   Z
interfacesr-   r-   r.   r^      s    zHasTraits.has_traits_interfacec                s   | j td}| j |jt fdd| jdddD  | jtrvx2|j D ]&\}}t	|sLt
d|| jj|f qLW |jdt |S )	ao   Returns a dictionary of traits to pickle.

        In general, avoid overriding __getstate__ in subclasses. Instead, mark
        traits that should not be pickled with 'transient = True' metadata.

        In cases where this strategy is not sufficient, override __getstate__
        in subclasses using the following pattern to remove items that should
        not be persisted::

            def __getstate__(self):
                state = super().__getstate__()
                for key in ['foo', 'bar']:
                    if key in state:
                        del state[key]
                return state
        )r  c                s    g | ]}| kr| | fqS r-   r-   )r   rb   )dicr-   r.   r   H  s   z*HasTraits.__getstate__.<locals>.<listcomp>r6   F)r   r  zGThe '%s' trait of a '%s' instance contains the unserializable value: %s__traits_version__)	trait_getr    r=   r?   r[   trait_namesr^   r_   r\   rZ   r#   	__class__r*   ri   TraitsVersion)rx   rF   rb   r`   r-   )r  r.   __getstate__.  s    


zHasTraits.__getstate__c             C   s   t | jf| j fS )N)r	   r  r  )rx   protocolr-   r-   r.   __reduce_ex__c  s    zHasTraits.__reduce_ex__c                s   |j   dddkrR fdd dg D }| jj| | jf d|it| n<| j  | j  | jf d|i| | j  | j  | j	  | j
  dS )z= Restores the previously pickled state of an object.
        r  Nc                s   g | ]}| |fqS r-   r-   )r   rb   )r   r-   r.   r   n  s    z*HasTraits.__setstate__.<locals>.<listcomp>Z__HasTraits_restore__trait_change_notify)r   r=   r?   	trait_setr[   _init_trait_listeners_init_trait_observers_post_init_trait_listeners_post_init_trait_observerstraits_init_trait_set_inited)rx   stater  valuesr-   )r   r.   __setstate__f  s    zHasTraits.__setstate__c             O   sv   i }t |}|dkr.t|d tkr.|d }n|dkrB| jf |}t }x(|D ] }t| ||}||k	rN|||< qNW |S )aV   Retrieve trait values for one or more traits.

        This function can be called in one of three ways. In the first form,
        the user passes the names of one or more traits to be retrieved::

            my_object.trait_get("trait_name1", "trait_name2")

        In the second form, the user passes a list of zero or more names of
        traits::

            my_object.trait_get(["trait_name1", "trait_name2"])

        In the final form, no trait names are passed, and all trait names
        and trait values are returned, subject to the given metadata filters::

            my_object.trait_get(transient=True, frombicated=False)

        In all cases, a dictionary mapping trait names to trait values is
        returned.

        For the first two forms, if any name does not correspond to a defined
        trait, it is not included in the result.

        Parameters
        ----------
        *names
            Names of the traits to look up, or a single positional argument
            providing a sequence of trait names.
        **metadata
            Metadata information used to filter the traits to return. This
            information is used only when no names are provided.

        Returns
        -------
        result : dict
            A dictionary mapping the selected trait names to their
            corresponding values.
        r   r   )rt   r   r   r  objectrB   )rx   namesr@   rF   rm   missingrb   r`   r-   r-   r.   r    s    (

zHasTraits.trait_getz!use "HasTraits.trait_get" insteadc             O   s   | j ||S )N)r  )rx   r)  r@   r-   r-   r.   rN     s    zHasTraits.getc             K   sj   |sD| j d z&x |j D ]\}}t| || qW W d| j d X n"x |j D ]\}}t| || qNW | S )a7   Shortcut for setting object trait attributes.

        Treats each keyword argument to the method as the name of a trait
        attribute and sets the corresponding trait attribute to the value
        specified. This is a useful shorthand when a number of trait attributes
        need to be set on an object, or a trait attribute value needs to be set
        in a lambda function. For example, you can write::

            person.trait_set(name='Bill', age=27)

        instead of::

            person.name = 'Bill'
            person.age = 27

        Parameters
        ----------
        trait_change_notify : bool
            If **True** (the default), then each value assigned may generate a
            trait change notification. If **False**, then no trait change
            notifications will be generated. (see also: trait_setq)
        **traits :
            Key/value pairs, the trait attributes and their values to be
            set

        Returns
        -------
        self :
            The method returns this object, after setting attributes.
        FNT)Z_trait_change_notifyr\   setattr)rx   r  traitsrb   r`   r-   r-   r.   r    s    
zHasTraits.trait_setz!use "HasTraits.trait_set" insteadc             K   s   | j f d|i|S )Nr  )r  )rx   r  r,  r-   r-   r.   r     s    zHasTraits.setc             K   s   | j f ddi|S )a   Shortcut for setting object trait attributes.

        Treats each keyword argument to the method as the name of a trait
        attribute and sets the corresponding trait attribute to the value
        specified. This is a useful shorthand when a number of trait attributes
        need to be set on an object, or a trait attribute value needs to be set
        in a lambda function. For example, you can write::

            person.trait_setq(name='Bill', age=27)

        instead of::

            person.name = 'Bill'
            person.age = 27

        Parameters
        ----------
        **traits :
            Key/value pairs, the trait attributes and their values to be set.
            No trait change notifications will be generated for any values
            assigned (see also: trait_set).

        Returns
        -------
        self :
            The method returns this object, after setting attributes.
        r  F)r  )rx   r,  r-   r-   r.   
trait_setq  s    zHasTraits.trait_setqNc             K   s\   g }|dkr| j f |}x>|D ]6}yt| | W q ttfk
rR   |j| Y qX qW |S )aK   Resets some or all of an object's trait attributes to their default
        values.

        Resets each of the traits whose names are specified in the *traits*
        list to their default values. If *traits* is None or omitted, the
        method resets all explicitly-defined object trait attributes to their
        default values. Note that this does not affect wildcard trait
        attributes or trait attributes added via add_trait(), unless they are
        explicitly named in *traits*.

        Parameters
        ----------
        traits : list of strings
            Names of trait attributes to reset.

        Returns
        -------
        unresetable : list of strings
            A list of attributes that the method was unable to reset, which is
            empty if all the attributes were successfully reset.
        N)r  delattrr   r#   rg   )rx   r,  r@   Zunresetablerb   r-   r-   r.   reset_traits  s    
zHasTraits.reset_traitsc             K   s   |j ddd  | jf |S )zF Returns the list of trait names to copy or clone by default.
        r  c             S   s   | dk	S )NTr-   )tr-   r-   r.   <lambda>8  s    z0HasTraits.copyable_trait_names.<locals>.<lambda>)ri   r  )rx   r@   r-   r-   r.   copyable_trait_names4  s    zHasTraits.copyable_trait_namesc             C   s   t | jj S )z_ Returns the list of all trait names, including implicitly defined
            traits.
        )rX   r0   r   )rx   r-   r-   r.   all_trait_names;  s    zHasTraits.all_trait_namesc                s   t  j | j  S )z Returns the list of trait names when calling the dir() builtin on
            the object. This enables tab-completion in IPython.
        )super__dir__r  )rx   )r  r-   r.   r5  A  s    zHasTraits.__dir__c             K   s  |dkr| j f |}n,|dks*t|dkrB| j }|dk	rBd|d< g }g }|dk}|dk}	x|D ]}
y| j|
}|jtkr|j|
 w`|j|
}|jdkrw`t||
}|j	}|dkrt
j	|}nH|dkrn>|dks|r|dkrt
j|}nt
j||}n|	rt
j	|}t| |
| W q`   |j|
 Y q`X q`W x|D ]}
yt||
}|j|
j	}|dkrjt
j	|}nP|dkrvnD|dks|r|dkrt
j|}nt
j||}n|	rt
j	|}t| |
| W n   |j|
 Y nX q8W |S )	a   Copies another object's trait attributes into this one.

        Parameters
        ----------
        other : object
            The object whose trait attribute values should be copied.
        traits : list of strings
            A list of names of trait attributes to copy. If None or
            unspecified, the set of names returned by trait_names() is used.
            If 'all' or an empty list, the set of names returned by
            all_trait_names() is used.
        memo : dict
            A dictionary of objects that have already been copied.
        copy : None | 'deep' | 'shallow'
            The type of copy to perform on any trait that does not have
            explicit 'copy' metadata. A value of None means 'copy reference'.

        Returns
        -------
        unassignable : list of strings
            A list of attributes that the method was unable to copy, which is
            empty if all the attributes were successfully copied.

        Nr  r   traits_to_copydeepZshallowr5   r   )r2  rt   r3  r;   r   DeferredCopyrg   
base_traitrB   r>   copy_moduledeepcopyr+  )rx   otherr,  memor>   r@   ZunassignabledeferredZ	deep_copyZshallow_copyrb   r;   r9  r`   Z	copy_typer-   r-   r.   copy_traitsG  sh    













zHasTraits.copy_traitsc             K   s   |dkri }|dkr"| j f |}n$|dks6t|dkrF| j }d|d< ||d< | j| j}||t| < |j  |j  |j| |||f| |j	  |j
  |j  |j  |S )a   Clones a new object from this one, optionally copying only a
        specified set of traits.

        Creates a new object that is a clone of the current object. If *traits*
        is None (the default), then all explicit trait attributes defined
        for this object are cloned. If *traits* is 'all' or an empty list, the
        list of traits returned by all_trait_names() is used; otherwise,
        *traits* must be a list of the names of the trait attributes to be
        cloned.

        Parameters
        ----------
        traits : list of strings
            The list of names of the trait attributes to copy.
        memo : dict
            A dictionary of objects that have already been copied.
        copy : str
            The type of copy ``deep`` or ``shallow`` to perform on any trait
            that does not have explicit 'copy' metadata. A value of None means
            'copy reference'.

        Returns
        -------
        new :
            The newly cloned object.
        Nr  r   r6  traits_copy_mode)r2  rt   r3  r   r  r   r  r   r?  r!  r"  r#  r$  )rx   r,  r=  r>   r@   r  r-   r-   r.   clone_traits  s$    zHasTraits.clone_traitsc             C   s   | j ||jd|jddS )z, Creates a deep copy of the object.
        r6  r@  )r=  r,  r>   )rA  rN   )rx   r=  r-   r-   r.   __deepcopy__  s    zHasTraits.__deepcopy__re   c       	   	   K   s2   |dkr| }| j |}|j|||| j ||||S )aM   Displays a user interface window for editing trait attribute
        values.

        Parameters
        ----------
        view : View or string
            A View object (or its name) that defines a user interface for
            editing trait attribute values of the current object. If the view
            is defined as an attribute on this class, use the name of the
            attribute. Otherwise, use a reference to the view object. If this
            attribute is not specified, the View object returned by
            trait_view() is used.
        parent : toolkit control
            The reference to a user interface component to use as the parent
            window for the object's UI window.
        kind : str
            The type of user interface window to create. See the
            **traitsui.view.kind_trait** trait for values and
            their meanings. If *kind* is unspecified or None, the **kind**
            attribute of the View object is used.
        context : object or dictionary
            A single object or a dictionary of string/object pairs, whose trait
            attributes are to be edited. If not specified, the current object
            is used.
        handler : Handler
            A handler object used for event handling in the dialog box. If
            None, the default handler for Traits UI is used.
        id : str
            A unique ID for persisting preferences about this user interface,
            such as size and position. If not specified, no user preferences
            are saved.
        scrollable : bool
            Indicates whether the dialog box should be scrollable. When set to
            True, scroll bars appear on the dialog box if it is not large
            enough to display all of the items in the view at one time.

        Returns
        -------
        A UI object.
        N)
trait_viewr:   trait_view_elements)	rx   viewparentkindcontextr   r   
scrollabler   r-   r-   r.   edit_traits  s    3
zHasTraits.edit_traitsc             C   s   d| iS )z[ Returns the default context to use for editing or configuring
            traits.
        r(  r-   )rx   r-   r-   r.   trait_context  s    zHasTraits.trait_contextc             C   s   | j j||| j| j| j| S )a   Gets or sets a ViewElement associated with an object's class.

        If both *name* and *view_element* are specified, the view element is
        associated with *name* for the current object's class. (That is,
        *view_element* is added to the ViewElements object associated with
        the current object's class, indexed by *name*.)

        If only *name* is specified, the function returns the view element
        object associated with *name*, or None if *name* has no associated
        view element. View elements retrieved by this function are those that
        are bound to a class attribute in the class definition, or that are
        associated with a name by a previous call to this method.

        If neither *name* nor *view_element* is specified, the method returns a
        View object, based on the following order of preference:

        1. If there is a View object named ``traits_view`` associated with the
           current object, it is returned.
        2. If there is exactly one View object associated the current
           object, it is returned.
        3. Otherwise, it returns a View object containing items for all the
           non-event trait attributes on the current object.

        Parameters
        ----------
        name : str
            Name of a view element
        view_element : ViewElement
            View element to associate

        Returns
        -------
        A view element.
        )r  _trait_viewdefault_traits_viewrD  visible_traits)rx   rb   view_elementr-   r-   r.   rC  %  s    #zHasTraits.trait_viewc             C   s   | j ||| j| j| jd S )N)rL  class_default_traits_viewclass_trait_view_elementsclass_visible_traits)rD   rb   rO  r-   r-   r.   class_trait_viewQ  s    zHasTraits.class_trait_viewc             C   s  t |tr|S | }|dkr dS td |rz|dkrl|j|}|dkrh|dk	rht||d}t|rh| }|S ||j|< dS | }t |tr|S |j }	||	kr|j|S |dk	rt||d}t|r| }t |tr|S t|	dkr|j|	d S ddl	m
}
 |
| ddgdS )	zG Gets or sets a ViewElement associated with an object's class.
        N   r   r   )ViewOKZCancel)Zbuttons)rW   r)   r%   rh   rB   r   content	filter_byrt   traitsui.apirU  )rD   rb   rO  default_namer   Ztrait_selector_fr   rF   rE   r)  rU  r-   r-   r.   rL  \  s@    





zHasTraits._trait_viewc             C   s
   | j j S )zM Returns the name of the default traits view for the object's class.
        )r  rP  )rx   r-   r-   r.   rM    s    zHasTraits.default_traits_viewc             C   s   t S )zD Returns the name of the default traits view for the class.
        )DefaultTraitsView)rD   r-   r-   r.   rP    s    z#HasTraits.class_default_traits_viewc             C   s(   | j jt }t|tr| j }|j|S )a7   Returns a list of the names of all view elements associated with
        the current object's class.

        If *klass* is specified, the list of names is filtered such that only
        objects that are instances of the specified class are returned.

        Parameters
        ----------
        klass : class
            A class, such that all returned names must correspond to instances
            of this class. Possible values include:

            * Group
            * Item
            * View
            * ViewElement
            * ViewSubElement
        )r  r=   r   rW   r[   _init_trait_view_elementsrX  )rx   r   r   r-   r-   r.   trait_views  s    
zHasTraits.trait_viewsc             C   s
   | j j S )z Returns the ViewElements object associated with the object's
        class.

        The returned object can be used to access all the view elements
        associated with the class.
        )r  rQ  )rx   r-   r-   r.   rD    s    zHasTraits.trait_view_elementsc             C   s    | j t }t|tr| j }|S )z Returns the ViewElements object associated with the class.

        The returned object can be used to access all the view elements
        associated with the class.
        )r=   r   rW   r[   r\  )rD   r   r-   r-   r.   rQ    s    

z#HasTraits.class_trait_view_elementsc       	      C   s   ddl m} dd | jD }| }| jt }x>|j D ]2\}}||jkrTtd| ||j|< |j| q6W x(|D ] }|j	 }|dk	rr|j
j| qrW t| t| |S )z> Lazily Initialize the ViewElements object from a dictionary. r   )ViewElementsc             S   s   g | ]}t |jkr|qS r-   )r   r=   )r   rR   r-   r-   r.   r     s    z7HasTraits._init_trait_view_elements.<locals>.<listcomp>z*Duplicate definition for view element '%s'N)Ztraitsui.view_elementsr^  	__bases__r=   r   r\   rW  r#   Zreplace_includerQ  parentsrg   r+  )	rD   r^  r   r   Zelements_dictrb   elementrR   Zparent_view_elementsr-   r-   r.   r\    s     




z#HasTraits._init_trait_view_elementsc	             K   s   |dk	rNd}
t j|
t tjj|rNt|d}| jtj	|j
  W dQ R X |dkr\d}nd}
t j|
t |rddlm} |dkr| }| j|| j||||||	}|r|dk	rt|d}tj|d	d
j|  W dQ R X |S dS )as  Creates and displays a dialog box for editing values of trait
        attributes, as if it were a complete, self-contained GUI application.

        This method is intended for use in applications that do not normally
        have a GUI. Control does not resume in the calling application until
        the user closes the dialog box.

        The method attempts to open and unpickle the contents of *filename*
        before displaying the dialog box. When editing is complete, the method
        attempts to pickle the updated contents of the object back to
        *filename*. If the file referenced by *filename* does not exist, the
        object is not modified before displaying the dialog box. If *filename*
        is unspecified or None, no pickling or unpickling occurs.

        If *edit* is True (the default), a dialog box for editing the
        current object is displayed. If *edit* is False or None, no
        dialog box is displayed. You can use ``edit=False`` if you want the
        object to be restored from the contents of *filename*, without being
        modified by the user.

        Parameters
        ----------
        filename : str
            The name (including path) of a file that contains a pickled
            representation of the current object. When this parameter is
            specified, the method reads the corresponding file (if it exists)
            to restore the saved values of the object's traits before
            displaying them. If the user confirms the dialog box (by clicking
            **OK**), the new values are written to the file. If this parameter
            is not specified, the values are loaded from the in-memory object,
            and are not persisted when the dialog box is closed.

            .. deprecated:: 6.0.0

        view : View or str
            A View object (or its name) that defines a user interface for
            editing trait attribute values of the current object. If the view
            is defined as an attribute on this class, use the name of the
            attribute. Otherwise, use a reference to the view object. If this
            attribute is not specified, the View object returned by
            trait_view() is used.
        kind : str
            The type of user interface window to create. See the
            **traitsui.view.kind_trait** trait for values and
            their meanings. If *kind* is unspecified or None, the **kind**
            attribute of the View object is used.
        edit : bool
            Indicates whether to display a user interface. If *filename*
            specifies an existing file, setting *edit* to False loads the
            saved values from that file into the object without requiring
            user interaction.

            .. deprecated:: 6.2.0

        context : object or dictionary
            A single object or a dictionary of string/object pairs, whose trait
            attributes are to be edited. If not specified, the current object
            is used
        handler : Handler
            A handler object used for event handling in the dialog box. If
            None, the default handler for Traits UI is used.
        id : str
            A unique ID for persisting preferences about this user interface,
            such as size and position. If not specified, no user preferences
            are saved.
        scrollable : bool
            Indicates whether the dialog box should be scrollable. When set to
            True, scroll bars appear on the dialog box if it is not large
            enough to display all of the items in the view at one time.

        Returns
        -------
        True on success.
        NzFRestoring from pickle will not be supported starting with traits 7.0.0rbTzXThe edit argument to configure_traits is deprecated, and will be removed in Traits 7.0.0r   )toolkitwbr   )r  )r   r   r   ospathexistsopenr?  pickle	UnpicklerloadrY  rc  Zview_applicationrC  Picklerdump)rx   filenamerE  rG  ZeditrH  r   r   rI  r   messagefdrc  r   r-   r-   r.   configure_traits  s6    XzHasTraits.configure_traitsc             C   s   | j ttd}|j  |S )zReturns an alphabetically sorted list of the names of non-event
        trait attributes associated with the current object.
        )r   editable)r  r!   r"   r   )rx   r)  r-   r-   r.   editable_traits  s    zHasTraits.editable_traitsc             C   s   | j ttd}|j  |S )zReturns an alphabetically sorted list of the names of non-event
        trait attributes associated with the current class.
        )r   rr  )class_trait_namesr!   r"   r   )rD   r)  r-   r-   r.   class_editable_traits  s    zHasTraits.class_editable_traitsc             C   s   | j ttdS )zReturns an alphabetically sorted list of the names of non-event
        trait attributes associated with the current object, that should be GUI
        visible
        )r   visible)r  r!   r"   )rx   r-   r-   r.   rN    s    zHasTraits.visible_traitsc             C   s   | j ttdS )zReturns an alphabetically sorted list of the names of non-event
        trait attributes associated with the current class, that should be GUI
        visible
        )r   rv  )rt  r!   r"   )rD   r-   r-   r.   rR    s    zHasTraits.class_visible_traitsc       
      K   s6  t |dkr| jf |}n| jtd}t |dkr>td dS g }tdd |D d }d| }|j  x|D ]}yTtt| |jd	d
}t ||krd|d|d d  ||d d  d f }W n   d}Y nX |d j	|}	|r|j
d|	|| j|jj f  qn|j
d|	|f  qnW td	j| dS )a  Prints the values of all explicitly-defined, non-event trait
        attributes on the current object, in an easily readable format.

        Parameters
        ----------
        show_help : bool
            Indicates whether to display additional descriptive information.
        r   )r   re   Nc             S   s   g | ]}t |qS r-   )rt   )r   xr-   r-   r.   r     s    z*HasTraits.print_traits.<locals>.<listcomp>r   N   
z\nz%s...%srH   r   z<undefined>:z%s %s
   The value must be %s.z%s %s)rt   r  r!   printmaxr   reprrB   replaceljustrg   r9  r   infor   )
rx   Z	show_helpr@   r)  rF   padmaxvalrb   r`   lnamer-   r-   r.   print_traits  s4    


zHasTraits.print_traitsr9   c             C   s$  t |tkr2x |D ]}| j|||||| qW dS |p8d}|r|dkrR| jd}n"| j|d}	|	dkrjdS |	jd}|dk	rx.t|D ]"\}
}|j|r||
= |j  P qW dS |dkr| jd}n| j|djd}xH|D ]}|j|rP qW | j| |||}|r|j	d| n
|j
| dS )aH  Causes the object to invoke a handler whenever a trait attribute
        is modified, or removes the association.

        Multiple handlers can be defined for the same object, or even for the
        same trait attribute on the same object. If *name* is not specified or
        is None, *handler* is invoked when any trait attribute on the
        object is changed.

        Parameters
        ----------
        handler : function
            A trait notification function for the attribute specified by
            *name*.
        name : str
            Specifies the trait attribute whose value changes trigger the
            notification.
        remove : bool
            If True, removes the previously-set association between
            *handler* and *name*; if False (the default), creates the
            association.
        Nr   Fr   TrH   r   )r   rX   _on_trait_changer   _trait	enumerateequalsdisposer  insertrg   )rx   r   rb   r   r   prioritytargetname_ir}   r;   iZnotifierr   r-   r-   r.   r    s<    




zHasTraits._on_trait_change)r   r   c            C   s$   t |}tj| ||t| |d dS )a   Causes the object to invoke a handler whenever a trait attribute
        matching a specified pattern is modified, or removes the association.

        The *expression* parameter can be a single string or an Expression
        object. A list of expressions is also accepted.

        When *expression* is a string, its content should follow Traits Mini
        Language semantics:

        ============================== ======================================
        Expression                       Meaning
        ============================== ======================================
        ``item1.item2``                Observes trait *item2* on the object
                                       under trait *item1*.
                                       Changes to either *item1* or *item2*
                                       cause a notification to be fired.
        ``item1:item2``                Similar to the above, except changes
                                       to *item1* will not fire events
                                       (the ':' indicates no notifications).
        ``[item1, item2, ..., itemN]`` A list which matches any of the
                                       specified items. Each item can itself
                                       be an expression.
        ``items``                      Special keyword for observing a trait
                                       named *items* or items inside a list /
                                       dict / set.
        ``+metadata_name``             Matches any trait on the object having
                                       *metadata_name* metadata.
        ============================== ======================================

        All spaces will be ignored.

        The :py:class:`ObserverExpression` object supports
        the above features and more.

        Parameters
        ----------
        handler : callable(event)
            A callable that will be invoked when the observed trait changes.
            It must accept one argument, which is an event object providing
            information about the change.
            See :py:mod:`traits.observation.events` for details.
        expression : str or list or ObserverExpression
            A description of what traits are being observed.
            If this is a list, each item must be a string or an Expression.
        remove : boolean, optional
            Whether to remove the event handler. Default is to add the event
            handler.
        dispatch : str, optional
            A string indicating how the handler should be run.
            Default is to run on the same thread where the change occurs.

            Possible values are:

            =========== =======================================================
            value       dispatch
            =========== =======================================================
            ``same``    Run notifications on the same thread where the change
                        occurs. The notifications are executed immediately.
            ``ui``      Run notifications on the UI thread. If the current
                        thread is the UI thread, the notifications are executed
                        immediately; otherwise, they are placed on the UI
                        event queue.
            =========== =======================================================

        Raises
        ------
        NotifierNotFound
            When attempting to remove a handler that doesn't exist.
        )r(  r   r   
dispatcherr   N)r   r   apply_observers_ObserverDispatchers)rx   r   r   r   r   r   r-   r-   r.   r   	  s    FzHasTraits.observec          
   C   s  t |trtj|dks |dkr8| j|||||| dS ddlm}m}	m}
m	} t |t
rx$|D ]}| j|||||||d q`W dS |pdj }|r(| jj|}|dk	r|j|}|dk	rxt|D ]X\}}|j|r||= t|dkr||= t|dkr| j|= |jj|  |j  P qW n| jj|i }|j|g }xj|D ]}|j|rHP qHW ||| |d|}|	||
|tj|||||jdj}||_|j|  |j| dS )a4-  Causes the object to invoke a handler whenever a trait attribute
        matching a specified pattern is modified, or removes the association.

        Multiple handlers can be defined for the same object, or even for the
        same trait attribute on the same object. If *name* is not specified or
        is None, *handler* is invoked when any trait attribute on the
        object is changed.

        The *name* parameter is a single *xname* or a list of *xname* names,
        where an *xname* is an extended name of the form::

            xname2[('.'|':') xname2]*

        An *xname2* is of the form::

            ( xname3 | '['xname3[','xname3]*']' ) ['*']

        An *xname3* is of the form::

             xname | ['+'|'-'][name] | name['?' | ('+'|'-')[name]]

        A *name* is any valid Python attribute name. The semantic meaning of
        this notation is as follows:

        ================================ ======================================
        expression                       meaning
        ================================ ======================================
        ``item1.item2``                  means *item1* is a trait containing an
                                         object (or objects if *item1* is a
                                         list or dict) with a trait called
                                         *item2*. Changes to either *item1* or
                                         *item2* cause a notification to be
                                         generated.
        ``item1:item2``                  means *item1* is a trait containing an
                                         object (or objects if *item1* is a
                                         list or dict) with a trait called
                                         *item2*. Changes to *item2* cause a
                                         notification to be generated, while
                                         changes to *item1* do not (i.e., the
                                         ':' indicates that changes to the
                                         *link* object should not be reported).
        ``[ item1, item2, ..., itemN ]`` A list which matches any of the
                                         specified items. Note that at the
                                         topmost level, the surrounding square
                                         brackets are optional.
        ``name?``                        If the current object does not have an
                                         attribute called *name*, the reference
                                         can be ignored. If the '?' character
                                         is omitted, the current object must
                                         have a trait called *name*, otherwise
                                         an exception will be raised.
        ``prefix+``                      Matches any trait on the object whose
                                         name begins with *prefix*.
        ``+metadata_name``               Matches any trait on the object having
                                         *metadata_name* metadata.
        ``-metadata_name``               Matches any trait on the object which
                                         does not have *metadata_name*
                                         metadata.
        ``prefix+metadata_name``         Matches any trait on the object whose
                                         name begins with *prefix* and which
                                         has *metadata_name* metadata.
        ``prefix-metadata_name``         Matches any trait on the object
                                         whose name begins with *prefix* and
                                         which does not have *metadata_name*
                                         metadata.
        ``+``                            Matches all traits on the object.
        ``pattern*``                     Matches object graphs where *pattern*
                                         occurs one or more times (useful for
                                         setting up listeners on recursive data
                                         structures like trees or linked
                                         lists).
        ================================ ======================================

        Some examples of valid names and their meaning are as follows:

        ======================= ===============================================
        example                 meaning
        ======================= ===============================================
        ``foo,bar,baz``         Listen for trait changes to *object.foo*,
                                *object.bar*, and *object.baz*.
        ``['foo','bar','baz']`` Equivalent to 'foo,bar,baz', but may be more
                                useful in cases where the individual items are
                                computed.
        ``foo.bar.baz``         Listen for trait changes to
                                *object.foo.bar.baz* and report changes to
                                *object.foo*, *object.foo.bar* or
                                *object.foo.bar.baz*.
        ``foo:bar:baz``         Listen for changes to *object.foo.bar.baz*, and
                                only report changes to *object.foo.bar.baz*.
        ``foo.[bar,baz]``       Listen for trait changes to *object.foo.bar*
                                and *object.foo.baz*.
        ``[left,right]*.name``  Listen for trait changes to the *name* trait of
                                each node of a tree having *left* and *right*
                                links to other tree nodes, and where *object*
                                the method is applied to the root node of the
                                tree.
        ``+dirty``              Listen for trait changes on any trait in the
                                *object* which has the 'dirty' metadata set.
        ``foo.+dirty``          Listen for trait changes on any trait in
                                *object.foo* which has the 'dirty' metadata
                                set.
        ``foo.[bar,-dirty]``    Listen for trait changes on *object.foo.bar* or
                                any trait on *object.foo* which does not have
                                'dirty' metadata set.
        ======================= ===============================================


        Note that any of the intermediate (i.e., non-final) links in a
        pattern can be traits of type Instance, List or Dict. In the case
        of List and Dict traits, the subsequent portion of the pattern is
        applied to each item in the list, or value in the dictionary.

        For example, if the self.children is a list, 'children.name'
        listens for trait changes to the *name* trait for each item in the
        self.children list.

        Note that items added to or removed from a list or dictionary in
        the pattern will cause the *handler* routine to be invoked as well,
        since this is treated as an *implied* change to the item's trait
        being monitored.

        The signature of the *handler* supplied also has an effect on
        how changes to intermediate traits are processed. The five valid
        handler signatures are:

        1. handler()
        2. handler(new)
        3. handler(name,new)
        4. handler(object,name,new)
        5. handler(object,name,old,new)

        For signatures 1, 4 and 5, any change to any element of a path
        being listened to invokes the handler with information about the
        particular element that was modified (e.g., if the item being
        monitored is 'foo.bar.baz', a change to 'bar' will call *handler*
        with the following information:

        - object: object.foo
        - name:   bar
        - old:    old value for object.foo.bar
        - new:    new value for object.foo.bar

        If one of the intermediate links is a List or Dict, the call to
        *handler* may report an *_items* changed event. If in the previous
        example, *bar* is a List, and a new item is added to *bar*, then
        the information passed to *handler* would be:

        - object: object.foo
        - name:   bar_items
        - old:    Undefined
        - new:    TraitListEvent whose *added* trait contains the new item
                  added to *bar*.

        For signatures 2 and 3, the *handler* does not receive enough
        information to discern between a change to the final trait being
        listened to and a change to an intermediate link. In this case,
        the event dispatcher will attempt to map a change to an
        intermediate link to its effective change on the final trait. This
        only works if all of the intermediate links are single values (such
        as an Instance or Any trait) and not Lists or Dicts. If the modified
        intermediate trait or any subsequent intermediate trait preceding
        the final trait is a List or Dict, then a TraitError is raised,
        since the effective value for the final trait cannot in general be
        resolved unambiguously. To prevent TraitErrors in this case, use the
        ':' separator to suppress notifications for changes to any of the
        intermediate links.

        Handler signature 1 also has the special characteristic that if a
        final trait is a List or Dict, it will automatically handle '_items'
        changed events for the final trait as well. This can be useful in
        cases where the *handler* only needs to know that some aspect of the
        final trait has been changed. For all other *handler* signatures,
        you must explicitly specify the 'xxx_items' trait if you want to
        be notified of changes to any of the items of the 'xxx' trait.

        Parameters
        ----------
        handler : function
            A trait notification function for the *name* trait attribute, with
            one of the signatures described below.
        name : str
            The name of the trait attribute whose value changes trigger the
            notification. The *name* can specify complex patterns of trait
            changes using an extended *name* syntax, which is described below.
        remove : bool
            If True, removes the previously-set association between
            *handler* and *name*; if False (the default), creates the
            association.
        dispatch : str
            A string indicating the thread on which notifications must be run.
            Possible values are:

            =========== =======================================================
            value       dispatch
            =========== =======================================================
            ``same``    Run notifications on the same thread as this one.
            ``ui``      Run notifications on the UI thread. If the current
                        thread is the UI thread, the notifications are executed
                        immediately; otherwise, they are placed on the UI
                        event queue.
            ``fast_ui`` Alias for ``ui``.
            ``new``     Run notifications in a new thread.
            =========== =======================================================

        See Also
        --------
        HasTraits.observe : A newer API for defining traits notifications.
        Nr   )TraitsListenerListenerParserListenerHandlerListenerNotifyWrapper)rb   r   r   r  r>  r  r   r   )r   Zwrapped_handler_refr   r  r>  Zhandler_type)rW   r   extended_trait_patmatchr  Ztraits_listenerr  r  r  r  rX   rK   stripr=   rN   r  r  rt   r   
unregisterr  ri   r   r   r   registerrg   )rx   r   rb   r   r   r  r>  r  r  r  r  r  r  r[   r   r  r   Zlnwr   r-   r-   r.   rK   l	  sh     ^








zHasTraits.on_trait_changec                sh  |dkr|}| j |o|j |}|r| j j|}|dk	rt||f}||kr||= t|dkr|= | j| j|dd |r| j| j|d dd |r|j|| |dd dS dd  | j j	|i }t||f} fd	d
}	t
j||	|f}
||krNt|dkr4| j| j| |r4| j| j|d  |
||< t||t| | |rd|j|| |d dS )a  Synchronizes the value of a trait attribute on this object with a
        trait attribute on another object.

        In mutual synchronization, any change to the value of the specified
        trait attribute of either object results in the same value being
        assigned to the corresponding trait attribute of the other object.
        In one-way synchronization, any change to the value of the attribute
        on this object causes the corresponding trait attribute of *object* to
        be updated, but not vice versa.

        For ``List`` traits, the list's items are also synchronized, so that
        mutations to this trait's list will be reflected in the synchronized
        list (and vice versa in the case of mutual synchronization). For
        ``Dict`` and ``Set`` traits, items are not synchronized.

        Parameters
        ----------
        name : str
            Name of the trait attribute on this object.
        object : object
            The object with which to synchronize.
        alias : str
            Name of the trait attribute on *other*; if None or omitted, same
            as *name*.
        mutual : bool or int
            Indicates whether synchronization is mutual (True or non-zero)
            or one-way (False or zero)
        remove : bool or int
            Indicates whether synchronization is being added (False or zero)
            or removed (True or non-zero)
        Nr   T)r   r   Fc             S   sd   x^t |j D ]N\}}|dkrx*t |j D ]\}}| |d kr,||= q,W t|dkr||= qW d S )Nre   r   )rX   r\   rt   )r   r  ro   r  rb   r`   r-   r-   r.   _sync_trait_listener_deleted
  s    
z:HasTraits.sync_trait.<locals>._sync_trait_listener_deletedc                s
    | S )Nr-   )r   )r  r  r-   r.   r1  
  s    z&HasTraits.sync_trait.<locals>.<lambda>)_is_list_trait_get_sync_trait_inforN   r   rt   r  _sync_trait_modified_sync_trait_items_modified
sync_traitri   r   r   r+  rB   )rx   
trait_namer(  aliasZmutualr   Zis_listr  ro   callbackr`   r-   )r  r  r.   r  
  sN    "
	
zHasTraits.sync_traitc             C   s.   t | dd }|d kr*i  | jd< }i |d< |S )N__sync_trait__re   )rB   r=   )rx   r  r-   r-   r.   r  
  s
    zHasTraits._get_sync_trait_infoc             C   sz   | j }||krd S |d }d ||< xL|| j D ]<\}}| }||j d kr0yt||| W q0   Y q0X q0W ||= d S )Nre   )r  r&  r  r+  )rx   r(  rb   r   r  r  lockedobject_namer-   r-   r.   r    s    
zHasTraits._sync_trait_modifiedc       
      C   s   |j }|t|j }|d d }| j}|d }d ||< xT|| j D ]D\}}	| }|	|j d krDy|jt||	||< W qD   Y qDX qDW ||= d S )Nr   re   i)indexrt   removedr  r&  r  addedrB   )
rx   r(  rb   r   r5   Zn0Zn1r  r  r  r-   r-   r.   r    s    
z$HasTraits._sync_trait_items_modifiedc             C   s    | j |j}|d k	o|jtjkS )N)r9  r   Zdefault_value_typer   Ztrait_list_object)rx   r  r   r-   r-   r.   r  #  s    zHasTraits._is_list_traitc       	      G   sJ  t |dkrtdt |dkr*t| }nt|d }|j}|dk	rz|jr^| j|d |j  |jrz| j|d t	|| | j
|d}| j }t| ||< }|dk	r|jd}|dk	r|jdj| nl| j}t|d	| t|d
| g}t||| |j| jjd dd |D }t |dkr6t|jd| |dkrF|| _dS )a  Adds a trait attribute to this object.

        Parameters
        ----------
        name : str
            Name of the attribute to add.
        *trait :
            Trait or a value that can be converted to a trait by Trait().
            Trait definition for *name*. If more than one value is specified,
            it is equivalent to passing the entire list of values to Trait().

        r   z"No trait definition was specified.r   Nr   rJ   FTz_%s_changedz	_%s_firedr   c             S   s   g | ]}|d k	r|qS )Nr-   )r   r   r-   r-   r.   r   i  s    z'HasTraits.add_trait.<locals>.<listcomp>)rt   r  r   r(   r   r   	add_traitr   r   r'   r  _instance_traitsrA   r   r   r  rG   r   rg   r1   rN   r   trait_added)	rx   rb   r;   r   Z	old_traititrait_dictZold_notifiersrD   r~   r-   r-   r.   r  *  s8    


zHasTraits.add_traitc             C   sz   | j |d}|dk	rv|j}|dk	rJ|jr6| j|d  |jrJ| j|d  || jkr\| j|= | j }||krv||= dS dS )a
  Removes a trait attribute from this object.

        Parameters
        ----------
        name : str
            Name of the attribute to remove.

        Returns
        -------
        result : bool
            True if the trait was successfully removed.
        r   Nr   rJ   TF)r  r   r   remove_traitr   r=   r  )rx   rb   r;   r   r  r-   r-   r.   r  s  s    
zHasTraits.remove_traitc             C   s2   d}|rd}| j ||}| s&|dkr*|S t|S )a  Returns the trait definition for the *name* trait attribute.

        If *force* is False (the default) and *name* is the name of an
        implicitly defined trait attribute that has never been referenced
        explicitly (i.e., has not yet been defined), the result is None. In
        all other cases, the result is the trait definition object associated
        with *name*.

        If *copy* is True, and a valid trait definition is found for *name*,
        a copy of the trait found is returned. In all other cases, the trait
        definition found is returned unmodified (the default).

        Parameters
        ----------
        name : str
            Name of the attribute whose trait definition is to be returned.
        force : bool
            Indicates whether to return a trait definition if *name* is
            not explicitly defined.
        copy : bool
            Indicates whether to return the original trait definition or a
            copy.
        r   r   Nrr   )r  rA   )rx   rb   forcer>   moderF   r-   r-   r.   r;     s    zHasTraits.traitc             C   s   | j |dS )a<  Returns the base trait definition for a trait attribute.

        This method is similar to the trait() method, and returns a
        different result only in the case where the trait attribute defined by
        *name* is a delegate. In this case, the base_trait() method follows the
        delegation chain until a non-delegated trait attribute is reached, and
        returns the definition of that attribute's trait as the result.

        Parameters
        ----------
        name : str
            Name of the attribute whose trait definition is returned.
        rH   )r  )rx   rb   r-   r-   r.   r9    s    zHasTraits.base_traitc             C   s   | j |j| ||S )zn Validates whether a value is legal for a trait.

        Returns the validated value if it is valid.
        )r9  r   )rx   rb   r`   r-   r-   r.   validate_trait  s    zHasTraits.validate_traitc       	      K   s  | j j }x0| j j D ] \}}|dd dkr|||< qW x4| jj D ]&}||krH| j|}|dk	rH|||< qHW t|dkr|S x0t|j D ] \}}t	|t
k	rt|||< qW i }xD|j D ]8\}}x.|j D ]\}}|t||dsP qW |||< qW |S )a1  Returns a dictionary containing the definitions of all of the trait
        attributes of this object that match the set of *metadata* criteria.
        Note that any traits with a name containing the suffix "_items" are
        always excluded.

        The keys of the returned dictionary are the trait attribute names, and
        the values are their corresponding trait definition objects.

        If no *metadata* information is specified, then all explicitly defined
        trait attributes defined for the object are returned.

        Otherwise, the *metadata* keyword dictionary is assumed to define a set
        of search criteria for selecting trait attributes of interest. The
        *metadata* dictionary keys correspond to the names of trait metadata
        attributes to examine, and the values correspond to the values the
        metadata attribute must have in order to be included in the search
        results.

        The *metadata* values either may be simple Python values like strings
        or integers, or may be lambda expressions or functions that return True
        if the trait attribute is to be included in the result. A lambda
        expression or function must receive a single argument, which is the
        value of the trait metadata attribute being tested. If more than one
        metadata keyword is specified, a trait attribute must match the
        metadata values of all keywords to be included in the result.

        Parameters
        ----------
        **metadata :
            Criteria for selecting trait attributes.
        r   Nr   r   i)r/   r>   r  r\   r=   r   r;   rt   rX   r   r   rw   rB   )	rx   r@   r,  rb   Ztrtr;   	meta_name	meta_evalrF   r-   r-   r.   r,    s*     

zHasTraits.traitsc             K   s   t |dkr| jj S i }x0t|j D ] \}}t|tk	r(t|||< q(W xF| jj D ]8\}}x.|j D ]\}}|t||dsjP qjW |||< qXW |S )a  Returns a dictionary containing the definitions of all of the trait
        attributes of the class that match the set of *metadata* criteria.

        The keys of the returned dictionary are the trait attribute names, and
        the values are their corresponding trait definition objects.

        If no *metadata* information is specified, then all explicitly defined
        trait attributes defined for the class are returned.

        Otherwise, the *metadata* keyword dictionary is assumed to define a set
        of search criteria for selecting trait attributes of interest. The
        *metadata* dictionary keys correspond to the names of trait metadata
        attributes to examine, and the values correspond to the values the
        metadata attribute must have in order to be included in the search
        results.

        The *metadata* values either may be simple Python values like strings
        or integers, or may be lambda expressions or functions that return
        **True** if the trait attribute is to be included in the result. A
        lambda expression or function must receive a single argument, which is
        the value of the trait metadata attribute being tested. If more than
        one metadata keyword is specified, a trait attribute must match the
        metadata values of all keywords to be included in the result.

        Parameters
        ----------
        **metadata :
            Criteria for selecting trait attributes.
        r   N)	rt   r/   r>   rX   r\   r   r   rw   rB   )rD   r@   rF   r  r  rb   r;   r-   r-   r.   r     s    
zHasTraits.class_traitsc             K   s   t | jf |j S )a  Returns a list of the names of all trait attributes whose
        definitions match the set of *metadata* criteria specified.

        This method is similar to the traits() method, but returns only the
        names of the matching trait attributes, not the trait definitions.

        Parameters
        ----------
        **metadata :
            Criteria for selecting trait attributes.
        )rX   r,  r   )rx   r@   r-   r-   r.   r  A  s    zHasTraits.trait_namesc             K   s   t | jf |j S )a  Returns a list of the names of all trait attributes whose
        definitions match the set of *metadata* criteria specified.

        This method is similar to the traits() method, but returns only the
        names of the matching trait attributes, not the trait definitions.

        Parameters
        ----------
        **metadata :
            Criteria for selecting trait attributes.
        )rX   r   r   )rD   r@   r-   r-   r.   rt  O  s    zHasTraits.class_trait_namesc             C   s:   t | }| jj|t}|| j|< ||kr6| j||| dS )z9 Explicitly sets the value of a cached property.
        N)r   r=   rN   r   r   )rx   rb   r`   r   	old_valuer-   r-   r.   r   ^  s
    
zHasTraits._set_traits_cachec             C   s   | j || jjt| t dS )z< Explicitly flushes the value of a cached property.
        N)r   r=   r   r   r   )rx   rb   r`   r-   r-   r.   r   g  s    zHasTraits._flush_traits_cachec             C   sH  |dd dkrH|dd dkrH|dkr,t S |r4tS td| jj|f |dd dkr| j|dd d}|dk	r|jd	krt|S | j}x|d
 D ]}||dt	| kr|| }| j}t
|d| t
|d| g}t||| |j|jd dd |D }t	|dkr(t|}t|jd| |S qW td|| jjf dS )zu Return the trait definition for a specified name when there is
        no explicit definition in the class.
        NrH   rI   r  z!'%s' object has no attribute '%s'r   rJ   r   r6   rq   z_%s_changedz	_%s_firedr   c             S   s   g | ]}|d k	r|qS )Nr-   )r   r   r-   r-   r.   r     s    z.HasTraits.__prefix_trait__.<locals>.<listcomp>TzHTrait class look-up failed for attribute '%s' for an object of type '%s'r  rr   rr   )r   	any_traitr   r  r*   r  r   rA   r1   rt   rG   r   rg   rN   r   r   SystemError)rx   rb   is_setr;   r   ru   rD   r~   r-   r-   r.   __prefix_trait__n  s:     zHasTraits.__prefix_trait__c             C   s   | j ||d dS )z/ Add (Java-style) event listener to an object. FN)_trait_listener)rx   r(  ru   r-   r-   r.   add_trait_listener  s    zHasTraits.add_trait_listenerc             C   s   | j ||d dS )z2 Remove (Java-style) event listener to an object. TN)r  )rx   r(  ru   r-   r-   r.   remove_trait_listener  s    zHasTraits.remove_trait_listenerc             C   s   |d	d  dkr|d7 }t |}| j}x| j|D ]}|d | |kr2|d
d  dkr||d }||kr| jt||||d n|dkr| jt|||d q2|d d dkr2||d }||kr| jt||||d q2|dkr2| jt|||d q2W d S )Nr   rJ      Z_changed)r   r   r   Z_firedrr   iiii)rt   r/   _each_trait_methodr  rB   )rx   r(  ru   r   rm   r,  rb   Z
short_namer-   r-   r.   r    s,    zHasTraits._trait_listenerc             c   sP   i }xF|j jD ]:}x4|jj D ]&\}}t|r||krd||< |V  qW qW dS )zD Generates each (name, method) pair for a specified object.
        TN)r  __mro__r=   r\   rC   )rx   r(  r  r   rb   rE   r-   r-   r.   r    s    zHasTraits._each_trait_methodc             C   sT   | j |}|dk	r0x|D ]}|j|ddi qW |dk	rPx|D ]}|j|  q>W dS )zK Handles adding/removing listeners for a generic 'Instance' trait.
        Nr   T)rp   rK   )rx   rb   r   r  rk   r   r-   r-   r.   _instance_changed_handler  s    


z#HasTraits._instance_changed_handlerc             C   s`   | j |}x*|D ]"}x|D ]}|j|ddi qW qW x$|D ]}x|D ]}|j|  qFW q<W dS )z_ Handles adding/removing listeners for a generic 'List( Instance )'
            trait.
        r   TN)rp   rK   )rx   rb   r   r  rk   ra   r   r-   r-   r.   r     s    




zHasTraits._list_changed_handlerc             C   sl   | j |dd }x,|jD ]"}x|D ]}|j|ddi q$W qW x&|jD ]}x|D ]}|j|  qRW qHW dS )z_ Handles adding/removing listeners for a generic 'List( Instance )'
            trait.
        Nr   r   Ti)rp   r  rK   r  )rx   rb   Znot_usedr5   rk   ra   r   r-   r-   r.   r     s    

z%HasTraits._list_items_changed_handlerc                s    fdd j j| D S )z{ Returns a list of ( name, method ) pairs for a specified 'Instance'
            or 'List( Instance )' trait name:
        c                s   g | ]\}}t  ||fqS r-   )rB   )r   method_nameZ	item_name)rx   r-   r.   r     s   z4HasTraits._get_instance_handlers.<locals>.<listcomp>)r  r4   )rx   rb   r-   )rx   r.   rp     s    
z HasTraits._get_instance_handlersc             C   sZ   xT| j jj D ]D\}}|d dkr|d }|d r| jt| ||d d|d d qW d	S )
z Initializes the object's statically parsed, but dynamically
            registered, traits listeners (called at object creation and
            unpickling times).
        r   rE   r   r   r   Tr   )r>  r   N)r  r2   r\   rK   rB   )rx   rb   dataconfigr-   r-   r.   r!    s    z$HasTraits._post_init_trait_listenersc             C   s:   x4| j jj D ]$\}}t| d|d  |f|  qW dS )z Initializes the object's statically parsed, but dynamically
            registered, traits listeners (called at object creation and
            unpickling times).
        z_init_trait_%s_listenerr   N)r  r2   r\   rB   )rx   rb   r  r-   r-   r.   r  !  s    zHasTraits._init_trait_listenersc             C   s,   |d s(| j t| ||d d|d d dS )z\ Sets up the listener for a method with the @on_trait_change
            decorator.
        r   r   Tr   )r>  r   N)rK   rB   )rx   rb   rG  r  r-   r-   r.   _init_trait_method_listener)  s    z%HasTraits._init_trait_method_listenerc                s(   t |  fdd}| j||| d dS )zJ Sets up the listener for an event with on_trait_change metadata.
        c                s   t |  d d S )NT)r+  )rx   )rb   r-   r.   notify9  s    z4HasTraits._init_trait_event_listener.<locals>.notify)r  N)r   rK   )rx   rb   rG  r   r  r-   )rb   r.   _init_trait_event_listener5  s    z$HasTraits._init_trait_event_listenerc                sx    dkrt | fdd}nF d t |  fdd}| j||d| d t | fd	d}| j||| d
 dS )zI Sets up the listener for a property with 'depends_on' metadata.
        Nc                s   | j  d  d S )N)r   )rx   )rb   r-   r.   r  D  s    z7HasTraits._init_trait_property_listener.<locals>.notifyz:oldc                s.   | j }|jt}|tkr*|j d |< d S )N)r=   rN   r   r   )rx   r[   r   )r   
cached_oldr-   r.   
pre_notifyK  s    z;HasTraits._init_trait_property_listener.<locals>.pre_notifyT)r  r  c                s&   | j j t}|tk	r"| j| d S )N)r=   r   r   r   )rx   r   )r  rb   r-   r.   r  V  s    )r  )r   rK   )rx   rb   rG  r   r   r  r  r-   )r   r  rb   r.   _init_trait_property_listener?  s    z'HasTraits._init_trait_property_listenerc                sZ   | j  |}t|jdd t|  fdd}| j||| d || jjti  < dS )z4 Sets up the listener for a delegate trait.
        rz  r   c                s   | j  |d   || d S )N)r   )rx   r(  Znotify_namer   r  )rb   target_name_lenr-   r.   r  d  s    z7HasTraits._init_trait_delegate_listener.<locals>.notify)r  Nrr   )_trait_delegate_namert   splitr   rK   r=   ri   r   )rx   rb   rG  r   Zname_patternr  r-   )rb   r  r.   r  ^  s
    z'HasTraits._init_trait_delegate_listenerc             C   s   | j jti }|r`||kr\| j|| | j|| jj| d dd ||= t|dkr\| j t= dS ||kr| j|d| jj| d  dS )zK Removes a delegate listener when the local delegate value is set.
        r   T)r   r   N)	r=   ri   r   rK   r  r  r2   rt   r  )rx   rb   r   r[   r-   r-   r.   _remove_trait_delegate_listenerm  s    z)HasTraits._remove_trait_delegate_listenerc          	   C   s\   xV| j jj D ]F\}}x<|D ]4}|d stj| |d | ||d t|d  d qW qW dS )z= Initialize observers prior to setting object state.
        r   r   r   r   )r(  r   r   r  N)r  r3   r\   r   r  r  )rx   rb   r   r%  r-   r-   r.   r     s    
zHasTraits._init_trait_observersc          	   C   s\   xV| j jj D ]F\}}x<|D ]4}|d rtj| |d | ||d t|d  d qW qW dS )z: Initialize observers after setting object state.
        r   r   r   r   )r(  r   r   r  N)r  r3   r\   r   r  r  )rx   rb   r   r%  r-   r-   r.   r"    s    
z$HasTraits._post_init_trait_observersc             C   s*   |d dkr&d|dd | j j|f }|S )z_ Returns the fully-formed 'on_trait_change' name for a specified
            delegate.
        r   rq   z%s%s%sNrr   rr   )r  Z
__prefix__)rx   rb   r   r-   r-   r.   r    s    
zHasTraits._trait_delegate_name)F)F)T)T)T)N)NNN)NNN)NNNNNre   N)NN)NN)N)NNNNNNre   N)F)NFr9   FN)NFr9   FFN)NTF)FF)re   )re   )`r*   r+   r,   r   r   Z_traits_cache__r   r   r   r   r  r   r   r  Ztrait_modifiedr  r   r  r  r  r	  r  r^   r  r  r'  r  r$   rN   r  r   r-  r/  r2  r3  r5  r?  rA  rB  rJ  rK  rC  rS  rL  rM  rP  r]  rD  rQ  r\  rq  rs  ru  rN  rR  r  r  r   rK   Zon_trait_eventr  r  r  r  r  r  r  r;   r9  r  r,  r   r  rt  r   r   r  r  r  r  r  r  r   r   rp   r!  r  r  r  r  r  r  r   r"  r  __classcell__r-   r-   )r  r.   r]   +  s   
"d5
9
-
#
Z
1      
;
,
M
	'       
u	
0    
DS     
  #
bI'
!>1	A



r]   )	metaclassc               @   s   e Zd ZdZeZdS )HasStrictTraitsa   This class guarantees that any object attribute that does not have an
    explicit or wildcard trait definition results in an exception.

    This feature can be useful in cases where a more rigorous software
    engineering approach is being used than is typical for Python programs. It
    also helps prevent typos and spelling mistakes in attribute names from
    going unnoticed; a misspelled attribute name typically causes an exception.
    N)r*   r+   r,   r   r   rJ   r-   r-   r-   r.   r    s   r  c                   s    e Zd ZdZ fddZ  ZS )HasRequiredTraitsa   This class builds on the functionality of HasStrictTraits and ensures
    that any object attribute with `required=True` in its metadata must be
    passed as an argument on object initialization.

    This can be useful in cases where an object has traits which are required
    for it to function correctly.

    Raises
    ------
    TraitError
        If a required trait is not passed as an argument.

    Examples
    --------
    A class with required traits:

    >>> class RequiredTest(HasRequiredTraits):
    ...     required_trait = Any(required=True)
    ...     non_required_trait = Any()

    Creating an instance of a HasRequiredTraits subclass:

    >>> test_instance = RequiredTest(required_trait=13, non_required_trait=11)
    >>> test_instance2 = RequiredTest(required_trait=13)

    Forgetting to specify a required trait:

    >>> test_instance = RequiredTest(non_required_trait=11)
    traits.trait_errors.TraitError: The following required traits were not
    provided: required_trait.
    c                sH    fdd| j ddD }|r6tdjdjt|t jf   d S )Nc                s   g | ]}| kr|qS r-   r-   )r   rb   )r,  r-   r.   r     s   z.HasRequiredTraits.__init__.<locals>.<listcomp>T)requiredz4The following required traits were not provided: {}.z, )r  r#   formatr   sortedr4  ry   )rx   r,  Zmissing_required_traits)r  )r,  r.   ry     s    
zHasRequiredTraits.__init__)r*   r+   r,   r   ry   r  r-   r-   )r  r.   r    s   r  c               @   s    e Zd ZdZedddZeZdS )HasPrivateTraitsaN   This class ensures that any public object attribute that does not have
    an explicit or wildcard trait definition results in an exception, but
    "private" attributes (whose names start with '_') have an initial value of
    **None**, and are not type-checked.

    This feature is useful in cases where a class needs private attributes to
    keep track of its internal object state, which are not part of the class's
    public API. Such attributes do not need to be type-checked, because they
    are manipulated only by the (presumably correct) methods of the class
    itself.
    T)r   r  N)r*   r+   r,   r   r   rI   r   rJ   r-   r-   r-   r.   r    s   r  c               @   s   e Zd ZdZdS )ABCMetaHasTraitsz A MetaHasTraits subclass which also inherits from
    abc.ABCMeta.

    .. note:: The ABCMeta class is cooperative and behaves nicely
        with MetaHasTraits, provided it is inherited first.
    N)r*   r+   r,   r   r-   r-   r-   r.   r    s   r  c               @   s   e Zd ZdZdS )ABCHasTraitsz A HasTraits subclass which enables the features of Abstract
    Base Classes (ABC). See the 'abc' module in the standard library
    for more information.

    N)r*   r+   r,   r   r-   r-   r-   r.   r    s   r  c               @   s   e Zd ZdZeZdS )ABCHasStrictTraitsz A HasTraits subclass which behaves like HasStrictTraits but
    also enables the features of Abstract Base Classes (ABC). See the
    'abc' module in the standard library for more information.

    N)r*   r+   r,   r   r   rJ   r-   r-   r-   r.   r    s   r  c               @   s    e Zd ZdZeddd ZdS )SingletonHasTraitsz4 Singleton class that support trait attributes.
    zXSingletonHasTraits has been deprecated and will be removed in the future. Avoid using itc             O   s$   d| j krtj| f||| _| jS )N_the_instance)r=   r]   r   r  )rD   r   r,  r-   r-   r.   r   2  s    
zSingletonHasTraits.__new__N)r*   r+   r,   r   r$   r   r-   r-   r-   r.   r  .  s   r  c               @   s    e Zd ZdZeddd ZdS )SingletonHasStrictTraitszq Singleton class that supports strict trait attributes.

        Non-trait attributes generate an exception.
    z^SingletonHasStrictTraits has been deprecated and will be removed in the future. Avoid using itc             O   s   t j| f||S )N)r  r   )rD   r   r,  r-   r-   r.   r   @  s    z SingletonHasStrictTraits.__new__N)r*   r+   r,   r   r$   r   r-   r-   r-   r.   r  :  s   r  c               @   s    e Zd ZdZeddd ZdS )SingletonHasPrivateTraitszf Singleton class that supports trait attributes, with private attributes
        being unchecked.
    z_SingletonHasPrivateTraits has been deprecated and will be removed in the future. Avoid using itc             O   s   t j| f||S )N)r  r   )rD   r   r,  r-   r-   r.   r   K  s    z!SingletonHasPrivateTraits.__new__N)r*   r+   r,   r   r$   r   r-   r-   r-   r.   r  F  s   r  c               @   s    e Zd ZdZedZdd ZdS )VetoablezB Defines a 'vetoable' request object and an associated event.
    Fc             C   s   | j | d S )N)Z_trait_veto_notify)rx   r%  r-   r-   r.   _veto_changedX  s    zVetoable._veto_changedN)r*   r+   r,   r   r   Zvetor  r-   r-   r-   r.   r  Q  s   r  c               @   s$   e Zd ZdZedefddZdS )MetaInterfacez Meta class for interfaces.

    Interfaces are simple ABCs with the following features:-

    1) They cannot be instantiated (they are interfaces, not implementations!).
    2) Calling them is equivalent to calling 'adapt'.

    z'use "adapt(adaptee, protocol)" instead.c             C   s   ddl m} ||| |dS )z Attempt to adapt the adaptee to this interface.

        Note that this means that (intentionally ;^) that interfaces
        cannot be instantiated!

        r   )adapt)r   )Ztraits.adaptation.apir  )rx   Zadapteer   r  r-   r-   r.   r{   i  s    	zMetaInterface.__call__N)r*   r+   r,   r   r$   r   r{   r-   r-   r-   r.   r  _  s   r  c               @   s   e Zd ZdZdS )	Interfacez( The base class for all interfaces.
    N)r*   r+   r,   r   r-   r-   r-   r.   r  w  s   r  c                 sT   ddl m} t dkr dd S x" D ]}tt||s&tdq&W  fdd}|S )z Class decorator to declare the protocols that a class provides.

    Parameters
    ----------
    *protocols :
        A list of protocols (Interface classes or Python ABCs) that the
        decorated class provides.

    r   )ABCMetac             S   s   | S )Nr-   )r   r-   r-   r.   r1    s    zprovides.<locals>.<lambda>zOAll arguments to 'provides' must be subclasses of Interface or be a Python ABC.c                sN   x D ]}t |j||  qW trJddlm} tjdtdd ||  t | S )Nr   )check_implementszIn the future, the @provides decorator will not perform interface checks. Set has_traits.CHECK_INTERFACES to 0 to suppress this warning.rH   )r   )r   r  CHECK_INTERFACESZinterface_checkerr  r   r   r   )r   r  r  )	protocolsr-   r.   wrapped_class  s    
zprovides.<locals>.wrapped_class)abcr  rt   r  r   r#   )r  r  r  r  r-   )r  r.   provides|  s    

r  c             C   s
   t | tS )z+ Return True if the class is an Interface. )rW   r  )r   r-   r-   r.   isinterface  s    r  c               @   s   e Zd ZdZdS )r_   z A class that implemented ISerializable requires that all HasTraits
        objects saved as part of its state also implement ISerializable.
    N)r*   r+   r,   r   r-   r-   r-   r.   r_     s   r_   )r5   r6   r7   )r6   r8   )N)Fr9   )FF)~r   r  r>   r:  rT   re  ri  rer   r   r   r   re   r   r  Zadaptation.adaptation_errorr   	constantsr   r   Zctraitr   r	   Zctraitsr
   Zobservationr   r   r,  r   r   r   r   Ztrait_typesr   r   r   r   r   r   Ztrait_notifiersr   r   r   r   r   r   r   Z
trait_baser   r   r   r    r!   r"   Ztrait_errorsr#   Zutil.deprecatedr$   Zutil._traitsui_helpersr%   Ztrait_convertersr&   r'   r(   r  ABCr)   r|   r   r   r   r   r   r   rf   r[  r   r8  compiler  r   r  Zdispatch_samer  rA   rG   rS   rC   rZ   rp   rv   rw   r   r   r   r   r   Z
_HasTraitsr   r   r   r   r   rK   r   r   r   r]   r  r  r  r  r  r  r  r  r  r  r  ZVetoableEventr  r  r  r  r_   r-   r-   r-   r.   <module>   s    $	 	


&	(#=  ?c
!,
0<                   13