View Source NxImage (NxImage v0.1.2)

Image processing in Nx.

All functions expect images to be tensors in either HWC or CHW order, with an arbitrary number of leading batch axes.

All transformations preserve the input type, rounding if necessary. For higher precision, cast the input to floating-point beforehand.

Summary

Transformation

Crops an image at the center.

Normalizes an image according to the given per-channel mean and standard deviation.

Scales an image such that the short edge matches the given size.

Conversion

Converts values from continuous range into pixel values (0-255).

Converts pixel values (0-255) into a continuous range.

Transformation

Link to this function

center_crop(input, size, opts \\ [])

View Source

Crops an image at the center.

If the image is too small to be cropped to the desired size, it gets padded with zeros.

Options

  • :channels - channels location, either :first or :last. Defaults to :last

Examples

iex> image = Nx.iota({4, 4, 1}, type: :u8)
iex> NxImage.center_crop(image, {2, 2})
#Nx.Tensor<
  u8[2][2][1]
  [
    [
      [5],
      [6]
    ],
    [
      [9],
      [10]
    ]
  ]
>

iex> image = Nx.iota({2, 2, 1}, type: :u8)
iex> NxImage.center_crop(image, {1, 4})
#Nx.Tensor<
  u8[1][4][1]
  [
    [
      [0],
      [0],
      [1],
      [0]
    ]
  ]
>
Link to this function

normalize(input, mean, std, opts \\ [])

View Source

Normalizes an image according to the given per-channel mean and standard deviation.

  • :channels - channels location, either :first or :last. Defaults to :last

Examples

iex> image = Nx.iota({2, 2, 3}, type: :f32)
iex> mean = Nx.tensor([0.485, 0.456, 0.406])
iex> std = Nx.tensor([0.229, 0.224, 0.225])
iex> NxImage.normalize(image, mean, std)
#Nx.Tensor<
  f32[2][2][3]
  [
    [
      [-2.1179039478302, 2.4285714626312256, 7.084444522857666],
      [10.982532501220703, 15.821427345275879, 20.41777801513672]
    ],
    [
      [24.08296775817871, 29.214284896850586, 33.7511100769043],
      [37.183406829833984, 42.607139587402344, 47.08444595336914]
    ]
  ]
>
Link to this function

resize(input, size, opts \\ [])

View Source

Resizes an image.

Options

  • :method - the resizing method to use, either of :nearest, :bilinear, :bicubic, :lanczos3, :lanczos5. Defaults to :bilinear

  • :antialias - whether an anti-aliasing filter should be used when downsampling. This has no effect with upsampling. Defaults to true

  • :channels - channels location, either :first or :last. Defaults to :last

Examples

iex> image = Nx.iota({2, 2, 1}, type: :u8)
iex> NxImage.resize(image, {3, 3}, method: :nearest)
#Nx.Tensor<
  u8[3][3][1]
  [
    [
      [0],
      [1],
      [1]
    ],
    [
      [2],
      [3],
      [3]
    ],
    [
      [2],
      [3],
      [3]
    ]
  ]
>

iex> image = Nx.iota({2, 2, 1}, type: :f32)
iex> NxImage.resize(image, {3, 3}, method: :bilinear)
#Nx.Tensor<
  f32[3][3][1]
  [
    [
      [0.0],
      [0.5],
      [1.0]
    ],
    [
      [1.0],
      [1.5],
      [2.0]
    ],
    [
      [2.0],
      [2.5],
      [3.0]
    ]
  ]
>
Link to this function

resize_short(input, size, opts \\ [])

View Source

Scales an image such that the short edge matches the given size.

Options

  • :method - the resizing method to use, same as resize/2

  • :antialias - whether an anti-aliasing filter should be used when downsampling. This has no effect with upsampling. Defaults to true

  • :channels - channels location, either :first or :last. Defaults to :last

Examples

iex> image = Nx.iota({2, 4, 1}, type: :u8)
iex> resized_image = NxImage.resize_short(image, 3, method: :nearest)
iex> Nx.shape(resized_image)
{3, 6, 1}

iex> image = Nx.iota({4, 2, 1}, type: :u8)
iex> resized_image = NxImage.resize_short(image, 3, method: :nearest)
iex> Nx.shape(resized_image)
{6, 3, 1}

Conversion

Link to this function

from_continuous(input, min, max)

View Source

Converts values from continuous range into pixel values (0-255).

Examples

iex> image = Nx.tensor([[[0.0], [0.5]], [[0.75], [1.0]]])
iex> NxImage.from_continuous(image, 0.0, 1.0)
#Nx.Tensor<
  u8[2][2][1]
  [
    [
      [0],
      [128]
    ],
    [
      [191],
      [255]
    ]
  ]
>

iex> image = Nx.tensor([[[-1.0], [0.0]], [[0.5], [1.0]]])
iex> NxImage.from_continuous(image, -1.0, 1.0)
#Nx.Tensor<
  u8[2][2][1]
  [
    [
      [0],
      [128]
    ],
    [
      [191],
      [255]
    ]
  ]
>
Link to this function

to_continuous(input, min, max)

View Source

Converts pixel values (0-255) into a continuous range.

Examples

iex> image = Nx.tensor([[[0], [128]], [[191], [255]]])
iex> NxImage.to_continuous(image, 0.0, 1.0)
#Nx.Tensor<
  f32[2][2][1]
  [
    [
      [0.0],
      [0.501960813999176]
    ],
    [
      [0.7490196228027344],
      [1.0]
    ]
  ]
>

iex> image = Nx.tensor([[[0], [128]], [[191], [255]]])
iex> NxImage.to_continuous(image, -1.0, 1.0)
#Nx.Tensor<
  f32[2][2][1]
  [
    [
      [-1.0],
      [0.003921627998352051]
    ],
    [
      [0.49803924560546875],
      [1.0]
    ]
  ]
>