o
    9i)                     @   s@  d dl Z d dlZd dlmZmZmZ d dlZd dlZd dl	m
Z
 d dlmZ d dlmZ d dlmZ d dlmZ d dlmZ G d	d
 d
ZdZdd eedd D ZeeZdd Zdd ZG dd dZ					d%dee dee fddZd&deeef fddZd&dejfdd Zg i d!ddddfd"efd#d$Z dS )'    N)ListOptionalUnion)	rearrange)WatermarkEncoder)
ListConfig)Image)autocast)append_dimsc                   @   s*   e Zd Zdd ZdejdejfddZdS )WatermarkEmbedderc                 C   s,   || _ tt| _t | _| jd| j  d S )Nbits)	watermarklenWATERMARK_BITSnum_bitsr   encoderset_watermark)selfr    r   ?/data/cameron/vidgen/generative-models/sgm/inference/helpers.py__init__   s   
zWatermarkEmbedder.__init__imagereturnc              
   C   s   t |jdk}|r|d }|jd }td|   d dddddddddf }t|jd D ]}| j|| d||< q5t	
t|dddddddddf d	|d
|j}t	j|d ddd}|rp|d }|S )z
        Adds a predefined watermark to the input image

        Args:
            image: ([N,] B, RGB, H, W) in range [0, 1]

        Returns:
            same as input but watermarked
           )N.r      zn b c h w -> (n b) h w cNdwtDctz(n b) h w c -> n b c h w)n              ?minmax)r   shaper   detachcpunumpyranger   encodetorch
from_numpytodeviceclamp)r   r   squeezer   image_npkr   r   r   __call__   s(   

 *zWatermarkEmbedder.__call__N)__name__
__module____qualname__r   r)   Tensorr1   r   r   r   r   r      s    r   l   1 O c                 C      g | ]}t |qS r   )int).0bitr   r   r   
<listcomp>9       r:      c                 C   s   t dd | jD S )Nc                 S   s   h | ]}|j qS r   )	input_key)r8   xr   r   r   	<setcomp>>   s    z<get_unique_embedder_keys_from_conditioner.<locals>.<setcomp>)list	embedders)conditionerr   r   r   )get_unique_embedder_keys_from_conditioner=   s   rC   c                 C   s   t jt j| dd tt t j| }t|}|D ]&}dt| 	 d }t
|tjt j| |dd |d7 }qd S )NT)exist_okg     o@zc h w -> h w c09z.png   )osmakedirspathjoinr   listdirembed_watermarkr   r%   r&   r   	fromarrayastypenpuint8save)	save_pathsamples
base_countsampler   r   r   perform_save_locallyA   s   
rV   c                   @   s(   e Zd ZdZd	defddZdd ZdS )
Img2ImgDiscretizationWrapperz
    wraps a discretizer, and prunes the sigmas
    params:
        strength: float between 0.0 and 1.0. 1.0 means full sampling (all sigmas are returned)
    r   strengthc                 C   s.   || _ || _d| j  krdksJ  J d S )Nr   r   )discretizationrX   )r   rY   rX   r   r   r   r   T   s   "z%Img2ImgDiscretizationWrapper.__init__c                 O   s~   | j |i |}td| t|d}|d tt| jt| d }tdtt| jt| d t|d}td| |S )Nz5sigmas after discretization, before pruning img2img: )r   rF   zprune index:zsigmas after pruning: )rY   printr)   flipr"   r7   rX   r   )r   argskwargssigmasr   r   r   r1   Y   s   
 
z%Img2ImgDiscretizationWrapper.__call__N)r   )r2   r3   r4   __doc__floatr   r1   r   r   r   r   rW   M   s    rW   Fcudaforce_uc_zero_embeddingsbatch2model_inputc              
      sd  |d u rg }|	d u rg }	t   t}  gttj|\}}|D ].}t|| t jr?t	||| j
 q,t|| trSt	|dd || D  q,t	|||  q,jj|||d\}}|D ]dkstfdd||f\|< |< qhi  |	D ]|  < qt||| || f}t |} fdd}|||||d	}|}t j|d
 d dd
