Color Transformation and Blending

In the final pipeline stage, the pixels from the previous pipeline stage (paint generation or image interpolation) are optionally transformed by a color transformation matrix. The resulting pixels are converted into the destination color space, and blending is performed using a subset of the standard Porter-Duff blending rules along with several additional rules.


Color Transformation [13.1]

If the VG_COLOR_TRANSFORM parameter is enabled, each color from the preceding pipeline stage is converted to non-premultiplied form. Each channel is multiplied by a per-channel scale factor, and a per-channel bias is added; the results for each channel are clamped to the range [0, 1]:

A'= clamp(A * ScaleA + BiasA, 0, 1)
R'= clamp(R * ScaleR + BiasR, 0, 1)
G'= clamp(G * ScaleG + BiasG, 0, 1)
B'= clamp(B * ScaleB + BiasB, 0, 1)

Scale and bias values are input in floating point format but are then modified as follows:

The color transformation is set as a vector of 8 floats, consisting of the R, G, B, A scale factors followed by the R, G, B, A biases:

/* Sr, Sg, Sb, Sa, Br, Bg, Bb, Ba */
VGfloat values[] = { 1.0, 1.0, 1.0, 1.0, 0.0, 0.0, 0.0, 0.0 };
vgSetfv(VG_COLOR_TRANSFORM_VALUES, 8, values);
vgSeti(VG_COLOR_TRANSFORM, VG_TRUE);

Blending Equations [13.2]

Blending modes define alpha and color blending functions.
Alpha blending function is formally defined as α(αsrc, αdst).
Color blending function is formally defined as c(csrc, cdst, αsrc, αdst).
Premultiplied alpha form is formally defined as c'(αsrc * csrc, αdst * cdst, αsrc, αdst) = c'(c'src, c'dst, αsrc, αdst) The VGBlendMode enumeration defines the possible blending modes:

Blend ModeColor blending function
c'(c'src, c'dst, αsrc, αdst)
Apha blending function α(αsrc, αdst)
VG_BLEND_SRCc'srcαsrc
VG_BLEND_SRC_OVERc'src + c'dst * (1 – αsrc)αsrc + αdst * (1 – αsrc)
VG_BLEND_DST_OVERc'src * (1 – αdst) + c'dstαsrc * (1 – αdst) + αdst
VG_BLEND_SRC_INc'src * αdstαsrc * αdst
VG_BLEND_DST_INc'dst * αsrcαdst * αsrc
VG_BLEND_MULTIPLYc'src * (1 - αdst) + c'dst * (1 - αsrc) + c'src * c'dstαsrc + αdst * (1 – αsrc)
VG_BLEND_SCREENc'src + c'dst – c'src * c'dstαsrc + αdst * (1 – αsrc)
VG_BLEND_DARKENmin(c'src + c'dst * (1 – αsrc), c'dst + c'src * (1 – αdst))αsrc + αdst * (1 – αsrc)
VG_BLEND_LIGHTENmax(c'src + c'dst * (1 – αsrc), c'dst + c'src * (1 – αdst))αsrc + αdst * (1 – αsrc)
VG_BLEND_ADDITIVEmin(c'src + c'dst, 1)min(αsrc + αdst, 1)

Example (set a “source over” blend mode):

vgSeti(VG_BLEND_MODE, VG_BLEND_SRC_OVER);