
    Q-jC                         d dl mZ d dlmZ d dlmZmZ d dlmZm	Z	m
Z
 d dlmZ d dlmZmZmZmZmZmZ g dZ	 d*d	ed
edede	def
dZ	 	 d*d	ede
dede	def
dZ	 d*d	ed
edede	def
dZ	 	 d*d	ede
dede	def
dZ	 	 d+d	ed
edededede	dedefdZ	 	 d+d	ede
dededede	defdZ	 	 	 	 d,dede
de
dededededede	defd Z	 	 d-d	ed
ededede	defd!Z	 	 	 d.d"ed#ed$e	d%e	de	dedefd&Z	 	 	 d/d'ede
ez  de
ez  ded(ed#ed$e	de	dedefd)Zy)0    )partial)nan)	DataFrameSeries)DictLikeIntIntFloat)zero)v_boolv_driftv_floatv_intv_offsetv_series)	aboveabove_valuebelowbelow_valuecrosscross_valuesignalstsignalsxsignalsNxyasintoffsetreturnc                 :     t        t        d      | |f||d|S )a  Above

    Determines if each ```x``` value is above (or ```>=```) each ```y``` value.

    Parameters:
        x (Series): ```x```
        y (Series): ```y```
        asint (bool): Returns as ```Int```.
        offset (Int): Post shift. Default: ```0```

    Returns:
        (Series): State where ```x >=  y```.

    Example:
        ```py
        x = Series([4, 2, 0, -1, 1])
        y = Series([1, 1, 1, 1, 1])

        x_above_y = ta.above(x, y)
        # x_above_y = Series([1, 1, 0, 0, 1])
        ```
    Tr   r   r   r   _above_belowr   r   r   r   kwargss        f/Users/jameslopez/projects/TradingBot25/.venv/lib/python3.12/site-packages/pandas_ta/utils/_signals.pyr   r   !   s'    2 -7<t,QXvXQWXX    valuec                     t        |t        t        f      st        d       yt	        || j
                  | j                  dd            } t        t        d      | |f||d|S )	a  Above Value

    Determines if each ```x``` value is above (or ```>=```) a
    constant ```value```.

    Parameters:
        x (Series): ```x```
        value (IntFloat): Value to compare with ```x```.
        asint (bool): Returns as ```Int```.

    Returns:
        (Series): State where ```x >= y```.

    Example:
        ```py
        x = Series([4, 2, 0, -1, 1])
        x_above_1 = ta.above_value(x, 1)
        # x_above_1 = Series([1, 1, 0, 0, 1])
        ```
    [X] value is not a numberN._indexnameTr    r!   	
isinstanceintfloatprintr   r.   replacer   r#   r   r(   r   r   r%   r   s         r&   r   r   =   sb    0 ec5\*)*uAGGUG*<*<S#*FGA,7<t,QXvXQWXXr'   c                 :     t        t        d      | |f||d|S )a   Below

    Determines if each ```x``` value is below (or ```<=```) each ```y``` value.

    Parameters:
        x (Series): ```x```
        y (Series): ```y```
        asint (bool): Returns as ```Int```.
        offset (Int): Post shift. Default: ```0```

    Returns:
        (Series): State where ```x <= y```.

    Example:
        ```py
        x = Series([4, 2, 0, -1, 1])
        y = Series([1, 1, 1, 1, 1])

        x_below_y = ta.below(x, y)
        # x_below_y = Series([0, 0, 1, 1, 1])
        ```
    Fr    r!   r"   r$   s        r&   r   r   \   s'    2 .7<u-aY%YRXYYr'   c                     t        |t        t        f      st        d       yt	        || j
                  | j                  dd            } t        t        d      | |f||d|S )	a  Below Value

    Determines if each ```x``` value is below (or ```<=```) a
    constant ```value```.

    Parameters:
        x (Series): ```x```
        value (IntFloat): Value to compare with ```x```.
        asint (bool): Returns as ```Int```.
        offset (Int): Post shift. Default: ```0```

    Returns:
        (Series): State where ```x <= y```.

    Example:
        ```py
        x = Series([4, 2, 0, -1, 1])
        x_below_1 = ta.below_value(x, 1)
        # x_below_1 = Series([0, 0, 1, 1, 1])
        ```
    r*   Nr+   r,   r-   Fr    r!   r0   r6   s         r&   r   r   x   sb    2 ec5\*)*uAGGUG*<*<S#*FGA-7<u-aY%YRXYYr'   r   equalr%   c                 <   t        |       } t        |      }t        |      }| j                  t               |j                  t               |r0|r| |k\  n| |kD  }| j	                  d      |j	                  d      k  }n/|r| |k  n| |k  }| j	                  d      |j	                  d      kD  }||z  }	d|	j
                  d<   |r|	j                  t              }	|dk7  r|	j	                  |      }	| j                   d|rdnd d|j                   |	_        d|	_	        |	S )a#  Cross

    Determines where ```x``` crosses ```y```, either _above_ or _below_,
    strictly (_equal_) or not.

    Parameters:
        x (Series): ```x```
        y (Series): ```y```
        above (bool): Check above. Check below, set ```above=False```
        equal (bool): At least/most, ```=```, check.
        asint (bool): Returns as ```Int```.
        offset (Int): Post shift. Default: ```0```

    Returns:
        (Series): Values where ```x``` crosses ```y```.

    Example:
        ```py
        x = Series([4, 2, 0, -1, 1])
        y = Series([1, 1, 1, 1, 1])

        # Cross Above Examples
        x_xae_y = ta.cross(x, y, above=True, equal=True)
        # x_xae_y = Series([0, 0, 0, 0, 1])

        x_xa_y = ta.cross(x, y, above=True, equal=False)
        # x_xa_y = Series([0, 0, 0, 0, 0])

        # Cross Below Examples
        x_xbe_y = ta.cross(x, y, above=False, equal=True)
        # x_xbe_y = Series([0, 0, 1, 0, 1])

        x_xb_y = ta.cross(x, y, above=False, equal=False)
        # x_xb_y = Series([0, 0, 1, 0, 0])
        ```
       Fr   r,   XAXBsignal)
