1
- import torch
2
- from torch import Tensor
3
1
import math
2
+ import numbers
3
+ import warnings
4
+ from collections .abc import Iterable
5
+
6
+ import numpy as np
7
+ from numpy import sin , cos , tan
4
8
from PIL import Image , ImageOps , ImageEnhance , __version__ as PILLOW_VERSION
9
+
10
+ import torch
11
+ from torch import Tensor
12
+ from torch .jit .annotations import List
13
+
5
14
try :
6
15
import accimage
7
16
except ImportError :
8
17
accimage = None
9
- import numpy as np
10
- from numpy import sin , cos , tan
11
- import numbers
12
- from collections .abc import Sequence , Iterable
13
- import warnings
14
18
15
19
from . import functional_pil as F_pil
16
20
from . import functional_tensor as F_t
@@ -342,20 +346,24 @@ def scale(*args, **kwargs):
342
346
return resize (* args , ** kwargs )
343
347
344
348
345
- def pad (img , padding , fill = 0 , padding_mode = 'constant' ):
346
- r"""Pad the given PIL Image on all sides with specified padding mode and fill value.
349
+ def pad (img : Tensor , padding : List [int ], fill : int = 0 , padding_mode : str = "constant" ) -> Tensor :
350
+ r"""Pad the given image on all sides with the given "pad" value.
351
+ The image can be a PIL Image or a torch Tensor, in which case it is expected
352
+ to have [..., H, W] shape, where ... means an arbitrary number of leading dimensions
347
353
348
354
Args:
349
- img (PIL Image): Image to be padded.
350
- padding (int or tuple): Padding on each border. If a single int is provided this
355
+ img (PIL Image or Tensor ): Image to be padded.
356
+ padding (int or tuple or list ): Padding on each border. If a single int is provided this
351
357
is used to pad all borders. If tuple of length 2 is provided this is the padding
352
358
on left/right and top/bottom respectively. If a tuple of length 4 is provided
353
- this is the padding for the left, top, right and bottom borders
354
- respectively.
355
- fill: Pixel fill value for constant fill. Default is 0. If a tuple of
359
+ this is the padding for the left, top, right and bottom borders respectively.
360
+ In torchscript mode padding as single int is not supported, use a tuple or
361
+ list of length 1: ``[padding, ]``.
362
+ fill (int or str or tuple): Pixel fill value for constant fill. Default is 0. If a tuple of
356
363
length 3, it is used to fill R, G, B channels respectively.
357
- This value is only used when the padding_mode is constant
364
+ This value is only used when the padding_mode is constant. Only int value is supported for Tensors.
358
365
padding_mode: Type of padding. Should be: constant, edge, reflect or symmetric. Default is constant.
366
+ Only "constant" is supported for Tensors as of now.
359
367
360
368
- constant: pads with a constant value, this value is specified with fill
361
369
@@ -372,68 +380,12 @@ def pad(img, padding, fill=0, padding_mode='constant'):
372
380
will result in [2, 1, 1, 2, 3, 4, 4, 3]
373
381
374
382
Returns:
375
- PIL Image: Padded image.
383
+ PIL Image or Tensor : Padded image.
376
384
"""
377
- if not _is_pil_image (img ):
378
- raise TypeError ('img should be PIL Image. Got {}' .format (type (img )))
379
-
380
- if not isinstance (padding , (numbers .Number , tuple )):
381
- raise TypeError ('Got inappropriate padding arg' )
382
- if not isinstance (fill , (numbers .Number , str , tuple )):
383
- raise TypeError ('Got inappropriate fill arg' )
384
- if not isinstance (padding_mode , str ):
385
- raise TypeError ('Got inappropriate padding_mode arg' )
386
-
387
- if isinstance (padding , Sequence ) and len (padding ) not in [2 , 4 ]:
388
- raise ValueError ("Padding must be an int or a 2, or 4 element tuple, not a " +
389
- "{} element tuple" .format (len (padding )))
390
-
391
- assert padding_mode in ['constant' , 'edge' , 'reflect' , 'symmetric' ], \
392
- 'Padding mode should be either constant, edge, reflect or symmetric'
393
-
394
- if padding_mode == 'constant' :
395
- if isinstance (fill , numbers .Number ):
396
- fill = (fill ,) * len (img .getbands ())
397
- if len (fill ) != len (img .getbands ()):
398
- raise ValueError ('fill should have the same number of elements '
399
- 'as the number of channels in the image '
400
- '({}), got {} instead' .format (len (img .getbands ()), len (fill )))
401
- if img .mode == 'P' :
402
- palette = img .getpalette ()
403
- image = ImageOps .expand (img , border = padding , fill = fill )
404
- image .putpalette (palette )
405
- return image
406
-
407
- return ImageOps .expand (img , border = padding , fill = fill )
408
- else :
409
- if isinstance (padding , int ):
410
- pad_left = pad_right = pad_top = pad_bottom = padding
411
- if isinstance (padding , Sequence ) and len (padding ) == 2 :
412
- pad_left = pad_right = padding [0 ]
413
- pad_top = pad_bottom = padding [1 ]
414
- if isinstance (padding , Sequence ) and len (padding ) == 4 :
415
- pad_left = padding [0 ]
416
- pad_top = padding [1 ]
417
- pad_right = padding [2 ]
418
- pad_bottom = padding [3 ]
419
-
420
- if img .mode == 'P' :
421
- palette = img .getpalette ()
422
- img = np .asarray (img )
423
- img = np .pad (img , ((pad_top , pad_bottom ), (pad_left , pad_right )), padding_mode )
424
- img = Image .fromarray (img )
425
- img .putpalette (palette )
426
- return img
427
-
428
- img = np .asarray (img )
429
- # RGB image
430
- if len (img .shape ) == 3 :
431
- img = np .pad (img , ((pad_top , pad_bottom ), (pad_left , pad_right ), (0 , 0 )), padding_mode )
432
- # Grayscale image
433
- if len (img .shape ) == 2 :
434
- img = np .pad (img , ((pad_top , pad_bottom ), (pad_left , pad_right )), padding_mode )
385
+ if not isinstance (img , torch .Tensor ):
386
+ return F_pil .pad (img , padding = padding , fill = fill , padding_mode = padding_mode )
435
387
436
- return Image . fromarray (img )
388
+ return F_t . pad (img , padding = padding , fill = fill , padding_mode = padding_mode )
437
389
438
390
439
391
def crop (img , top , left , height , width ):
0 commit comments