o
    &?e                     @   sL   d dl ZddlmZ ddlmZmZ dddddd	d
Zdd Zdd Z	dS )    N   )_supported_float_type   )apply_kernelapply_kernel_nand   F)radiuskernelnansafenum_threadsc             	   C   s,  t | } t| j}| j|dd}|du rd}|du r!t|| j}||}t |j}|d }|t| }	|	| }
t j	|
|t j	k< |
|j}
|

d}
t j||ddt jf t j	dd}|rbtnt}||
d|
t j| |jd	
dt j| jt jd	t j|jt jd	|t j|}|j| jdd}|S )
a`  Estimate background intensity by rolling/translating a kernel.

    This rolling ball algorithm estimates background intensity for a
    ndimage in case of uneven exposure. It is a generalization of the
    frequently used rolling ball algorithm [1]_.

    Parameters
    ----------
    image : ndarray
        The image to be filtered.
    radius : int, optional
        Radius of a ball shaped kernel to be rolled/translated in the image.
        Used if ``kernel = None``.
    kernel : ndarray, optional
        The kernel to be rolled/translated in the image. It must have the
        same number of dimensions as ``image``. Kernel is filled with the
        intensity of the kernel at that position.
    nansafe: bool, optional
        If ``False`` (default) assumes that none of the values in ``image``
        are ``np.nan``, and uses a faster implementation.
    num_threads: int, optional
        The maximum number of threads to use. If ``None`` use the OpenMP
        default value; typically equal to the maximum number of virtual cores.
        Note: This is an upper limit to the number of threads. The exact number
        is determined by the system's OpenMP library.

    Returns
    -------
    background : ndarray
        The estimated background of the image.

    Notes
    -----
    For the pixel that has its background intensity estimated (without loss
    of generality at ``center``) the rolling ball method centers ``kernel``
    under it and raises the kernel until the surface touches the image umbra
    at some ``pos=(y,x)``. The background intensity is then estimated
    using the image intensity at that position (``image[pos]``) plus the
    difference of ``kernel[center] - kernel[pos]``.

    This algorithm assumes that dark pixels correspond to the background. If
    you have a bright background, invert the image before passing it to the
    function, e.g., using `utils.invert`. See the gallery example for details.

    This algorithm is sensitive to noise (in particular salt-and-pepper
    noise). If this is a problem in your image, you can apply mild
    gaussian smoothing before passing the image to this function.

    References
    ----------
    .. [1] Sternberg, Stanley R. "Biomedical image processing." Computer 1
           (1983): 22-34. :DOI:`10.1109/MC.1983.1654163`

    Examples
    --------
    >>> import numpy as np
    >>> from skimage import data
    >>> from skimage.restoration import rolling_ball
    >>> image = data.coins()
    >>> background = rolling_ball(data.coins())
    >>> filtered_image = image - background


    >>> import numpy as np
    >>> from skimage import data
    >>> from skimage.restoration import rolling_ball, ellipsoid_kernel
    >>> image = data.coins()
    >>> kernel = ellipsoid_kernel((101, 101), 75)
    >>> background = rolling_ball(data.coins(), kernel=kernel)
    >>> filtered_image = image - background
    F)copyNr   r   Zconstant)Zconstant_valuesmode)dtype)npasarrayr   r   Zastypeball_kernelndimshapetupleinfZreshapepadZnewaxisr   r   Z
zeros_likearrayZintp)imager   r	   r
   r   Z
float_typeZimgZkernel_shapeZkernel_centerZcenter_intensityZintensity_differencefunc
background r   b/home/www/facesmatcher.com/pyenv/lib/python3.10/site-packages/skimage/restoration/_rolling_ball.pyrolling_ball   s<   
J




r   c                 C   sz   t jt jdd t | g| D ddidd}t j|d dd}t |}t t | d | dd	}t j||| k< |S )
a  Create a ball kernel for restoration.rolling_ball.

    Parameters
    ----------
    radius : int
        Radius of the ball.
    ndim : int
        Number of dimensions of the ball. ``ndim`` should match the
        dimensionality of the image the kernel will be applied to.

    Returns
    -------
    kernel : ndarray
        The kernel containing the surface intensity of the top half
        of the ellipsoid.

    See Also
    --------
    rolling_ball
    c                 S      g | ]}t | |d  qS r   r   Zarange.0xr   r   r   
<listcomp>       zball_kernel.<locals>.<listcomp>indexingijr   Zaxisr   r   N)r   stackmeshgridceilsumsqrtclipr   )r   r   kernel_coordsZsum_of_squaresZdistance_from_centerr	   r   r   r   r   x   s   
r   c                 C   s   t | } t | d dd}t jt jdd |D ddidd	}dt j|| d dd	 }|t t |d
d }t j||d
k < |S )a/  Create an ellipoid kernel for restoration.rolling_ball.

    Parameters
    ----------
    shape : arraylike
        Length of the principal axis of the ellipsoid (excluding
        the intensity axis). The kernel needs to have the same
        dimensionality as the image it will be applied to.
    intensity : int
        Length of the intensity axis of the ellipsoid.

    Returns
    -------
    kernel : ndarray
        The kernel containing the surface intensity of the top half
        of the ellipsoid.

    See Also
    --------
    rolling_ball
    r   r   Nc                 S   r   r    r!   r"   r   r   r   r%      r&   z$ellipsoid_kernel.<locals>.<listcomp>r'   r(   r   r)   r   )r   r   r/   r*   r+   r-   r.   r   )r   Z	intensityZ	semi_axisr0   Zintensity_scalingr	   r   r   r   ellipsoid_kernel   s   
r1   )
numpyr   Z_shared.utilsr   Z_rolling_ball_cyr   r   r   r   r1   r   r   r   r   <module>   s    q&