r   r   applyr
   shiftilocastyper2   r/   category)
r   r   r   r9   r   r   r%   currentpreviousr   s
             r&   r   r      s   V 	AAfFGGDMGGDM !!q&q1u771:
*!!q&q1u771:
*hEEJJqMS! {F# FF81UT5Qqvvh?EJENLr'   c                 v    t        || j                  | j                  dd            }t        | |||||fi |S )aI  Cross Value

    Determines where ```x``` crosses a constant ```value```, either _above_
    or _below_, strictly (_equal_) or not.

    Parameters:
        x (Series): ```x```
        value (IntFloat): Value to compare with ```x```.
        above (bool): Check above. Check below, set ```above=False```
        equal (bool): At least/most, ```=```, check.
        asint (bool): Returns as ```Int```.
        offset (Int): Post shift. Default: ```0```

    Returns:
        (Series): Values where ```x``` crosses ```y```.

    Example:
        ```py
        x = Series([4, 2, 0, -1, 1])

        # Cross Above Examples
        x_xae_y = ta.cross_value(x, 1, above=True, equal=True)
        # x_xae_y = Series([0, 0, 0, 0, 1])

        x_xa_y = ta.cross_value(x, 1, above=True, equal=False)
        # x_xa_y = Series([0, 0, 0, 0, 0])

        # Cross Below Examples
        x_xbe_y = ta.cross_value(x, 1, above=False, equal=True)
        # x_xbe_y = Series([0, 0, 1, 0, 1])

        x_xb_y = ta.cross_value(x, 1, above=False, equal=False)
        # x_xb_y = Series([0, 0, 1, 0, 0])
        ```
    r+   r,   r-   )r   r.   r5   r   )r   r(   r   r9   r   r   r%   r   s           r&   r   r      s@    R 	uAGGUG*<*<S#*FGAAueUF=f==r'   	indicatorxaxbcross_valuesxseries	xseries_a	xseries_bcross_seriesc	                    t               }	|rt        |t        t        f      r\|r=t	        | |d|      }
t	        | |d|      }|
|	|
j
                  <   ||	|j
                  <   nt        | ||      }||	|j
                  <   |rt        |t        t        f      r\|r=t	        | |d|      }t	        | |d|      }||	|j
                  <   ||	|j
                  <   nt        | ||      }||	|j
                  <   ||}||}|:t        |      r/|rt        | |d|      }nt        | ||      }||	|j
                  <   |:t        |      r/|rt        | |d|      }nt        | ||      }||	|j
                  <   |	S )a  Signals

    Mulitfuncational signal checker that determines whether an
    indicator crosses above/below value or Series.

    Parameters:
        indicator (Series): Indicator to check for signal crossings.
        cross_values (bool): Check if crossed value.
        xseries (Series): Cross Series
        xseries_a (Series): Cross Above Series
        xseries_b (Series): Cross Below Series
        cross_series (bool): Check if crossed ```xseries```.

    Other Parameters:
        xa (IntFloat): Crossing above value.
        xb (IntFloat): Crossing below value.
        offset (Int): Post shift. Default: ```0```

    Returns:
        (DataFrame): 2 columns

    Note:
        See sources of: ```er```, ```macd```, ```rsi```, and ```rsx```
        for examples of use.
    T)r   r   F)r   )r   r1   r2   r3   r   r/   r   r   r   r   r   r   )rG   rH   rI   rJ   rK   rL   rM   rN   r   dfxa_startxa_endxd_abovexb_startxb_endxd_belowxsaxsbs                     r&   r   r     sv   > 