d}|d ur||}|
r||fW  d    W  d    W  d    S |W  d    W  d    W  d    S 1 sw   Y  W d    n1 sw   Y  W d    d S W d    d S 1 s+w   Y  d S )Nc                 S   r6   r   )r   )r8   lr   r   r   r:      r;   zdo_sample.<locals>.<listcomp>batch_ucrb   	crossattnc                    s   |  d t   S N)mathprodr+   yr,   r0   num_samplesr   r   <lambda>   s    zdo_sample.<locals>.<lambda>c                    s   j j| ||fi  S rh   denoisermodel)inputsigmac)additional_model_inputsrr   r   r   rq      s
   
zdo_sample.<locals>.denoiserconducr          @r   r    )r)   no_gradr	   	ema_scope	get_batchrC   rB   
isinstancer5   rZ   r#   r@   get_unconditional_conditioningmapri   rj   randnr+   decode_first_stager-   )rr   sampler
value_dictrn   HWCFrb   rc   return_latentsfilterr,   precision_scopebatchrf   keyru   ry   r#   r   rq   	samples_z	samples_xrS   r   )rv   r,   r0   rr   rn   r   	do_samplee   sn   



1 $r   Nc                 C   s  i }i }| D ]}|dkr5t j|d gt|d| |d< t j|d gt|d| |d< q|dkrRt|d |d g|jg |dR  |d< q|d	krot|d
 |d g|jg |dR  |d	< q|dkrt|d g|jg |dR  |d< t|d g|jg |dR  |d< q|dkrt|d |d g|jg |dR  |d< q|| ||< q|	 D ]}||vrt
|| tjrt|| ||< q||fS )Ntxtprompt)repeatsnegative_promptoriginal_size_as_tupleorig_height
orig_widthrF   crop_coords_top_leftcrop_coords_topcrop_coords_leftaesthetic_scorenegative_aesthetic_scoretarget_size_as_tupletarget_heighttarget_width)rO   repeatri   rj   reshapetolistr)   tensorr+   keysr~   r5   clone)r   r   r   r,   r   rf   r   r   r   r   r}      s|   $r}   r   c                 C   s   | j \}}td| d| d tdd ||f\}}| ||f} t| d}|d  ddd	d
}t	|j
tjdd d }|
|S )Nzloaded input image of size (z, )c                 S   s   | | d  S )N@   r   )r>   r   r   r   ro      s    z(get_input_image_tensor.<locals>.<lambda>RGBr      rF   r<   )dtypeg     _@r   )sizerZ   r   resizerO   arrayconvert	transposer)   r*   r+   float32)r   r,   whwidthheightimage_arrayimage_tensorr   r   r   get_input_image_tensor   s   

r   r   offset_noise_levelc              
      sJ  t   t }  ttj|g\}}jj|||d\}}|D ]t fdd||f\|< |< q)|D ]|  |< |< qA|	rS| }n	| }t 
|}||j}|d |j}|dkr||tt j|jd |jd|j  }||t||j  }|t d|d d   }fd	d
}|||||d}|}t j|d d ddd}|
d ur|
|}|r||fW  d    W  d    W  d    S |W  d    W  d    W  d    S 1 sw   Y  W d    n1 sw   Y  W d    d S W d    d S 1 sw   Y  d S )Nre   c                    s   |  d    S rh   )r+   rk   rm   r   r   ro     s    zdo_img2img.<locals>.<lambda>r   r   )r,   r   rz   c                    s      j| ||S rh   rp   )r>   rt   ru   )rr   r   r   rq   %  s   zdo_img2img.<locals>.denoiserrw   r    )r)   r{   r	   r|   r}   rC   rB   r   r   encode_first_stage
randn_likerY   	num_stepsr+   r,   r
   r   r#   ndimsqrtr   r-   )imgrr   r   r   rn   rb   additional_kwargsr   r   skip_encoder   r,   r   r   rf   ru   ry   znoiser^   rt   noised_zrq   r   r   rS   r   )r,   r0   rr   rn   r   
do_img2img   sf   


(


0 $r   )NNFNra   )ra   )!ri   rG   typingr   r   r   r&   rO   r)   einopsr   imwatermarkr   	omegaconfr   PILr   r	   sgm.utilr
   r   WATERMARK_MESSAGEbinr   rL   rC   rV   rW   r   r}   r   r`   r   r   r   r   r   <module>   sP    '!	

H9