This thread has been locked.
If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.
This is a query regarding overlay blending functionality in GC320 driver using Vivante 2D APIs.
Our requirement is to overlay an ARGB surface(src) on top of another ARGB surface (dst) with blending.
When the src surface pixel alpha value is 0x00, a completely transparent src surface, with no components of src contributing to final output is required.
Also when src surface alpha is 0xff, a completely opaque src surface, with no components of dst in the overlapping area in the final output is required.
We are able to implement blending using two methods:
1) Pixel level alpha value adjustment, with global alpha disabled
2) Global alpha value adjustment, with pixel alpha values set to 0xff for both src and dst surfaces.
Our observation is that when blending is done using pixel level alpha with global alpha disabled(method 1), src surface components were not completely transparent when src pixel alpha values were 0x00. Please note in this case the dst pixel alpha value is always 0xFF.
When we were adjusting global alpha value, with individual pixel alpha values set to 0xff(method 2), we were able to achieve the desired result.
Can the same be achieved using individual pixel level alpha value?
Sample code snippet used for both modes, and the respective outputs are attached in this mail.
Gal2DAlphaBlending_pixelAlpha.c has the code which implements the blending using pixel level alpha values with global alpha disabled.
Corresponding output is gal2DAlphaBlending_PixelAlpha.bmp
Gal2DAlphaBlending_globalAlpha.c has the global alpha mode enabled and pixel level alpha for both src and dst are set to 0xff.
Corresponding output is gal2DAlphaBlendingGlobalAlpha.bmp
In the above code snippet, desiredSrcAlpha is the alpha value needed for src surface overlay.
The desired output in our use case is gal2DAlphaBlendingGlobalAlpha.bmp (method 2).
Is it possible to achieve the same result with pixel level alpha blending(method 1) as it is in global alpha blending(method 2).
Note:
The code snippet is modified version of AlphaBlending /001 sample from ti_dra7x_gc320-unified-driver example.
Hi,
In the example code, some of the factors are set differently leading up to different blend equations.
In the case of global alpha the final blend equation is getting evaluated to `Cb = Cd` hence you see the solid red rectangle, where as for the pixel alpha case its getting evaluated to `Cb = Cs + Cd` hence the red + pink rectangle.
Try changing the following in pixel alpha example
```
gcmONERROR(gco2D_EnableAlphaBlendAdvanced(egn2D,
gcvSURF_PIXEL_ALPHA_INVERSED, gcvSURF_PIXEL_ALPHA_STRAIGHT,
gcvSURF_GLOBAL_ALPHA_OFF, gcvSURF_GLOBAL_ALPHA_OFF,
gcvSURF_BLEND_STRAIGHT, gcvSURF_BLEND_STRAIGHT));
```
to the following to get to the same result as of global alpha
```
gcmONERROR(gco2D_EnableAlphaBlendAdvanced(egn2D,
gcvSURF_PIXEL_ALPHA_INVERSED, gcvSURF_PIXEL_ALPHA_INVERSED,
gcvSURF_GLOBAL_ALPHA_OFF, gcvSURF_GLOBAL_ALPHA_OFF,
gcvSURF_BLEND_STRAIGHT, gcvSURF_BLEND_STRAIGHT));
```
As to why, its easier to consider the blending ops by its genarlized equation and set the parameters accordingly to get to your final desired output
```
Cb = Fs * Cs' + Fd * Cd'
Ad = Fs * As'' + Fd * Ad''
Fs: source factor
Fd: dest factor
Cs': source color
Cd': dest color
As'': source alpha
Ad'': dest alpha
```
`gco2D_EnableAlphaBlendAdvanced()` takes in blend mode variables that determine how `As''` and `Fs` values are calculated. Below are the scenarios for different config options
```
As' = As if gcvSURF_PIXEL_ALPHA_STRAIGHT
= (1-As) if gcvSURF_PIXEL_ALPHA_INVERSED
As'' = As' if gcvSURF_GLOBAL_ALPHA_OFF
= Ags if gcvSURF_GLOBAL_ALPHA_ON
= As' * Ags if gcvSURF_GLOBAL_ALPHA_SCALE
```
similarly for `Ad''`
```
Fs = 0 if gcvSURF_BLEND_ZERO
= 1 if gcvSURF_BLEND_ONE
= Ad'' if gcvSURF_BLEND_STRAIGHT (notice that its dest for Fs and src for Fd)
= (1-Ad'') if gcvSURF_BLEND_INVERSED
```
similarly for `Fd`
`gco2DSetPixelMultiplyModeAdvanced()` determines how the `Cs'` values are calculated based on the options given to it
```
Cs' = Cs * As if gcv2D_COLOR_MULTIPLY_ENABLE (for pixel level alpha)
= Cs * Ags if gcv2D_COLOR_MULTIPLY_ENABLE (for global alpha)
= Cs * As * Ags if gcv2D_COLOR_MULTIPLY_ENABLE (for both pixel and global alpha)
```
you can also specify if you want the destination color to be pre-multiplied or not.
Considering above in the global alpha example, the following are set as pixel and global alphas
```
gcmONERROR(gco2D_EnableAlphaBlendAdvanced(egn2D,
gcvSURF_PIXEL_ALPHA_STRAIGHT, gcvSURF_PIXEL_ALPHA_STRAIGHT,
gcvSURF_GLOBAL_ALPHA_ON, gcvSURF_GLOBAL_ALPHA_ON,
gcvSURF_BLEND_STRAIGHT, gcvSURF_BLEND_STRAIGHT));
```
```
As = 1
Ad = 1
Ags = 1
Agd = 0
As' = As
Ad' = Ad
As'' = Ags * As' = 1
Ad'' = Agd * Ad' = 0
Cs' = Cs
Cd' = Cd
Cb = Ad'' * Cs' + As'' * Cd' = Cd (red rectangle)
```
In the case of per pixel alpha
```
gcmONERROR(gco2D_EnableAlphaBlendAdvanced(egn2D,
gcvSURF_PIXEL_ALPHA_INVERSED, gcvSURF_PIXEL_ALPHA_STRAIGHT,
gcvSURF_GLOBAL_ALPHA_OFF, gcvSURF_GLOBAL_ALPHA_OFF,
gcvSURF_BLEND_STRAIGHT, gcvSURF_BLEND_STRAIGHT));
As = 0
Ad = 1
Ags = 0
Agd = 0
As' = 1 - As = 1
Ad' = Ad = 1
As'' = As'
Ad'' = Ad'
Cs' = Cs
Cd' = Cd
Cb = Ad'' * Cs' + As'' * Cd' = Cs + Cd
```
Hope this helps.
Thanks,
Gowtham
Hi Gowtham,
Thanks for the details.
I have a doubt whether the said modes for pixel level alpha blending will help in achieving the desired results in all scenarios.
Consider the case with alpha modes set to gcvSURF_PIXEL_ALPHA_INVERSED for both src and dst , as you mentioned :
gcmONERROR(gco2D_EnableAlphaBlendAdvanced(egn2D,
gcvSURF_PIXEL_ALPHA_INVERSED, gcvSURF_PIXEL_ALPHA_INVERSED,
gcvSURF_GLOBAL_ALPHA_OFF, gcvSURF_GLOBAL_ALPHA_OFF,
gcvSURF_BLEND_STRAIGHT, gcvSURF_BLEND_STRAIGHT));
Consider the blending equation:
Cb = Fs * Cs' + Fd * Cd'
Ad = Fs * As'' + Fd * Ad''
Scenario 1: Src alpha is 0 (Expected output: Only dst surface components should be present in the overlapping output regions)
Values for the above parameters would be:
Fs = (1 - 1)
Fd = (1 - 0)
Cb = 0 * Cs + 1 * Cd = (Cd)
Ad = 0 * 1 + 1 * 0 = 0
The output will not have any src components as expected.
Scenario 2: src alpha is 0.5 (Expected output: 50 % of the src components should be present in the overlapping output regions)
Values for the above parameters would be:
Fs = ( 1 - 1)
Fd = (1 - 0.5)
Cb = 0 * Cs + 0.5 * Cd = (0.5 *Cd)
Ad = 0 * 0.5 + 0.5 * 0 = 0
The output will have 50 % of dst components with no src components present.
Scenario 3:Src alpha is 1(Expected output is only src components should be present in the overlapping output regions)
Values for the above parameters would be:
Fs = (1 – 1)
Fd = (1 - 1)
Cb = 0 * Cs + 0 * Cd = 0
Ad = 0 * 0 + 0 * 0 = 0
In this case, the output will be a blank screen.
Note:
In all the above cases dst surface alpha is always set as 1.
--Regards
Thushara Jayakumar