B	~*R#u6"9bVLH BeFKF (Bx}}$Bv{{O"9b@H (Bx}}	~*R#u6"9bVLH BeFKF (Bx}}$Bv{{O"9b@H (Bx}} 		)!4	9DHC	9V<C388)!4	9E&IC	9V<C388Ir'   c                 l   t        |       } t        |      }t        |      }| j                  t               |j                  t               |r| |k\  }n| |k  }|r|j	                  t
              }|dk7  r|j                  |      }| j                   d|rdnd d|j                   |_        d|_        |S )a  Above / Below

    Determines if ```x``` is above or below ```y```.

    Parameters:
        x (Series): ```x```
        y (Series): ```y```
        above (bool): Above check. Below: ```above=False```
        equal (bool): At least/most, ```=```, check.
        asint (bool): Returns as ```Int```.
        offset (Int): Post shift. Default: ```0```

    Returns:
        (Series): Values where ```x``` values are above/below ```y``` values.
    r   r,   ABr>   )	r   r   r?   r
   rB   r2   r@   r/   rC   )r   r   r   r   r   r%   rD   s          r&   r#   r#   b  s    * 	AAfFGGDMGGDM q&q&..% {--' ffXQes5Qqvvh?GLGNr'   trendasbooltrade_offsetdriftc                    t        |       } | yt        |d      }t        |d      }t        |      }t	        |      }| j                  t              }|j                  |      j                  |      j                  d      j                  t              }|dkD  j                  t              }|dk  j                         j                  t              }	|r?|j                  t              }|j                  t              }|	j                  t              }	d|d|d|d|	i}
t        |
|j                        }|dk7  r|j                  |      }d	|v r|j                  |d	   d
       d|_        d|_        |S )a!  Trend Signals

    This function creates Trend, Trades, Entries and Exit values per bar when
    given a trend condition e.g. ```trend = close > sma(close, 50)```.

    Source:
        * Kevin Johnson

    Parameters:
        trend (Series): ```trend``` Series. Boolean or integer values of
            ```0``` and ```1```
        asbool (bool): Return booleans. Default: ```False```
        trade_offset (value): Shift trade entries/exits with live: ```0``` and
            backesting: ```1```. Default: ```0```
        drift (int): Difference amount. Default: ```1```
        offset (int): Post shift. Default: ```0```

    Other Parameters:
        fillna (value): ```pd.DataFrame.fillna(value)```

    Returns:
        (DataFrame): 4 columns

    Note: Column Detail
        * Trends (trend: 1, no trend: 0)
        * Trades (Enter: 1, Exit: -1, Otherwise: 0)
        * Entries (entry: 1, nothing: 0)
        * Exits (exit: 1, nothing: 0)

    Note: Details
        A ```trend``` is a state or condition, that is as simple
        as ```Close > MA``` or something more complex that has boolean
        or integer (trend: 1, no trend: 0) values.

    Tip: VectorBT
        * For backtesting, set ```trade_offset=1```.
        * Setting ```asbool=True``` is useful for backtesting with vectorbt's
          ```Portfolio.from_signal(close, entries, exits)``` method.

    Example:
        These are two different outcomes for each (long/short) position and
        depends on the source and it's behavior.

        Signals when ```Close > SMA50(Close)```

            ta.tsignals(close > ta.sma(close, 50), asbool=False)

        Signals when ```EMA(Close, 8) > EMA(Close, 21)```

            ta.tsignals(ta.ema(close, 8) > ta.ema(close, 21), asbool=True)

    Warning:
        Check ALL outcomes BEFORE making an Issue
    NFr   	TS_Trends	TS_Trades
