libdragon
Macros | Typedefs
rdpq_macros.h File Reference

RDP command macros. More...

Go to the source code of this file.

Macros

#define RDPQ_COMB0_MASK   ((cast64(0xF)<<52)|(cast64(0x1F)<<47)|(cast64(0x7)<<44)|(cast64(0x7)<<41)|(cast64(0xF)<<28)|(cast64(0x7)<<15)|(cast64(0x7)<<12)|(cast64(0x7)<<9))
 Combiner: mask to isolate settings related to cycle 0.
 
#define RDPQ_COMB1_MASK   (~RDPQ_COMB0_MASK & cast64(0x00FFFFFFFFFFFFFF))
 Combiner: mask to isolate settings related to cycle 1.
 
#define RDPQ_COMBINER_2PASS   (cast64(1)<<63)
 Flag to mark the combiner as requiring two passes. More...
 
#define RDPQ_COMBINER1(rgb, alpha)
 Build a 1-pass combiner formula. More...
 
#define RDPQ_COMBINER2(rgb0, alpha0, rgb1, alpha1)
 Build a 2-pass combiner formula. More...
 
#define RDPQ_BLENDER(bl)
 Build a 1-pass blender formula. More...
 
#define RDPQ_BLENDER2(bl0, bl1)
 Build a 2-pass blender formula. More...
 
Standard color combiners

These macros offer some standard color combiner configuration that can be used to implement common render modes.

#define RDPQ_COMBINER_FLAT   RDPQ_COMBINER1((0,0,0,PRIM), (0,0,0,PRIM))
 Draw a flat color. Configure the color via rdpq_set_prim_color.
 
#define RDPQ_COMBINER_SHADE   RDPQ_COMBINER1((0,0,0,SHADE), (0,0,0,SHADE))
 Draw an interpolated color. This can be used for solid, non-textured triangles with per-vertex lighting (gouraud shading). The colors must be specified on each vertex. Only triangles allow to specify a per-vertex color, so you cannot draw rectangles with this.
 
#define RDPQ_COMBINER_TEX   RDPQ_COMBINER1((0,0,0,TEX0), (0,0,0,TEX0))
 Draw with a texture. This is standard texture mapping, without any lights. It can be used for rectangles (rdpq_texture_rectangle) or triangles (rdpq_triangle).
 
#define RDPQ_COMBINER_TEX_FLAT   RDPQ_COMBINER1((TEX0,0,PRIM,0), (TEX0,0,PRIM,0))
 Draw with a texture modulated with a flat color. Configure the color via rdpq_set_prim_color. More...
 
#define RDPQ_COMBINER_TEX_SHADE   RDPQ_COMBINER1((TEX0,0,SHADE,0), (TEX0,0,SHADE,0))
 Draw with a texture modulated with an interpolated color. This does texturing with gouraud shading, and can be used for textured triangles with per-vertex lighting. More...
 
SET_OTHER_MODES bit macros

These macros can be used to assemble a raw SET_OTHER_MODES command to send via rdpq_set_other_modes_raw (or rdpq_change_other_modes_raw). Assembling this command manually can be complex because of the different intertwined render modes that can be created. Beginners should look into the RDPQ mode API before (rdpq_mode.h),

rdpq stores some special flag within unused bits of this register. These flags are defined using the prefix SOMX_.

#define SOMX_NUMLODS_MASK   ((cast64(7))<<59)
 Rdpq extension: number of LODs.
 
#define SOMX_NUMLODS_SHIFT   59
 Rdpq extension: number of LODs shift.
 
#define SOM_ATOMIC_PRIM   ((cast64(1))<<55)
 Atomic: serialize command execution.
 
#define SOM_CYCLE_1   ((cast64(0))<<52)
 Set cycle-type: 1cyc.
 
#define SOM_CYCLE_2   ((cast64(1))<<52)
 Set cycle-type: 2cyc.
 
#define SOM_CYCLE_COPY   ((cast64(2))<<52)
 Set cycle-type: copy.
 
#define SOM_CYCLE_FILL   ((cast64(3))<<52)
 Set cycle-type: fill.
 
#define SOM_CYCLE_MASK   ((cast64(3))<<52)
 Cycle-type mask.
 
#define SOM_CYCLE_SHIFT   52
 Cycle-type shift.
 
