o
    oi                     @   s   d dl mZmZmZmZ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mZ G dd	 d	e
Zd
S )    )AnyDictOptionalTupleUnion)random_generator)GeometricAugmentationBase2D)ResampleSamplePadding)Tensor	as_tensor)deg2rad)get_shear_matrix2dwarp_affinec                       s(  e Zd ZdZejjddejjddfde	e
eeeef eeeeef f de	eeef dedede	eeef d	ed
eddf fddZde
deee
f deeef de
fddZ	dde
deee
f deeef dee
 de
f
ddZ		dde
deeef dee
 deeeef  de
f
ddZ  ZS )RandomSheara  Apply a random 2D shear transformation to a tensor image.

    The transformation is computed so that the image center is kept invariant.

    Args:
        shear: Range of degrees to select from.
            If float, a shear parallel to the x axis in the range (-shear, +shear) will be applied.
            If (a, b), a shear parallel to the x axis in the range (-shear, +shear) will be applied.
            If (a, b, c, d), then x-axis shear in (shear[0], shear[1]) and y-axis shear in (shear[2], shear[3])
            will be applied. Will not apply shear by default.
        resample: resample mode from "nearest" (0) or "bilinear" (1).
        padding_mode: padding mode from "zeros" (0), "border" (1) or "reflection" (2).
        same_on_batch: apply the same transformation across the batch.
        align_corners: interpolation flag.
        p: probability of applying the transformation.
        keepdim: whether to keep the output shape the same as input (True) or broadcast it to the batch form (False).

    Shape:
        - Input: :math:`(C, H, W)` or :math:`(B, C, H, W)`
        - Output: :math:`(B, C, H, W)`

    .. note::
        This function internally uses :func:`kornia.geometry.transform.warp_affine`.

    Examples:
        >>> import torch
        >>> rng = torch.manual_seed(0)
        >>> input = torch.rand(1, 1, 3, 3)
        >>> aug = RandomShear((-5., 2., 5., 10.), p=1.)
        >>> out = aug(input)
        >>> out, aug.transform_matrix
        (tensor([[[[0.4403, 0.7614, 0.1516],
                  [0.1753, 0.3074, 0.6127],
                  [0.4438, 0.8924, 0.4061]]]]), tensor([[[ 1.0000,  0.0100, -0.0100],
                 [-0.1183,  0.9988,  0.1194],
                 [ 0.0000,  0.0000,  1.0000]]]))
        >>> aug.inverse(out)
        tensor([[[[0.4045, 0.7577, 0.1393],
                  [0.2071, 0.3074, 0.5582],
                  [0.3958, 0.8868, 0.4265]]]])

    To apply the exact augmenation again, you may take the advantage of the previous parameter state:
        >>> input = torch.randn(1, 3, 32, 32)
        >>> aug = RandomShear((-15., 20.), p=1.)
        >>> (aug(input) == aug(input, params=aug._params)).all()
        tensor(True)

    Fg      ?shearresamplesame_on_batchalign_cornerspadding_modepkeepdimreturnNc                    s<   t  j|||d t|| _t|t||d| _d S )N)r   r   r   )r   r   r   )	super__init__rgShearGenerator_param_generatorr	   getr
   flags)selfr   r   r   r   r   r   r   	__class__ [/home/ubuntu/.local/lib/python3.10/site-packages/kornia/augmentation/_2d/geometric/shear.pyr   N   s   
zRandomShear.__init__inputparamsr   c              	   C   sJ   t t|d |j|jdtt|d |j|jdtt|d |j|jdS )Ncenterdevicedtypeshear_xshear_y)r   r   r)   r*   r   )r    r%   r&   r   r#   r#   r$   compute_transformation`   s
   z"RandomShear.compute_transformation	transformc                 C   sr   |j \}}}}t|tstdt| dt||d d d dd d f ||f|d j |d |d j dS )N*Expected the `transform` be a Tensor. Got .   r   r   r   )r   r   )shape
isinstancer   	TypeErrortyper   namelower)r    r%   r&   r   r.   _heightwidthr#   r#   r$   apply_transformg   s   
zRandomShear.apply_transformsizec                 C   s@   t |tstdt| d| j|| jt||j|jd|dS )Nr/   r0   r(   )r&   r.   r   )	r3   r   r4   r5   r;   _paramsr   r)   r*   )r    r%   r   r.   r<   r#   r#   r$   inverse_transformw   s   
zRandomShear.inverse_transform)N)NN)__name__
__module____qualname____doc__r	   BILINEARr6   r
   ZEROSr   r   floatr   strintboolr   r   r   r-   r   r;   r>   __classcell__r#   r#   r!   r$   r      sf    4"	*



r   N)typingr   r   r   r   r   kornia.augmentationr   r   &kornia.augmentation._2d.geometric.baser   kornia.constantsr	   r
   kornia.corer   r   kornia.geometry.conversionsr   kornia.geometry.transformr   r   r   r#   r#   r#   r$   <module>   s   