TS_EntriesTS_Exits)r.   fillnaTinplaceTSr\   )r   r   r   r   r   rB   r2   diffr@   re   absboolr   r.   r/   rC   )r\   r]   r^   r_   r   r%   trendstradesentriesexitsdatarP   s               r&   r   r     sX   x UOE}FE"Fq)LENEfF \\#F[[%%l3::1=DDSIFz!!#&GaZ%%c*Et$..&T" f
f
w
U	D 
4v||	,B {XXf 6
		&"D	1 BGBKIr'   sourcelongc                 0   t        |       } | yt        |      }|rt        | |      }	t        | |d       }
nt        | |d      }	t        | |       }
|	|
z   }|j                  dt        id       |j                  dd       |j                  dd       |dkD  j                  t              }|sd	|z
  }|||d
}t        |fi |}t        d|j                  dd	|j                  z
  i       d|v r|j                  |d   d       d|_        d|_        |S )au  Cross Signals

    This function creates Trend, Trades, Entries and Exits values per bar
    for crossing events.

    Sources:
        * Kevin Johnson

    Parameters:
        source (Series): ```source``` Signal
        xa (Series): Series the Signal crosses above if ```above=True```
        xb (Series): Series the Signal crosses below if ```above=True```
        above (bool): The ```source``` crossing; below is ```False```.
            Default: ```True```
        long (bool): The ```source``` position; short is ```False```.
            Default: ```True```
        offset (int): Post shift. Default: ```0```
        asbool (bool): Return booleans. Default: ```False```
        trade_offset (value): Shift trade entries/exits with live: ```0``` and
            backesting: ```1```. Default: ```0```

    Other Parameters:
        fillna (value): ```pd.DataFrame.fillna(value)```

    Returns:
        (DataFrame): 4 columns

    Note: Column Detail
        * Trends  (trend: 1, no trend: 0)
        * Trades  (Enter: 1, Exit: -1, Otherwise: 0)
        * Entries (entry: 1, nothing: 0)
        * Exits   (exit: 1, nothing: 0)

    Tip: VectorBT
        * For backtesting, set ```trade_offset=1```.
        * Setting ```asbool=True``` is useful for backtesting with vectorbt's
          ```Portfolio.from_signal(close, entries, exits)``` method.

    Example:
        These are two different outcomes for each (long/short) position and
        depends on the source and it's behavior.

            rsi = df.ta.rsi()

        When RSI crosses above 20 and then below 80 in a long position:

            ta.xsignals(source=rsi, xa=20, xb=80, above=True, long=True)
            # Simpler
            # ta.xsignals(rsi, 20, 80, True, True)

        When RSI crosses below 20 and then above 80 in a long position:

            ta.xsignals(source=rsi, xa=20, xb=80, above=False, long=True)
            # Simpler
            # ta.xsignals(rsi, 20, 80, False, True)

        * Similarly, short positions (```long=False```) also differ depending
          on ```above``` state.

    Warning:
        Check ALL parameter combination outcomes BEFORE making an Issue.
    NFr    r   Trf   inside)
limit_arearg   r;   )r]   r^   r   XS_LONGXS_SHORTre   XSr\   )r   r   r   r5   r   ffillre   rB   r2   r   r   ra   r/   rC   )rq   rH   rI   r   rr   r]   r^   r   r%   rn   ro   rm   rl   tskwargsrP   s                  r&   r   r     s<   N fF~fF fb)VRu55fb6VR((u_F NNAs8TN*
LLHdL3
MM!TM"qj  %FV $H
 
&	%H	%B 
BLL
Q%  6
		&"D	1 BGBKIr'   )TN)TTTN)NNNNNNNN)TTN)NNNN)TTNNN) 	functoolsr   numpyr   pandasr   r   pandas_ta._typingr   r   r	   pandas_ta.utils._mathr
   pandas_ta.utils._validater   r   r   r   r   r   __all__rk   r   r   r   r   r   r   r   r#   r   r    r'   r&   <module>r      sY     $ 5 5 & 
 =AYYY!%Y69YY: /3YYY'+YY Y@ =AZZZ!%Z69ZZ: /3ZZZ'+ZZ ZD '+&*IIII#I I !$I 	I
 I\ '+&**>*>*>*>#*> *> !$*>
 *>^ <@1526-1	MM#M08MM(.M M *0M 	M (+	M
 Md '+----#- - 	-d #'+/dddd%(d d #+d 	dX &*-1tt6t 	6t 	t #	t
 t
 (+t t #+t tr'   