#define SOM_TEXTURE_PERSP   (cast64(1)<<51)
 Texture: enable perspective correction.
 
#define SOM_TEXTURE_DETAIL   (cast64(1)<<50)
 Texture: enable "detail".
 
#define SOM_TEXTURE_SHARPEN   (cast64(1)<<49)
 Texture: enable "sharpen".
 
#define SOM_TEXTURE_LOD   (cast64(1)<<48)
 Texture: enable LODs.
 
#define SOM_TEXTURE_LOD_SHIFT   48
 Texture: LODs shift.
 
#define SOM_TLUT_NONE   (cast64(0)<<46)
 TLUT: no palettes.
 
#define SOM_TLUT_RGBA16   (cast64(2)<<46)
 TLUT: draw with palettes in format RGB16.
 
#define SOM_TLUT_IA16   (cast64(3)<<46)
 TLUT: draw with palettes in format IA16.
 
#define SOM_TLUT_MASK   (cast64(3)<<46)
 TLUT mask.
 
#define SOM_TLUT_SHIFT   46
 TLUT mask shift.
 
#define SOM_SAMPLE_POINT   (cast64(0)<<44)
 Texture sampling: point sampling (1x1)
 
#define SOM_SAMPLE_BILINEAR   (cast64(2)<<44)
 Texture sampling: bilinear interpolation (2x2)
 
#define SOM_SAMPLE_MEDIAN   (cast64(3)<<44)
 Texture sampling: mid-texel average (2x2)
 
#define SOM_SAMPLE_MASK   (cast64(3)<<44)
 Texture sampling mask.
 
#define SOM_SAMPLE_SHIFT   44
 Texture sampling mask shift.
 
#define SOM_TF0_RGB   (cast64(1)<<43)
 Texture Filter, cycle 0 (TEX0): standard fetching (for RGB)
 
#define SOM_TF0_YUV   (cast64(0)<<43)
 Texture Filter, cycle 0 (TEX0): fetch nearest and do first step of color conversion (for YUV)
 
#define SOM_TF1_RGB   (cast64(2)<<41)
 Texture Filter, cycle 1 (TEX1): standard fetching (for RGB)
 
#define SOM_TF1_YUV   (cast64(0)<<41)
 Texture Filter, cycle 1 (TEX1): fetch nearest and do first step of color conversion (for YUV)
 
#define SOM_TF1_YUVTEX0   (cast64(1)<<41)
 Texture Filter, cycle 1 (TEX1): don't fetch, and instead do color conversion on TEX0 (allows YUV with bilinear filtering)
 
#define SOM_TF_MASK   (cast64(7)<<41)
 Texture Filter mask.
 
#define SOM_TF_SHIFT   41
 Texture filter mask shift.
 
#define SOM_RGBDITHER_SQUARE   ((cast64(0))<<38)
 RGB Dithering: square filter.
 
#define SOM_RGBDITHER_BAYER   ((cast64(1))<<38)
 RGB Dithering: bayer filter.
 
#define SOM_RGBDITHER_NOISE   ((cast64(2))<<38)
 RGB Dithering: noise.
 
#define SOM_RGBDITHER_NONE   ((cast64(3))<<38)
 RGB Dithering: none.
 
#define SOM_RGBDITHER_MASK   ((cast64(3))<<38)
 RGB Dithering mask.
 
#define SOM_RGBDITHER_SHIFT   38
 RGB Dithering mask shift.
 
#define SOM_ALPHADITHER_SAME   ((cast64(0))<<36)
 Alpha Dithering: same as RGB.
 
#define SOM_ALPHADITHER_INVERT   ((cast64(1))<<36)
 Alpha Dithering: invert pattern compared to RG.
 
#define SOM_ALPHADITHER_NOISE   ((cast64(2))<<36)
 Alpha Dithering: noise.
 
#define SOM_ALPHADITHER_NONE   ((cast64(3))<<36)
 Alpha Dithering: none.
 
#define SOM_ALPHADITHER_MASK   ((cast64(3))<<36)
 Alpha Dithering mask.
 
#define SOM_ALPHADITHER_SHIFT   36
 Alpha Dithering mask shift.
 
#define SOMX_FOG   ((cast64(1))<<32)
 RDPQ special state: fogging is enabled.
 
#define SOMX_UPDATE_FREEZE   ((cast64(1))<<33)
 RDPQ special state: render mode update is frozen (see rdpq_mode_begin)
 
#define SOMX_AA_REDUCED   ((cast64(1))<<34)
 RDPQ special state: reduced antialiasing is enabled.
 
#define SOMX_LOD_INTERPOLATE   ((cast64(1))<<35)
 RDPQ special state: mimap interpolation (aka trilinear) requested.
 
#define SOM_BLEND0_MASK   (cast64(0xCCCC0000) | SOM_BLENDING | SOM_READ_ENABLE | SOMX_BLEND_2PASS)
 Blender: mask of settings related to pass 0.
 
#define SOM_BLEND1_MASK   (cast64(0x33330000) | SOM_BLENDING | SOM_READ_ENABLE | SOMX_BLEND_2PASS)
 Blender: mask of settings related to pass 1.
 
#define SOM_BLEND_MASK   (SOM_BLEND0_MASK | SOM_BLEND1_MASK)
 Blender: mask of all settings.
 
#define SOMX_BLEND_2PASS   ((cast64(1))<<15)
 RDPQ special state: record that the blender is made of 2 passes.
 
#define SOM_BLENDING   ((cast64(1))<<14)
 Activate blending for all pixels.
 
#define SOM_BLALPHA_CC   ((cast64(0))<<12)
 Blender IN_ALPHA is the output of the combiner output (default)
 
#define SOM_BLALPHA_CVG   ((cast64(2))<<12)
 Blender IN_ALPHA is the coverage of the current pixel.
 
#define SOM_BLALPHA_CVG_TIMES_CC   ((cast64(3))<<12)
 Blender IN_ALPHA is the product of the combiner output and the coverage.
 
#define SOM_BLALPHA_MASK   ((cast64(3))<<12)
 Blender alpha configuration mask.
 
#define SOM_BLALPHA_SHIFT   12
 Blender alpha configuration shift.
 
#define SOM_ZMODE_OPAQUE   ((cast64(0))<<10)
 Z-mode: opaque surface.
 
#define SOM_ZMODE_INTERPENETRATING   ((cast64(1))<<10)
 Z-mode: interprenating surfaces.
 
#define SOM_ZMODE_TRANSPARENT   ((cast64(2))<<10)
 Z-mode: transparent surface.
 
#define SOM_ZMODE_DECAL   ((cast64(3))<<10)
 Z-mode: decal surface.
 
#define SOM_ZMODE_MASK   ((cast64(3))<<10)
 Z-mode mask.
 
#define SOM_ZMODE_SHIFT   10
 Z-mode mask shift.
 
#define SOM_Z_WRITE   ((cast64(1))<<5)
 Activate Z-buffer write.
 
#define SOM_Z_WRITE_SHIFT   5
 Z-buffer write bit shift.
 
#define SOM_Z_COMPARE   ((cast64(1))<<4)
 Activate Z-buffer compare.
 
#define SOM_Z_COMPARE_SHIFT   4
 Z-buffer compare bit shift.
 
#define SOM_ZSOURCE_PIXEL   ((cast64(0))<<2)
 Z-source: per-pixel Z.
 
#define SOM_ZSOURCE_PRIM   ((cast64(1))<<2)
 Z-source: fixed value.
 
#define SOM_ZSOURCE_MASK   ((cast64(1))<<2)
 Z-source mask.
 
#define SOM_ZSOURCE_SHIFT   2
 Z-source mask shift.
 
#define SOM_ALPHACOMPARE_NONE   ((cast64(0))<<0)
 Alpha Compare: disable.
 
#define SOM_ALPHACOMPARE_THRESHOLD   ((cast64(1))<<0)
 Alpha Compare: use blend alpha as threshold.
 
#define SOM_ALPHACOMPARE_NOISE   ((cast64(3))<<0)
 Alpha Compare: use noise as threshold.
 
#define SOM_ALPHACOMPARE_MASK   ((cast64(3))<<0)
 Alpha Compare mask.
 
#define SOM_ALPHACOMPARE_SHIFT   0
 Alpha Compare mask shift.
 
#define SOM_READ_ENABLE   ((cast64(1)) << 6)
 Enable reads from framebuffer.
 
#define SOM_AA_ENABLE   ((cast64(1)) << 3)
 Enable anti-alias.
 
#define SOM_COVERAGE_DEST_CLAMP   ((cast64(0)) << 8)
 Coverage: add and clamp to 7 (full)
 
#define SOM_COVERAGE_DEST_WRAP   ((cast64(1)) << 8)
 Coverage: add and wrap from 0.
 
#define SOM_COVERAGE_DEST_ZAP   ((cast64(2)) << 8)
 Coverage: force 7 (full)
 
#define SOM_COVERAGE_DEST_SAVE   ((cast64(3)) << 8)
 Coverage: save (don't write)
 
#define SOM_COVERAGE_DEST_MASK   ((cast64(3)) << 8)
 Coverage mask.
 
#define SOM_COVERAGE_DEST_SHIFT   8
 Coverage mask shift.
 
#define SOM_COLOR_ON_CVG_OVERFLOW   ((cast64(1)) << 7)
 Update color buffer only on coverage overflow.
 

Typedefs

typedef uint64_t rdpq_combiner_t
 A combiner formula, created by RDPQ_COMBINER1 or RDPQ_COMBINER2.
 
typedef uint32_t rdpq_blender_t
 A blender formula, created by RDPQ_BLENDER or RDPQ_BLENDER2.
 

Detailed Description

RDP command macros.

This file contains macros that can be used to assembly some complex RDP commands: the blender and the color combiner configurations.

The file is meant to be included also from RSP assembly code, for readability while manipulating these commands.

Macro Definition Documentation

◆ RDPQ_COMBINER_2PASS

#define RDPQ_COMBINER_2PASS   (cast64(1)<<63)

Flag to mark the combiner as requiring two passes.

This is an internal flag used by rdpq to mark combiner configurations that require 2 passes to be executed, and differentiate them from 1 pass configurations.

It is used by rdpq to automatically switch to 2cycle mode when such a combiner is configured.

Application code should not use this macro directly.

◆ RDPQ_COMBINER1

#define RDPQ_COMBINER1 (   rgb,
  alpha 
)

Build a 1-pass combiner formula.

This macro allows to build a 1-pass color combiner formula. In general, the color combiner is able to execute the following per-pixel formula:

 (A - B) * C + D

where A, B, C, D can be configured picking several possible inputs called "slots". Two different formulas (with the same structure but different inputs) must be configured: one for the RGB channels and for the alpha channel.

The macro must be invoked as:

 RDPQ_COMBINER1((A1, B1, C1, D1), (A2, B2, C2, D2))

where A1, B1, C1, D1 define the formula used for RGB channels, while A2, B2, C2, D2 define the formula for the alpha channel. Please notice the double parenthesis.

For example, this macro:

 RDPQ_COMBINER1((TEX0, 0, SHADE, 0), (0, 0, 0, TEX0))

configures the formulas:

 RGB   = (TEX0 - 0) * SHADE + 0    = TEX0 * SHADE
 ALPHA = (0    - 0) * 0     + TEX0 = TEX0

In the RGB channels, the texel color is multiplied by the shade color (which is the per-pixel interpolated vertex color), basically applying gouraud shading. The alpha channel of the texel is instead passed through with no modifications.

The output of the combiner goes into the blender unit, that allows for further operations on the RGB channels, especially allowing to blend it with the framebuffer contents. See RDPQ_BLENDER for information on how to configure the blender.

The values created by RDPQ_COMBINER1 are of type rdpq_combiner_t. They can be used in two different ways:

  • When using the higher-level mode API (rdpq_mode.h), pass it to rdpq_mode_combiner. This will take care of everything else required to make the combiner work (eg: render mode tweaks). See the documentation of rdpq_mode_combiner for more information.
  • When using the lower-level API (rdpq_set_combiner_raw), the combiner is configured into RDP, but it is up to the programmer to make sure the current render mode is compatible with it, or tweak it by calling rdpq_set_other_modes_raw. For instance, if the render mode is in 2-cycle mode, only a 2-pass combiner should be set.

This is the list of all possible slots. Not all slots are available for the four variables (see the table below).

  • TEX0: texel of the texture being drawn.
  • SHADE: per-pixel interpolated color. This can be set on each vertex of a triangle, and is interpolated across each pixel. It cannot be used while drawing rectangles.
  • PRIM: value of the PRIM register (set via rdpq_set_prim_color)
  • ENV: value of the ENV register (set via rdpq_set_env_color)
  • NOISE: a random value
  • 1: the constant value 1.0
  • 0: the constant value 0.0
  • K4: the constant value configured as k4 as part of YUV parameters (via rdpq_set_yuv_parms).
  • K5: the constant value configured as k5 as part of YUV parameters (via rdpq_set_yuv_parms).
  • TEX0_ALPHA: alpha of the text of the texture being drawn.
  • SHADE_ALPHA: alpha of the per-pixel interpolated color.
  • PRIM_ALPHA: alpha of the PRIM register (set via rdpq_set_prim_color)
  • ENV_ALPHA: alpha of the ENV register (set via rdpq_set_env_color)
  • LOD_FRAC: the LOD fraction, that is the fractional value that can be used as interpolation value between different mipmaps. It basically says how much the texture is being scaled down.
  • PRIM_LOD_FRAC
  • KEYCENTER
  • KEYSCALE

These tables show, for each possible variable of the RGB and ALPHA formula, which slots are allowed:

RGB ATEX0, SHADE, PRIM, ENV, NOISE, 1, 0
B TEX0, SHADE, PRIM, ENV, KEYCENTER, K4, 0
C TEX0, SHADE, PRIM, ENV, TEX0_ALPHA, SHADE_ALPHA, PRIM_ALPHA, ENV_ALPHA, LOD_FRAC, PRIM_LOD_FRAC, K5, 'KEYSCALE', 0
DTEX0, SHADE, PRIM, ENV, 1, 0
ALPHA ATEX0, SHADE, PRIM, ENV, 1, 0
BTEX0, SHADE, PRIM, ENV, 1, 0
CTEX0, SHADE, PRIM, ENV, LOD_FRAC, PRIM_LOD_FRAC, 0
DTEX0, SHADE, PRIM, ENV, 1, 0

For instance, to draw a gouraud-shaded textured triangle, one might want to calculate the following combiner formula:

   RGB   = TEX0 * SHADE
   ALPHA = TEX0 * SHADE

which means that for all channels, we multiply the value sampled from the texture with the per-pixel interpolated color coming from the triangle vertex. To do so, we need to adapt the formula to the 4-variable combiner structure:

   RGB   = (TEX0 - 0) * SHADE + 0
   ALPHA = (TEX0 - 0) * SHADE + 0

To program this into the combiner, we can issue the following command:

   rdpq_mode_combiner(RDPQ1_COMBINER((TEX0, 0, SHADE, 0), (TEX0, 0, SHADE, 0)));

Notice that this is just a way to obtain the formula above. Another possibility is:

   rdpq_mode_combiner(RDPQ1_COMBINER((1, 0, SHADE, TEX0), (1, 0, SHADE, TEX0)));

which will obtain exactly the same result.

A complete example drawing a textured rectangle with a fixed semi-transparency of 0.7:

// Set standard mode
// Set a combiner to sample TEX0 as-is in RGB channels, and put a fixed value
// as alpha channel, coming from the ENV register.
rdpq_mode_combiner(RDPQ_COMBINER1((ZERO, ZERO, ZERO, TEX0), (ZERO, ZERO, ZERO, ENV)));
// Set the fixed value in the ENV register. RGB components are ignored as the slot
// ENV is not used in the RGB combiner formula, so we just put zero there.
rdpq_set_env_color(RGBA32(0, 0, 0, 0.7*255));
// Activate blending with the background
rdpq_mode_blender(RDPQ_BLENDER(IN_RGB, ENV_ALPHA, MEMORY_RGB, INV_MUX_ALPHA));
// Load the texture in TMEM
rdpq_tex_load(TILE0, texture, 0);
// Draw the rectangle
0, 0, 100, 80,
0, 0, 1.f, 1.0f);
#define RGBA32(rx, gx, bx, ax)
Create a color_t from the R,G,B,A components in the RGBA32 range (0-255).
Definition: graphics.h:49
void rdpq_set_env_color(color_t color)
Set the RDP ENV combiner register (RDP command: SET_ENV_COLOR)
Definition: rdpq.h:1065
@ TILE0
Tile #0 (for code readability)
Definition: rdpq.h:250
#define RDPQ_BLENDER(bl)
Build a 1-pass blender formula.
Definition: rdpq_macros.h:826
#define RDPQ_COMBINER1(rgb, alpha)
Build a 1-pass combiner formula.
Definition: rdpq_macros.h:429
void rdpq_mode_blender(rdpq_blender_t blend)
Configure the formula to use for blending.
Definition: rdpq_mode.h:591
void rdpq_mode_combiner(rdpq_combiner_t comb)
Configure the color combiner.
Definition: rdpq_mode.h:465
void rdpq_set_mode_standard(void)
Reset render mode to standard.
Definition: rdpq_mode.c:92
#define rdpq_texture_rectangle(tile, x0, y0, x1, y1, s, t)
Draw a textured rectangle (RDP command: TEXTURE_RECTANGLE)
Definition: rdpq_rect.h:293
Parameters
[in]rgbThe RGB formula as (A, B, C, D)
[in]alphaThe ALPHA formula as (A, B, C, D)
See also
rdpq_mode_combiner
rdpq_set_combiner_raw
RDPQ_COMBINER2
RDPQ_BLENDER

◆ RDPQ_COMBINER2

#define RDPQ_COMBINER2 (   rgb0,
  alpha0,
  rgb1,
  alpha1 
)

Build a 2-pass combiner formula.

This is similar to RDPQ_COMBINER1, but it creates a two-passes combiner. The combiner unit in RDP in fact allows up to two sequential combiner formulas that can be applied to each pixel.

In the second pass, you can refer to the output of the first pass using the COMBINED slot (not available in the first pass).

Refer to RDPQ_COMBINER1 for more information.

See also
rdpq_mode_combiner
rdpq_set_combiner_raw
RDPQ_COMBINER1
RDPQ_BLENDER

◆ RDPQ_COMBINER_TEX_FLAT

#define RDPQ_COMBINER_TEX_FLAT   RDPQ_COMBINER1((TEX0,0,PRIM,0), (TEX0,0,PRIM,0))

Draw with a texture modulated with a flat color. Configure the color via rdpq_set_prim_color.

Among other uses, this mode is the correct one to colorize a FMT_IA8 and FMT_IA4 texture with a fixed color.

◆ RDPQ_COMBINER_TEX_SHADE

#define RDPQ_COMBINER_TEX_SHADE   RDPQ_COMBINER1((TEX0,0,SHADE,0), (TEX0,0,SHADE,0))

Draw with a texture modulated with an interpolated color. This does texturing with gouraud shading, and can be used for textured triangles with per-vertex lighting.

This mode makes sense only for triangles with per-vertex colors. It should not be used with rectangles.

◆ RDPQ_BLENDER

#define RDPQ_BLENDER (   bl)

Build a 1-pass blender formula.

This macro allows to build a 1-pass blender formula. In general, the blender is able to execute the following per-pixel formula:

 (P * A) + (Q * B)

where P and Q are usually pixel inputs, while A and B are blending factors. P, Q, A, B can be configured picking several possible inputs called "slots".

The macro must be invoked as:

 RDPQ_BLENDER((P, A, Q, B))

where P, A, Q, B can be any of the values described below. Please notice the double parenthesis.

For example, this macro:

 RDPQ_BLENDER((IN_RGB, IN_ALPHA, MEMORY_RGB, 1))

configures the formula:

 (IN_RGB * IN_ALPHA) + (MEMORY_RGB * 1.0)

The value created is of type rdpq_blender_t. They can be used in two different ways:

  • When using the higher-level mode API (rdpq_mode.h), the blender formula can be passed to either rdpq_mode_fog or rdpq_mode_blender. The blender unit is in fact capable of running up two passes in sequence, so each function configures one different pass.
  • When using the lower-level API (rdpq_set_other_modes_raw), the value created by RDPQ_BLENDER can be directly combined with other SOM_* macros to create the final value to pass to the function. If a two-pass blender must be configured, use RDPQ_BLENDER2 instead.

Pre-made formulas for common scenarios are available: see RDPQ_BLENDER_MULTIPLY, RDPQ_BLENDER_ADDITIVE, RDPQ_FOG_STANDARD.

These are all possible inputs for P and Q:

  • IN_RGB: The RGB channels of the pixel being drawn. This is actually the output of the color combiner (that can be configured via rdpq_mode_combiner, RDPQ_COMBINER1, and RDPQ_COMBINER2).
  • MEMORY_RGB: Current contents of the framebuffer, where the current pixel will be drawn. Reading the framebuffer contents and using them in the formula allows to create the typical blending effect.
  • BLEND_RGB: A fixed RGB value programmed into the BLEND register. This can be configured via rdpq_set_blend_color.
  • FOG_RGB: A fixed RGB value programmed into the FOG register. This can be configured via rdpq_set_fog_color.

These are all possible inputs for A:

  • IN_ALPHA: The alpha channel of the pixel being drawn. This is actually the output of the color combiner (that can be configured via rdpq_mode_combiner, RDPQ_COMBINER1, and RDPQ_COMBINER2).
  • FOG_ALPHA: The alpha channel of the FOG register. This can be configured via rdpq_set_fog_color.
  • SHADE_ALPHA: The alpha channel of the shade color. The shade component is the color optionally set on each vertex when drawing a triangle (see rdpq_triangle). The RDP interpolates it on each pixel.
  • 0: the constant value 0.

These are all possible inputs for B:

  • INV_MUX_ALPHA: This value is the inverse of whatever input was selected for A. For instance, if A was configured as FOG_ALPHA, setting B to INV_MUX_ALPHA means using 1.0 - FOG_ALPHA in the calculation. This basically allows to do a linear interpolation between P and Q where A is the interpolation factor.
  • MEMORY_CVG: This is the subpixel coverage value stored in the framebuffer at the position where the current pixel will be drawn. The coverage is normally stored as a value in the range 0-7, but the blender normalizes in the range 0.0-1.0.
  • 1: the constant value 1.
  • 0: the constant value 0.

The blender uses the framebuffer precision for the RGB channels: when drawing to a 32-bit framebuffer, P and Q will have 8-bit precision per channel, whilst when drawing to a 16-bit framebuffer, P and Q will be 5-bit. You can add dithering if needed, via rdpq_mode_dithering.

On the other hand, A and B always have a reduced 5-bit precision, even on 32-bit framebuffers. This means that the alpha values will be quantized during the blending, possibly creating mach banding. Consider using dithering via rdpq_mode_dithering to improve the quality of the picture.

Notice that the blender formula only works on RGB channels. Alpha channels can be used as input (as multiplicative factor), but the blender does not produce an alpha channel as output. In fact, the RGB output will be written to the framebuffer after the blender, while the bits normally used for alpha in each framebuffer pixel will contain information about subpixel coverage (that will be then used by VI for doing antialiasing as a post-process filter – see rdpq_mode_antialias for a brief explanation).

See also
rdpq_mode_blender
rdpq_mode_fog
rdpq_mode_dithering
rdpq_set_fog_color
rdpq_set_blend_color
rdpq_set_other_modes_raw

◆ RDPQ_BLENDER2

#define RDPQ_BLENDER2 (   bl0,
  bl1 
)

Build a 2-pass blender formula.

This macro is similar to RDPQ_BLENDER, but it can be used to build a two-passes blender formula. This formula can be then configured using the mode API via rdpq_mode_blender, or using the lower-level API via rdpq_change_other_modes_raw.

Refer to RDPQ_BLENDER for information on how to build a blender formula.

In two-passes mode, there are a few differences and gotchas in the way the formula must be constructed:

  • In the first pass, B must be INV_MUX_ALPHA (any other value is invalid and will result in a compile-time error).
  • In the first pass, MEMORY_RGB is not available.
  • In the second pass, IN_RGB is not available, but you can instead use CYCLE1_RGB to refer to the output of the first cycle. IN_ALPHA is still available (as the blender does not produce a alpha output, so the input alpha is available also in the second pass).
  • In the second pass, because of a hardware bug, SHADE_ALPHA will actually refer to the alpha color of the next pixel in the scanline (the pixel to the right). On the last pixel of the triangle in each scanline, the value read as SHADE_ALPHA is mostly undefined. Given this hardware bug, avoid using SHADE_ALPHA in the second pass if possible.
See also
RDPQ_BLENDER
rdpq_mode_blender
rdpq_set_other_modes_raw