kwimage.im_alphablend module

Numpy implementation of alpha blending based on information in [SO25182421] and [WikiAlphaBlend].

References

SO25182421

http://stackoverflow.com/questions/25182421/overlay-numpy-alpha

WikiAlphaBlend

https://en.wikipedia.org/wiki/Alpha_compositing#Alpha_blending

kwimage.im_alphablend.overlay_alpha_layers(layers, keepalpha=True, dtype=<class 'numpy.float32'>)[source]

Stacks a sequences of layers on top of one another. The first item is the topmost layer and the last item is the bottommost layer.

Parameters
  • layers (Sequence[ndarray]) – stack of images

  • keepalpha (bool) – if False, the alpha channel is removed after blending

  • dtype (np.dtype) – format for blending computation (defaults to float32)

Returns

raster: the blended images

Return type

ndarray

Example

>>> import kwimage
>>> keys = ['astro', 'carl', 'stars']
>>> layers = [kwimage.grab_test_image(k, dsize=(100, 100)) for k in keys]
>>> layers = [kwimage.ensure_alpha_channel(g, alpha=.5) for g in layers]
>>> stacked = kwimage.overlay_alpha_layers(layers)
>>> # xdoctest: +REQUIRES(--show)
>>> import kwplot
>>> kwplot.autompl()
>>> kwplot.imshow(stacked)
>>> kwplot.show_if_requested()
_images/fig_kwimage_im_alphablend_overlay_alpha_layers_002.jpeg
kwimage.im_alphablend.overlay_alpha_images(img1, img2, keepalpha=True, dtype=<class 'numpy.float32'>, impl='inplace')[source]

Places img1 on top of img2 respecting alpha channels. Works like the Photoshop layers with opacity.

Parameters
  • img1 (ndarray) – top image to overlay over img2

  • img2 (ndarray) – base image to superimpose on

  • keepalpha (bool) – if False, the alpha channel is removed after blending

  • dtype (np.dtype) – format for blending computation (defaults to float32)

  • impl (str) – code specifying the backend implementation

Returns

raster: the blended images

Return type

ndarray

Todo

  • [ ] Make fast C++ version of this function

Example

>>> import kwimage
>>> img1 = kwimage.grab_test_image('astro', dsize=(100, 100))
>>> img2 = kwimage.grab_test_image('carl', dsize=(100, 100))
>>> img1 = kwimage.ensure_alpha_channel(img1, alpha=.5)
>>> img3 = kwimage.overlay_alpha_images(img1, img2)
>>> # xdoctest: +REQUIRES(--show)
>>> import kwplot
>>> kwplot.autompl()
>>> kwplot.imshow(img3)
>>> kwplot.show_if_requested()
_images/fig_kwimage_im_alphablend_overlay_alpha_images_002.jpeg
kwimage.im_alphablend.ensure_alpha_channel(img, alpha=1.0, dtype=<class 'numpy.float32'>, copy=False)[source]

Returns the input image with 4 channels.

Parameters
  • img (ndarray) – an image with shape [H, W], [H, W, 1], [H, W, 3], or [H, W, 4].

  • alpha (float | ndarray) – default scalar value for missing alpha channel, or an ndarray with the same height / width to use explicitly.

  • dtype (type) – The final output dtype. Should be numpy.float32 or numpy.float64.

  • copy (bool) – always copy if True, else copy if needed.

Returns

an image with specified dtype with shape [H, W, 4].

Return type

ndarray

Raises

ValueError - if the input image does not have 1, 3, or 4 input channels – or if the image cannot be converted into a float01 representation

Example

>>> # Demo with a scalar default alpha value
>>> import kwimage
>>> data0 = np.zeros((5, 5))
>>> data1 = np.zeros((5, 5, 1))
>>> data2 = np.zeros((5, 5, 3))
>>> data3 = np.zeros((5, 5, 4))
>>> ensured0 = kwimage.ensure_alpha_channel(data0, alpha=0.5)
>>> ensured1 = kwimage.ensure_alpha_channel(data1, alpha=0.5)
>>> ensured2 = kwimage.ensure_alpha_channel(data2, alpha=0.5)
>>> ensured3 = kwimage.ensure_alpha_channel(data3, alpha=0.5)
>>> assert np.all(ensured0[..., 3] == 0.5), 'should have been populated'
>>> assert np.all(ensured1[..., 3] == 0.5), 'should have been populated'
>>> assert np.all(ensured2[..., 3] == 0.5), 'should have been populated'
>>> assert np.all(ensured3[..., 3] == 0.0), 'last image already had alpha'

Example

>>> import kwimage
>>> # Demo with a explicit alpha channel
>>> alpha = np.random.rand(5, 5)
>>> data0 = np.zeros((5, 5))
>>> data1 = np.zeros((5, 5, 1))
>>> data2 = np.zeros((5, 5, 3))
>>> data3 = np.zeros((5, 5, 4))
>>> ensured0 = kwimage.ensure_alpha_channel(data0, alpha=alpha)
>>> ensured1 = kwimage.ensure_alpha_channel(data1, alpha=alpha)
>>> ensured2 = kwimage.ensure_alpha_channel(data2, alpha=alpha)
>>> ensured3 = kwimage.ensure_alpha_channel(data3, alpha=alpha)
>>> assert np.all(ensured0[..., 3] == alpha), 'should have been populated'
>>> assert np.all(ensured1[..., 3] == alpha), 'should have been populated'
>>> assert np.all(ensured2[..., 3] == alpha), 'should have been populated'
>>> assert np.all(ensured3[..., 3] == 0.0), 'last image already had alpha'