- iOS 13.0+
- Xcode 11.3+
This sample builds on the Converting Luminance and Chrominance Planes to an ARGB Image sample to leverage the lower-level, high-performance YpCbCr to RGB conversion functions provided by vImage to add additional, real-time video effects to a live camera stream.
Two effects are implemented in the YpCbCr color space:
Two effects are implemented in the RGB color space:
Color quantization using lookup tables.
You can easily adjust the color saturation of a YpCbCr image, without affecting its luminance, using the following formula:
You use the
v function to perform this math on the source chrominance buffer. The following code prepares the source chrominance buffer—which contains two planes for Cb and Cr—for use as the source and destination of the matrix multiply function:
Pass the pre-bias (–128), and then multiply by the divisor both the post-bias (+128) and the saturation. The saturation is passed to the matrix multiply function as a single element matrix:
With the parameters prepared, call
v to perform the saturation adjustment formula to the chrominance planes:
In this sample, dithering is applied only to the luminance channel: converting the grayscale image to a pattern of black dots. To eliminate the chrominance information, the dithering step uses the previous saturation adjustment step, with the saturation set to zero.
vImage provides dithering when reducing the bit depth of an image. In this sample, you convert the 8-bit luminance channel to a dithered 1-bit image, and then convert that back to 8-bit to pass to the YpCbCr to RGB function.
To create the 1-bit buffer, you initialize a
v structure, specifying one bit per pixel:
vImage offers several dithering algorithms, this sample uses Atkinson dithering that’s specified by passing
kv to the 8-bit to 1-bit conversion function. Because the luminance buffer is planar, use
v to do the conversion:
dithered populated with the 1-bit dithered image, convert it back to 8-bit, specifying the original 8-bit luminance buffer,
source, as the destination:
Once you’re finished with the 1-bit planar buffer, free its memory:
Rotate the Image
vImage supports two types of specialized rotation functions—those that rotate an image in discrete 90º steps and those that rotate an image by an arbitrary angle. This sample uses the latter and specifies opaque white as the background color. Define the rotation, in radians, with the
fx floating point variable::
Quantize Color Using Lookup Tables
Mapping the individual channel values of an 8-bit per-channel image to a reduced set of values (for example, mapping the range 0…255 to the values
[0, 25, 50, 75, 100, 125, 150, 175, 200, 225, 255]) decreases the number of distinct colors in an image. This process is known as color quantization and can be used for special effects or other applications such as compression.
vImage includes lookup table functions that provide this functionality. In this sample, generate the look up table dynamically based on a
quantization value of 25,
look contains 25 of each of the values in
[0, 25, 50, 75, 100, 125, 150, 175, 200, 225, 255]. Passing
lookup as the red, green, and blue lookup table parameters to
v maps all of the red, green, and blue values between 0 and 24 to 0, between 25 and 49 to 25, between 50 and 74 to 50, and so on: