4.1. Shader Stage
The vertex shader and geometry shader are configured in the shader stage by functions defined in the nn::gd::ShaderStage
class.
The following figure provides an overview of the settings made in the shader stage.
Applications load vertex shaders and geometry shaders as precompiled shader binary files. A shader binary file can contain one or more vertex shader and geometry shader programs.
To access a particular shader in a shader binary file, pass the loaded shader binary file to the nn::gd::ShaderStage::CreateShaderBinary()
function and then use the ShaderBinary
object that is generated.
static nnResult nn::gd::ShaderStage::CreateShaderBinary( const void* shaderBytecode, u32 bytecodeLength, nn::gd::ShaderBinary** shaderBinary);
Specify the starting address of the buffer storing the loaded shader binary code in the shaderBytecode
parameter, and specify the size of the code (in bytes) in the bytecodeLength
parameter.
Use the pointer that you receive from shaderBinary
to access the ShaderBinary
object that you have created.
Use the nn::gd::ShaderStage::CreateShader()
function to create a Shader
object for accessing the shader program contained within the ShaderBinary
object. A Shader
object represents the code for a single shader (either a vertex shader or a geometry shader).
static nnResult nn::gd::ShaderStage::CreateShader( nn::gd::ShaderBinary* shaderBinary, u32 shaderBinaryIndex, nn::gd::Shader** shader);
If the ShaderBinary
object specified in the shaderBinary
parameter has multiple shader programs, specify the shader program index in the shaderBinaryIndex
parameter to create a Shader
object.
The function sets a pointer in the shader
parameter to the created Shader
object.
Call the nn::gd::ShaderStage::CreateShaderPipeline()
function with one or two Shader
objects to create a ShaderPipeline
object that you can use to apply the shader programs to the pipeline.
static nnResult nn::gd::ShaderStage::CreateShaderPipeline( nn::gd::Shader* vertexShader, nn::gd::Shader* geometryShader, nn::gd::ShaderPipeline** shaderPipeline, nn::gd::ShaderPipelineUnmanagedRegisters* unmanagedRegister = NULL); static nnResult nn::gd::ShaderStage::SetShaderPipeline( nn::gd::ShaderPipeline* shaderPipeline);
Use the vertexShader
parameter to specify the Shader
object to use as the vertex shader. Use the geometryShader
parameter to specify the Shader
object to use as the geometry shader, or NULL
if a geometry shader is not required.
Use the unmanagedRegister
parameter to specify a range of registers for which the library will not automatically generate commands. For more information about this setting, see 4.1.2. Commands Automatically Generated by the Library to Set Registers.
The GD library does not check whether the vertex shader outputs the proper vertex attributes to the geometry shader. To ensure that the vertex attributes output by the vertex shader match the vertex attributes used as input to the geometry shader, create a ShaderPipeline
object with the correct combination of Shader
objects.
The following sample code first creates a ShaderPipeline
object that only uses a vertex shader, and then applies that object to the pipeline.
nn::gd::ShaderBinary* shaderBinary = 0; nn::gd::ShaderPipeline* shaderPipeline = 0; nn::gd::Shader* vertexShader = 0; nn::gd::ShaderStage::CreateShaderBinary( shaderBinaryFileBuffer, bufferSize, &shaderBinary); nn::gd::ShaderStage::CreateShader(shaderBinary, 0, &vertexShader); nn::gd::ShaderStage::CreateShaderPipeline(vertexShader, NULL, &shaderPipeline); nn::gd::ShaderStage::SetShaderPipeline(shaderPipeline);
4.1.1. Configuring Registers for Shader Settings
A ShaderPipeline
object maintains values configured for floating-point constant registers and other registers that are used for shader settings. The GD library allows you to use shader stage functions to change register values for shader settings. These functions update variables that are temporarily saved as the international state of the ShaderPipeline
object, and are not output to the 3D command buffer until a render command request.
The following table shows which functions to use to set values in different types of registers.
Type of Register | Function |
---|---|
Floating-point constant register | nn::gd::ShaderStage::SetShaderPipelineConstantFloat |
Boolean register | nn::gd::ShaderStage::SetShaderPipelineConstantBoolean |
Integer register | nn::gd::ShaderStage::SetShaderPipelineConstantInteger |
static nnResult nn::gd::ShaderStage::SetShaderPipelineConstantFloat( nn::gd::ShaderPipeline* shaderPipeline, nn::gd::UniformLocation uniformLocation, f32* v); static nnResult nn::gd::ShaderStage::SetShaderPipelineConstantBoolean( nn::gd::ShaderPipeline* shaderPipeline, nn::gd::UniformLocation uniformLocation, u16 v, u32 count); static nnResult nn::gd::ShaderStage::SetShaderPipelineConstantInteger( nn::gd::ShaderPipeline* shaderPipeline, nn::gd::UniformLocation uniformLocation, u8* v); static nn::gd::UniformLocation nn::gd::ShaderStage::GetShaderUniformLocation( nn::gd::ShaderPipeline* shaderPipeline, const char* name);
Get a UniformLocation
object using the nn::gd::ShaderStage::GetShaderUniformLocation()
function, and then use the object to specify which register value to change. Use the name
parameter to specify the name of the uniform setting when getting the object. The IsValid()
function of the UniformLocation
object returns a value of 1
when the correct uniform setting has been obtained.
4.1.2. Commands Automatically Generated by the Library to Set Registers
Commands to set registers are normally generated automatically when a different ShaderPipeline
object (from the one currently being applied) is applied to the pipeline. However, performance may be improved in some cases by generating commands that write directly to the registers, rather than having commands generated automatically.
The nn::gd::ShaderStage::SetFloatConstantBuffer()
function takes this into account and allows you to change register settings independently.
static nnResult nn::gd::ShaderStage::SetFloatConstantBuffer( nn::gd::ShaderStage::ShaderType shaderType, u32 firstRegisterIndex, u32 registerCount, f32* constantBufferSrc);
This function can only change the value of unmanaged floating-point constant registers, which are not set by automatically generated commands. The range of unmanaged registers is specified by the ShaderPipelineUnmanagedRegisters
object given as the unmanagedRegister
argument when a ShaderPipeline
object is created.
The ShaderPipelineUnmanagedRegisters
class comprises an array of the UnmanagedRegistersInterval
objects and the number of elements in that array. The UnmanagedRegistersInterval
class comprises the shader type (m_ShaderType
), the number of the first unmanaged register (m_FirstUnmanagedRegister
), and the number of unmanaged registers (m_RegisterCount
).
class nn::gd::UnmanagedRegistersInterval { nn::gd::ShaderStage::ShaderType m_ShaderType; u32 m_FirstUnmanagedRegister; u32 m_RegisterCount; }; class nn::gd::ShaderPipelineUnmanagedRegisters { nn::gd::UnmanagedRegistersInterval* m_ArrayUnmanagedRegistersInterval; u32 m_CountUnmanagedRegistersInterval; };
The following sample code shows how to create a ShaderPipeline
object that includes unmanaged registers.
nn::gd::ShaderPipelineUnmanagedRegisters unmanagedRegs; nn::gd::UnmanagedRegistersInterval arrayUnmanagedRegistersInterval[] = { {nn::gd::ShaderStage::SHADER_TYPE_VERTEX, 0, 4}, {nn::gd::ShaderStage::SHADER_TYPE_VERTEX, 4, 3}, {nn::gd::ShaderStage::SHADER_TYPE_VERTEX, 8, 3} }; unmanagedRegs.m_ArrayUnmanagedRegistersInterval = arrayUnmanagedRegistersInterval; unmanagedRegs.m_CountUnmanagedRegistersInterval = 3; nn::gd::ShaderStage::CreateShaderPipeline( s_vertexShader, NULL, &s_shaderPipeline, &unmanagedRegs);
The following code is an example of writing directly to unmanaged registers.
nn::gd::UniformLocation s_shaderVariable_proj = nn::gd::ShaderStage::GetShaderUniformLocation( s_shaderPipeline, "uProjection"); nn::gd::ShaderStage::SetFloatConstantBuffer( nn::gd::ShaderStage::SHADER_TYPE_VERTEX, s_shaderVariable_proj.getRegister(), 4, data);
If a ShaderPipeline
object has already been applied to the pipeline and you apply a new one that was generated from different ShaderBinary
objects, all of the data in the ShaderBinary
objects is output to the 3D command buffer during rendering. Because of the associated processing load, we recommend using unmanaged registers instead to minimize the number of 3D commands that are output.
4.2. Vertex Input Stage
The vertex input stage handles settings related to vertex data (vertex attributes) input to the pipeline. The nn::gd::VertexInputStage
class defines functions that configure these settings.
The following diagram provides an overview of the settings made in the vertex input stage.
4.2.1. Registering Vertex Buffers
Vertex buffers are registered in the vertex input stage's 12 slots. By specifying an array of VertexBufferResource
objects and an array of starting offsets to vertex data, you can register vertex buffers in multiple consecutive slots by making a single call to the nn::gd::VertexInputStage::SetVertexBuffers()
function.
static nnResult nn::gd::VertexInputStage::SetVertexBuffers( u32 startSlot, u32 numBuffers, nn::gd::VertexBufferResource** vertexBuffers, u32* offsets);
Use the startSlot
parameter to specify the first slot number (0–11) for registering a vertex buffer. Use the numBuffers
parameter to specify the number of elements in the array of VertexBufferResource
objects given to vertexBuffers
. Use the offsets
parameter to specify the starting offset for the vertex data array. You must register vertex buffers with the same number of vertex data elements defined by the InputLayout
object (described in 4.2.4. Input Layout).
4.2.2. Using Vertex Indices
When you use vertex indices to render primitives, create a VertexBufferResource
object by specifying an array of vertex indices as resource data, and then call the nn::gd::VertexInputStage::SetIndexBuffer()
function to register that object to the vertex input stage.
static nnResult nn::gd::VertexInputStage::SetIndexBuffer( nn::gd::VertexBufferResource* indexBuffer, nn::gd::VertexInputStage::IndexFormat format, u32 offset);
The VertexBufferResource
object specified for the indexBuffer
parameter is registered to the vertex input stage. When you register VertexBufferResource
objects interleaved with vertex and other data, specify the starting offset (in bytes) of the vertex indices in the offset
parameter.
You can specify one of the following vertex index formats for the format
parameter.
Definition | Description |
---|---|
INDEX_FORMAT_UBYTE |
Vertex indices are treated as an unsigned byte array. |
INDEX_FORMAT_USHORT |
Vertex indices are treated as an unsigned short array. |
4.2.3. Types of Primitives
Use the nn::gd::VertexInputStage::SetPrimitiveTopology()
function to set the type of primitives to render.
static nnResult nn::gd::VertexInputStage::SetPrimitiveTopology( nn::gd::VertexInputStage::PrimitiveTopology primitiveTopology);
Specify one of the following types of primitives for the primitiveTopology
parameter.
Definition | Description |
---|---|
PRIMITIVE_TOPOLOGY_TRIANGLELIST |
Triangles (GL_TRIANGLES ) |
PRIMITIVE_TOPOLOGY_TRIANGLESTRIP |
Triangle strip (GL_TRIANGLE_STRIP ) |
PRIMITIVE_TOPOLOGY_TRIANGLEFAN |
Triangle fan (GL_TRIANGLE_FAN ) |
PRIMITIVE_TOPOLOGY_GEOMETRY |
Geometry shader (GL_GEOMETRY_PRIMITIVE_DMP ) |
4.2.4. Input Layout
An input layout (InputLayout
object) defines how input variables are connected between a vertex shader and vertex buffer. A vertex buffer comprises either a simple scalar value or several interleaved scalar values. Call the nn::gd::VertexInputStage::CreateInputLayout()
function to create an InputLayout
object. This function's parameters include an array of descriptor (InputElementDescription
) objects for the input elements (vertex data) and a Shader
object that was created in the shader stage.
static nnResult nn::gd::VertexInputStage::CreateInputLayout( nn::gd::InputElementDescription* inputElementDescs, u32 numElements, u32* strides, nn::gd::Shader* vertexShader, nn::gd::InputLayout** inputLayout); static nnResult nn::gd::VertexInputStage::ReleaseInputLayout( nn::gd::InputLayout* inputLayout); static nnResult nn::gd::VertexInputStage::SetInputLayout( nn::gd::InputLayout* inputLayout);
Specify an array of descriptor (InputElementDescription
) objects with information on the input elements in inputElementDescs
, and pass the number of descriptor objects in the array to numElements
. For more information about descriptor class settings, see 4.2.4.1. Descriptor Class for InputLayout Objects.
Specify the amount of vertex data used by a single vertex as an array in strides
for each slot number. If all of the input elements are interleaved in a single vertex buffer, this array only has a single element that represents the total size of the input elements. If the input elements are not interleaved, this array has multiple elements for the size of each input element.
Use vertexShader
to specify the Shader
object for the vertex shader.
You can use the nn::gd::VertexInputStage::SetInputLayout()
function to apply a created InputLayout
object to the pipeline.
Use the nn::gd::VertexInputStage::ReleaseInputLayout()
function to release an InputLayout
object that is no longer needed. This also deallocates memory regions that were allocated internally when the CombinerState
object was created.
In the following sample code, an input layout is created from a descriptor class that describes a single vertex buffer with three interleaved input elements. The layout is then applied to the pipeline (vertex input stage).
nn::gd::InputLayout* inputLayout = 0; nn::gd::InputElementDescription descs[] = { { 0, "aPosition", nn::gd::VertexInputStage::STREAM_TYPE_FLOAT, 3, 0 }, { 0, "aColor", nn::gd::VertexInputStage::STREAM_TYPE_FLOAT, 4, sizeof(float) * 3 }, { 0, "aNormal", nn::gd::VertexInputStage::STREAM_TYPE_FLOAT, 3, sizeof(float) * 7 }, }; u32 strides[] = { sizeof(float) * 10 }; nn::gd::VertexInputStage::CreateInputLayout( descs, 3, strides, vertexShader, &inputLayout); nn::gd::VertexInputStage::SetInputLayout(inputLayout);
4.2.4.1. Descriptor Class for InputLayout Objects
This section introduces the members of the descriptor class (InputElementDescription
) for InputLayout
objects and provides setting-related cautions and information.
class nn::gd::InputElementDescription { u32 m_StreamSlot; const char* m_SemanticName; nn::gd::VertexInputStage::ShaderStreamFormatType m_Format; u32 m_Count; u32 m_AlignedByteOffset; static const u32 Append = 0x00080000; };
Slot Number (m_StreamSlot)
The slot number (0–11) used by an input element. To use the same slot number for more than one input element, the vertex buffers registered to that slot number must be interleaved. Slot numbers must be registered consecutively in ascending order, starting at 0.
Input Variable Name (m_SemanticName)
The name of an input variable defined by the vertex shader.
Input Element Data Format (m_Format)
The data format of an input element. Specify one of the values from the following table.
Definition | Description |
---|---|
VertexInputStage::STREAM_TYPE_BYTE |
byte (GL_BYTE ) |
VertexInputStage::STREAM_TYPE_UNSIGNED_BYTE |
unsigned byte (GL_UNSIGNED_BYTE ) |
VertexInputStage::STREAM_TYPE_SHORT |
short (GL_SHORT ) |
VertexInputStage::STREAM_TYPE_FLOAT |
float (GL_FLOAT ) |
Input Element Size (m_Count)
The size of (number of components in) an input element. It can be a value between 1 and 4. Note that this is not the size of the input element in bytes.
Input Element Offset (m_AlignedByteOffset)
The offset (in bytes) to the starting input element. By specifying InputElementDescription::Append
, the offset can be calculated automatically, thus simplifying descriptor class settings.
4.3. Texture Stage
The texture stage creates texture objects and handles texture unit-related settings. The nn::gd::TextureStage
class defines functions that configure these settings.
The following diagram provides an overview of the settings made in the texture stage.
4.3.1. 2D Textures
2D textures are handled by Texture2D
objects in the GD library. A Texture2D
object is created from a single Texture2DResource
object and a descriptor class (Texture2DDescription
). If the Texture2DResource
object has mipmap data, you can use descriptor class settings to specify which levels of mipmap data to use when you create a Texture2D
object. For more information about the descriptor class settings, see 4.3.1.1. Descriptor Class for Texture2D Objects.
You can create and release a Texture2D
object using the following functions.
static nnResult nn::gd::TextureStage::CreateTexture2D( const nn::gd::Texture2DResource* tex2DResource, nn::gd::Texture2DDescription* desc, nn::gd::Texture2D** texture2D); static nnResult nn::gd::TextureStage::ReleaseTexture2D( nn::gd::Texture2D* texture2D);
Only management information is released when a Texture2D
object is released. Texture2DResource
objects are not released.
The following sample code creates a Texture2DResource
object and uses it to create a Texture2D
object.
nn::gd::Texture2DResource* texture2DResource = 0; nn::gd::Texture2DResourceDescription Text2DResDesc = {256, 256, 1, nn::gd::Resource::NATIVE_FORMAT_RGB_888, nn::gd::Memory::LAYOUT_BLOCK_8, nn::gd::Memory::FCRAM}; nn::gd::Resource::CreateTexture2DResource( &Text2DResDesc, data, GD_FALSE, &texture2DResource); nn::gd::Texture2D* texture2D = 0; nn::gd::Texture2DDescription tex2DDesc = {0, 0}; nn::gd::TextureStage::CreateTexture2D( texture2DResource, &tex2DDesc, &texture2D);
4.3.1.1. Descriptor Class for Texture2D Objects
This section introduces the member variables of the descriptor class (Texture2DDescription
) for Texture2D
objects and provides setting-related cautions and information.
class nn::gd::Texture2DDescription { s32 m_MinMipLevelIndex; s32 m_MaxMipLevelIndex; };
Index of the Smallest Mipmap Level (m_MinMipLevelIndex)
This is the mipmap level of the Texture2DResource
object used as the smallest mipmap level of a Texture2D
object. If you set a value of -1
, the largest mipmap level of the Texture2DResource
object is used.
Index of the Largest Mipmap Level (m_MaxMipLevelIndex)
This is the mipmap level of the Texture2DResource
object used as the largest mipmap level of a Texture2D
object. If you set a value of -1
, the largest mipmap level of the Texture2DResource
object is used.
4.3.1.2. Getting Detailed Information About a Texture2D Object
You can use the nn::gd::TextureStage::GetTexture2DProperties()
function to get detailed information (using the Texture2DProperties
class).
static nnResult nn::gd::TextureStage::GetTexture2DProperties( const nn::gd::Texture2D* texture2D, nn::gd::Texture2DProperties* properties);
Although the width, height, mipmap levels, and starting address of resource data may change with the mipmap levels specified when an object was created, they are generally the same as the detailed information for the Texture2DResource
object.
class nn::gd::Texture2DProperties { u32 m_Width; u32 m_Height; u32 m_CountMipLevels; u32 m_PixelSize; nn::gd::Resource::NativeFormat m_Format; nn::gd::Memory::MemoryLayout m_MemLayout; nn::gd::Memory::MemoryLocation m_MemLocation; u8* m_MemAddr; nn::gd::MipmapResourceInfo GetMipmapAddress(u32 mipmapLevel); };
4.3.2. Cube Map Textures
Cube map textures are handled by TextureCube
objects in the GD library. A TextureCube
object is created using six Texture2DResource
objects. As with Texture2D
objects, you can specify which mipmap levels to use. Each face (Texture2DResource
object) of the cube map texture must have the same format, mipmap levels, resolution (which depends on the mipmap level), and memory placement.
You can create and release a TextureCube
object using the following functions.
static nnResult nn::gd::TextureStage::CreateTextureCube( nn::gd::Texture2DResource** tex2DResources, nn::gd::TextureCubeDescription* desc, nn::gd::TextureCube** textureCube); static nnResult nn::gd::TextureStage::ReleaseTextureCube( nn::gd::TextureCube* textureCube);
Specify an array of six Texture2DResource
objects, one for each face of the cube map texture, in the tex2DResources
parameter. These textures are used for the +X, -X, +Y, -Y, +Z, and -Z faces, respectively, from the beginning of the array. Cube map texture faces are specified in the same order as the elements in descriptor class arrays.
Only management information is released when a TextureCube
object is released. Texture2DResource
objects are not released.
4.3.2.1. Descriptor Class for TextureCube Objects
This section introduces the members of the descriptor class (TextureCubeDescription
) for TextureCube
objects and provides setting-related cautions and information.
class nn::gd::TextureCubeDescription { s32 m_MinMipLevelIndex[6]; s32 m_MaxMipLevelIndex[6]; TextureCubeDescription(); TextureCubeDescription(int minMipLevelIndex, int maxMipLevelIndex); };
This class differs from Texture2DDescription
in that it specifies mipmap levels for six faces and has a constructor to simplify the process of doing so.
Index of the Smallest Mipmap Level (m_MinMipLevelIndex)
This is the mipmap level of the Texture2DResource
object used as the smallest mipmap level of a TextureCube
object. If you set a value of -1
, the largest mipmap level of the Texture2DResource
object is used.
The values in the array correspond to the Texture2DResource
objects for the +X, -X, +Y, -Y, +Z, and -Z faces, in that order.
Index of the Largest Mipmap Level (m_MaxMipLevelIndex)
This is the mipmap level of the Texture2DResource
object used as the largest mipmap level of a TextureCube
object. If you set a value of -1
, the largest mipmap level of the Texture2DResource
object is used.
The values in the array correspond to the Texture2DResource
objects for the +X, -X, +Y, -Y, +Z, and -Z faces, in that order.
4.3.2.2. Getting Detailed Information About a TextureCube Object
You can use the nn::gd::TextureStage::GetTextureCubeProperties()
function to get detailed information (using the TextureCubeProperties
class) about a TextureCube
object.
static nnResult nn::gd::TextureStage::GetTextureCubeProperties( const nn::gd::TextureCube* TextureCube, nn::gd::TextureCubeProperties* properties);
This class is the same as Texture2DProperties
with the following exceptions: it maintains the starting address of six faces of resource data and accepts a cube map face in the faceIndex
parameter, to get address information for mipmap data.
class nn::gd::TextureCubeProperties { u32 m_Width; u32 m_Height; u32 m_CountMipLevels; u32 m_PixelSize; nn::gd::Resource::NativeFormat m_Format; nn::gd::Memory::MemoryLayout m_MemLayout; nn::gd::Memory::MemoryLocation m_MemLocation; u8* m_MemAddr[6]; nn::gd::MipmapResourceInfo GetMipmapAddress(u32 faceIndex, u32 mipmapLevel); };
4.3.3. Texture Units
The GD library provides four logical texture units to match the 3DS hardware.
Definition | Types of Textures That Can Be Set |
---|---|
(Texture unit 0) |
2D textures (including gas and shadows) Cube map textures (including shadows) Projection textures |
(Texture unit 1) |
2D textures |
(Texture unit 2) |
2D textures |
(Texture unit 3) |
Procedural textures |
The procedural texture stage handles all TextureStage::TEXTURE_UNIT_3_PROCEDURAL
settings except for texture coordinates.
2D textures
Use the nn::gd::TextureStage::SetTexture()
function to set a 2D texture. You can set a 2D texture in three texture units: 0, 1, and 2.
static nnResult nn::gd::TextureStage::SetTexture( nn::gd::TextureStage::TextureUnitId textureUnitId, nn::gd::Texture2D& texture2D);
Other (Non-Procedural) Textures
All other textures (except for procedural textures) can only be set in texture unit 0.
static nnResult nn::gd::TextureStage::SetTextureUnit0( nn::gd::TextureCube& textureCube); static void nn::gd::TextureStage::SetTexture2DProjectionForUnit0(gdBool value); static void nn::gd::TextureStage::SetPerspectiveShadow(gdBool v); static void nn::gd::TextureStage::SetShadowZBias(f32 zBias);
Use the nn::gd::TextureStage::SetTextureUnit0()
function to set a cube map texture.
By calling the nn::gd::TextureStage::SetTexture2DProjectionForUnit0()
function and passing GD_TRUE
as an argument, you can treat the 2D texture set in texture unit 0 as a projection texture.
If you apply perspective projection to create texture coordinates when you access a shadow texture or shadow cube map texture, pass GD_TRUE
as an argument to nn::gd::TextureStage::SetPerspectiveShadow
. You can also use nn::gd::TextureStage::SetShadowZBias
to set a bias value that will be subtracted from the distance to the light source when a shadow texture is generated.
4.3.3.1. Texture Coordinates
The following functions set the texture coordinates input to texture units 2 and 3.
// For TextureUnit2 static void nn::gd::TextureStage::SetTextureCoordinateSourceForUnit2( nn::gd::TextureStage::TextureCoordinateSourceUnit2 u); // For TextureUnit3 static void nn::gd::TextureStage::SetTextureCoordinateSourceForUnit3Procedural( nn::gd::TextureStage::TextureCoordinateSourceUnit3Procedural u);
You can specify the following arguments to these functions.
Definition | Input Texture Coordinates |
---|---|
UNIT2_TEXTURE_COORDINATE_FROM_UNIT_2 |
Texture coordinate 2 (default). |
UNIT2_TEXTURE_COORDINATE_FROM_UNIT_1 |
Texture coordinate 1 |
Definition | Input Texture Coordinates |
---|---|
UNIT3_PROCEDURAL_TEXTURE_COORDINATE_FROM_UNIT_0 |
Texture coordinate 0 (default). |
UNIT3_PROCEDURAL_TEXTURE_COORDINATE_FROM_UNIT_1 |
Texture coordinate 1 |
UNIT3_PROCEDURAL_TEXTURE_COORDINATE_FROM_UNIT_2 |
Texture coordinate 2 |
4.3.4. Sampler Settings
To configure the texture sampling method (sampler settings), create a state (SamplerState
) object and set it in a texture unit.
static nnResult nn::gd::TextureStage::CreateSamplerState( const nn::gd::SamplerStateDescription* desc, nn::gd::SamplerState** sampler); static nnResult nn::gd::TextureStage::ReleaseSamplerState( nn::gd::SamplerState* sampler); static nnResult nn::gd::TextureStage::SetSamplerState( nn::gd::TextureStage::TextureUnitId textureUnitId, nn::gd::SamplerState* sampler);
Configure sampler settings in a descriptor class (SamplerStateDescription
) in advance, specified in the desc
parameter. For more information about descriptor class settings, see 4.3.4.1. Descriptor Class for SamplerState Objects.
You can use the nn::gd::TextureStage::SetSamplerState()
function to set a created SamplerState
object in a texture unit. You can configure sampler settings in three texture units: 0, 1, and 2.
Use the nn::gd::TextureStage::ReleaseSamplerState()
function to release a SamplerState
object that is no longer needed. This also deallocates memory regions that were allocated internally when the CombinerState
object was created.
The following sample code creates a SamplerState
object with the default settings, changes the minification and magnification filters, and then sets that object in texture unit 0.
nn::gd::SamplerState* sampler = 0; nn::gd::SamplerStateDescription samplerdesc; samplerdesc.ToDefault(); samplerdesc.m_MinFilter = nn::gd::TextureStage::SAMPLER_MIN_FILTER_LINEAR; samplerdesc.m_MagFilter = nn::gd::TextureStage::SAMPLER_MAG_FILTER_LINEAR; nn::gd::TextureStage::CreateSamplerState(&samplerdesc, &sampler); nn::gd::TextureStage::SetSamplerState( nn::gd::TextureStage::TEXTURE_UNIT_0, sampler);
4.3.4.1. Descriptor Class for SamplerState Objects
This section introduces the members of the descriptor (SamplerStateDescription
) class for SamplerState
objects and provides setting-related cautions and information.
class nn::gd::SamplerStateDescription { nn::gd::TextureStage::SamplerMinFilter m_MinFilter; nn::gd::TextureStage::SamplerMagFilter m_MagFilter; nn::gd::TextureStage::SamplerWrapMode m_WrapS; nn::gd::TextureStage::SamplerWrapMode m_WrapT; u8 m_BorderColor[4]; u32 m_LodBias; u32 m_MinLod; u32 m_MaxLod; void SetMinFilter(nn::gd::TextureStage::SamplerMinFilter filter); void SetMagFilter(nn::gd::TextureStage::SamplerMagFilter filter); void SetWrapS(nn::gd::TextureStage::SamplerWrapMode wrap); void SetWrapT(nn::gd::TextureStage::SamplerWrapMode wrap); void SetBorderColor(u8 colorR, u8 colorG, u8 colorB, u8 colorA); void SetBorderColor(f32 colorR, f32 colorG, f32 colorB, f32 colorA); void SetLodBias(f32 biasValue); void SetMinLod(u32 lodValue); void SetMaxLod(u32 lodValue); SamplerStateDescription(); void ToDefault(); void SetShadow(); void SetShadowCube(); void SetGas(); };
Minification Filter (m_MinFilter)
This filter is applied during texture minification. You can set this value using the SetMinFilter()
function.
Magnification Filter (m_MagFilter)
This filter is applied during texture magnification. You can set this value using the SetMagFilter()
function.
Wrapping Mode in the S Direction (m_WrapS)
This wrapping mode is applied to repeating textures in the S direction. You can set this value using the SetWrapS()
function.
Wrapping Mode in the T Direction (m_WrapT)
This wrapping mode is applied to repeating textures in the T direction. You can set this value using the SetWrapT()
function.
Border Color (m_BorderColor)
This border color is used when TextureStage::SAMPLER_WRAP_CLAMP_TO_BORDER
is specified as the wrapping mode. You can call the SetBorderColor()
function to set each RGBA component to a value between 0
and 255
or between 0.0
and 1.0
.
LOD Bias (m_LodBias)
This bias value is used to determine the level of detail (LOD). Because you must set this value using the same format as when setting a GPU register, do so by passing a value between -16.0
and 16.0
to the SetLoadBias()
function.
The bias value is a 13-bit signed fixed-point decimal number with 8 fractional bits. To change member variables directly, use the Utils::Float32ToFix13Fraction8
utility function.
Minimum LOD (m_MinLod)
This is the smallest mipmap level used for LOD. If you use LOD, set the smallest mipmap level to a value of 0 or greater. (Specify 0
if you do not use LOD.) You can set this value using the SetMinLod()
function.
Maximum LOD (m_MaxLod)
This is the largest mipmap level used for LOD. Specify a value of 0
when you do not use LOD and a value that is one less than the maximum number of mipmap levels in the texture when you do use LOD. You can set this value using the SetMaxLod()
function.
Specify UINT_MAX
or another large value when the same sampler settings are used by textures that have different numbers of mipmap levels. This value will be one less than the number of mipmap levels in the texture when it is rendered. It is determined from the default settings and source.
Default Settings (ToDefault)
You can call the ToDefault()
function to change all members to their default values. This is also done in the constructor.
Member | Setting Value |
---|---|
m_MinFilter |
TextureStage::SAMPLER_MIN_FILTER_NEAREST |
m_MagFilter |
TextureStage::SAMPLER_MAG_FILTER_NEAREST |
m_WrapS |
TextureStage::SAMPLER_WRAP_REPEAT |
m_WrapT |
TextureStage::SAMPLER_WRAP_REPEAT |
m_BorderColor |
(0, 0, 0, 0) |
m_LodBias |
0.0 |
m_MinLod |
0 |
m_MaxLod |
0xFFFFFFFF |
Shadow Texture Settings (SetShadow)
You can call the SetShadow()
function to change all members to their values for shadow textures.
Member | Setting Value |
---|---|
m_MinFilter |
TextureStage::SAMPLER_MIN_FILTER_LINEAR |
m_MagFilter |
TextureStage::SAMPLER_MAG_FILTER_LINEAR |
m_WrapS |
TextureStage::SAMPLER_WRAP_CLAMP_TO_BORDER |
m_WrapT |
TextureStage::SAMPLER_WRAP_CLAMP_TO_BORDER |
m_BorderColor |
(0, 0, 0, 0) |
m_LodBias |
0.0 |
m_MinLod |
0 |
m_MaxLod |
0xFFFFFFFF |
Do not change the filter, wrapping mode, and LOD settings.
Shadow Cube Texture Settings (SetShadowCube)
You can call the SetShadowCube()
function to change all members to their values for shadow cube map textures.
Member | Setting Value |
---|---|
m_MinFilter |
TextureStage::SAMPLER_MIN_FILTER_LINEAR |
m_MagFilter |
TextureStage::SAMPLER_MIN_FILTER_LINEAR |
m_WrapS |
TextureStage::SAMPLER_WRAP_CLAMP_TO_EDGE |
m_WrapT |
TextureStage::SAMPLER_WRAP_CLAMP_TO_EDGE |
m_BorderColor |
(0, 0, 0, 0) |
m_LodBias |
0.0 |
m_MinLod |
0 |
m_MaxLod |
0xFFFFFFFF |
Do not change the filter, wrapping mode, and LOD settings.
Gas Texture Settings (SetGas)
You can call the SetGas()
function to change all members to their values for gas textures.
Member | Setting Value |
---|---|
m_MinFilter |
TextureStage::SAMPLER_MIN_FILTER_NEAREST |
m_MagFilter |
TextureStage::SAMPLER_MAG_FILTER_NEAREST |
m_WrapS |
TextureStage::SAMPLER_WRAP_CLAMP_TO_EDGE |
m_WrapT |
TextureStage::SAMPLER_WRAP_CLAMP_TO_EDGE |
m_BorderColor |
(0, 0, 0, 0) |
m_LodBias |
0.0 |
m_MinLod |
0 |
m_MaxLod |
0xFFFFFFFF |
Do not change the filter, wrapping mode, and LOD settings.
4.4. Procedural Texture Stage
The procedural texture stage handles settings related to procedural textures. The nn::gd::ProceduralTextureStage
class defines functions that configure these settings.
The following figure gives an overview of the settings made in the procedural texture stage.
4.4.1. Setting Procedural Texture Parameters
Functions have been provided for setting each of the procedural texture parameters.
class nn::gd::ProceduralTextureStage { static void SetRgbMap(UvMap rgbMap); static void SetAlphaSeparate(gdBool alphaSeparate); static void SetAlphaMap(UvMap alphaMap); static void SetClampUV(Clamp u, Clamp v); static void SetShiftUV(Shift u, Shift v); static void SetMinFilter(MinFilter minFilter); static void SetTexBias(f32 texBias); static void SetNoiseEnable(gdBool noiseEnable); static void SetNoiseUV(f32 noiseU[3], f32 noiseV[3]); static void SetTexWidth(u8 texWidth); static void SetTexOffset(u8 texOffset); };
The following table shows which parameters are set by each function. For more information about how to specify arguments and what effect these parameters have, see the CTR-SDK API Reference and other documentation.
Function | Parameters |
---|---|
SetRgbMap |
The G function for RGB mapping. Default value: UV_MAP_U |
SetAlphaSeparate |
Whether to enable independent alpha mode. Default value: GD_FALSE |
SetAlphaMap |
The G function for alpha mapping. Default value: UV_MAP_U |
SetClampUV |
The clamp mode. Default value: CLAMP_TO_ZERO |
SetShiftUV |
The shift mode. Default value: SHIFT_NONE |
SetMinFilter |
The minification filter mode. Default value: MIN_FILTER_LINEAR |
SetTexBias |
The LOD bias. Default value: 0.5 |
SetNoiseEnable |
Whether to enable noise. Default value: GD_FALSE |
SetNoiseUV |
Noise parameters. Default values: F=0.0, P=0.0, and A=0.0 for both U and V |
SetTexWidth |
Color lookup table width. Default value: 0 |
SetTexOffset |
Color lookup table offset. Default value: 0 |
The SetTexBias
and SetNoiseUV()
functions convert the values passed as arguments into the format used when setting GPU registers.
4.4.2. Loading Lookup Tables Used by the Procedural Texture Stage
There are two ways to load F functions (for RGB mapping and alpha mapping), noise modulation data, color lookup tables, and other lookup tables used by procedural textures: The first is to use functions (with the Float
suffix) that take arrays of floating-point numbers. The second is to use functions (with the Native
suffix) that take arrays of data to be written unchanged to the GPU registers. Because these are immediate functions, data is written to the 3D command buffer when they are run.
class nn::gd::ProceduralTextureStage { static nnResult UploadLookUpTableRgbMapFloat( u32 index, f32* Map, f32* MapDelta, u32 lutSize); static nnResult UploadLookUpTableRgbMapNative( u32 index, u32* Map, u32 lutSize); static nnResult UploadLookUpTableAlphaMapFloat( u32 index, f32* Map, f32* MapDelta, u32 lutSize); static nnResult UploadLookUpTableAlphaMapNative( u32 index, u32* Map, u32 lutSize); static nnResult UploadLookUpTableNoiseMapFloat( u32 index, f32* Map, f32* MapDelta, u32 lutSize); static nnResult UploadLookUpTableNoiseMapNative( u32 index, u32* Map, u32 lutSize); static nnResult UploadLookUpTableColorMapFloat( u32 index, f32** Map, f32** MapDelta, u32 lutSize); static nnResult UploadLookUpTableColorMapNative( u32 index, u32* Map, u32* MapDelta, u32 lutSize); };
You can use index
and lutSize
values to partially overwrite a lookup table. However, an error occurs if the total exceeds the maximum number of elements in the following table.
To load a lookup table with arrays of floating-point numbers, you must provide one array for the data (the Map
parameter) and one for the deltas (the MapDelta
parameter). However, you need eight arrays to load a color lookup table: two for each of the color's four components.
If you load any lookup table (except for a color lookup table) with an array that has been converted into native format, you only need to provide one array because both the data and the delta have been combined into a single element.
The following table shows the format of and maximum number of elements in the arrays used by each function to load a lookup table.
Function | Lookup Table | Format | Maximum Number of Elements |
---|---|---|---|
UploadLookUpTableRgbMapFloat |
RGB mapping | Floating-point numbers | 128 |
UploadLookUpTableRgbMapNative |
RGB mapping | Native | 128 |
UploadLookUpTableAlphaMapFloat |
Alpha mapping | Floating-point numbers | 128 |
UploadLookUpTableAlphaMapNative |
Alpha mapping | Native | 128 |
UploadLookUpTableNoiseMapFloat |
Noise modulation table | Floating-point numbers | 128 |
UploadLookUpTableNoiseMapNative |
Noise modulation table | Native | 128 |
UploadLookUpTableColorMapFloat |
Color lookup table | Floating-point numbers | 256 |
UploadLookUpTableColorMapNative |
Color lookup table | Native | 256 |
4.4.2.1. Helper Functions for Loading Lookup Tables
Helper functions have been provided for converting arrays of floating-point numbers into native format. Functions that load lookup tables from arrays of floating-point numbers internally convert the arrays into native format. This is expensive and not suited for runtime use. We recommend that you use some other strategy, such as providing data that has already been converted into native format or using the helper functions to convert the data when the lookup table is loaded for the first time.
class nn::gd::ProceduralTextureStage::Helper { static nnResult ConvertLookUpTableDataFloatToNative( f32* valueData, f32* deltaData, u32 lutSize, u32* destination); static nnResult ConvertColorLookUpTableDataFloatToNative( f32** refArray, f32** deltaArray, u32 lutSize, u32* destRef, u32* destDelta); };
For all lookup tables except for color lookup tables, a single array of data (destination
) is generated by combining the data and deltas. The original data is converted into 12-bit unsigned fixed-point numbers with 12 fractional bits in bits [11:0] of the generated data. The original deltas are converted into 12-bit signed fixed-point numbers with 11 fractional bits (and negative numbers expressed in two's complement) in bits [23:12] of the generated data.
For color lookup tables, a combination of data and deltas for each RGBA component (a total of eight arrays) is converted into a combination of a single color and delta value (the destRef
and destDelta
parameters). Although they are converted through different methods, every color and delta value that is generated has eight bits each for the alpha, blue, green, and red components, arranged respectively from the most- to the least-significant bit. Color values are converted from 8-bit signed fixed-point numbers with 7 fractional bits, between 0.0
and 1.0
, into unsigned 8-bit integers between 0
and 255
. Delta values between -1.0
and 1.0
are converted into 8-bit signed (two’s complement) fixed-point numbers with 7 fractional bits.
For more information about how these values are converted, see the 3DS Programming Manual: Advanced Graphics.
The GD library provides utility functions for these conversions.
4.5. Lighting Stage
The lighting stage configures the global lighting environment and individual lights. The nn::gd::LightingStage
class defines functions that configure these settings. Applications do not need to enable or disable the lighting environment. The library manages lighting settings. The lighting environment is only enabled when lighting results are required by combiner settings.
The following diagram provides an overview of the settings made in the lighting stage. (This does not include individual lights).
4.5.1. Configuring the Global Lighting Environment
Functions have been provided for setting each of the global lighting environment parameters.
class nn::gd::LightingStage { static void SetGlobalColorAmbient(u8 R, u8 G, u8 B); static void SetClampHightlight(gdBool value); static void SetFresnelSelector(FresnelSelectorType fresnelSelectorType); static void SetShadowSelectorTexture( nn::gd::TextureStage::TextureUnitId textureUnit); static void SetShadowPrimary(gdBool value); static void SetShadowSecondary(gdBool value); static void SetShadowAlpha(gdBool value); static void SetInvertShadow(gdBool value); static void SetBumpMode(BumpMode bumpMode, gdBool bumpRenorm); static void SetBumpSelectorTexture( nn::gd::TextureStage::TextureUnitId textureUnit); };
The following table shows which parameters are set by each function. For more information about how to specify arguments and what effect these parameters have, see the CTR-SDK API Reference and other documentation.
Function | Parameters |
---|---|
SetGlobalColorAmbient |
The light source color of global ambient light. Default value: (10, 10, 10) |
SetClampHightlight |
Specular light clamping. Default value: GD_TRUE |
SetFresnelSelector |
Fresnel factor. Default value: FRESNEL_SELECTOR_TYPE_NO_FRESNEL |
SetShadowSelectorTexture |
The texture unit used by shadows. Default value: TEXTURE_UNIT_0 |
SetShadowPrimary |
Effect of shadows on the primary color. Default value: GD_FALSE |
SetShadowSecondary |
Effect of shadows on the secondary color. Default value: GD_FALSE |
SetShadowAlpha |
Effect of shadows on the alpha component. Default value: GD_FALSE |
SetInvertShadow |
Shadow term inversion. Default value: GD_FALSE |
SetBumpMode |
Bump-map perturbation mode and whether to regenerate the third component of normal vectors. Default values: BUMPMODE_NOT_USED , GD_FALSE |
SetBumpSelectorTexture |
The texture unit used for bump mapping. Default value: TEXTURE_UNIT_0 |
SetGlobalColorAmbient
is an immediate function.
4.5.2. Setting the Layer Configuration and Lookup Tables
Functions have been provided to set the following: the layer configuration (this determines which lookup tables are used for lighting), lookup table input values, scaling of lookup table output values, distribution factors, and reflections.
class nn::gd::LightingStage { static void SetLayerConfiguration(LayerConfiguration layerConfiguration); static void SetLookUpTableInputValue( LookUpTableId lutId, LookUpTableInputValue lutInputValue); static void SetLookUpTableAbsInput(LookUpTableId lutId, gdBool value); static void SetLookUpTableOutputScaling( LookUpTableId lutId, LookUpTableOutputScaleValue outputScalingValue); static void EnableLookUpTableD0(gdBool value); static void EnableLookUpTableD1(gdBool value); static void EnableLookUpTableReflection(gdBool value); };
The following table shows which parameters are set by each function. For more information about how to specify arguments and what effect these parameters have, see the CTR-SDK API Reference and other documentation.
Function | Parameters |
---|---|
SetLayerConfiguration |
The layer configuration. Default value: LAYER_CONFIGURATION_0 |
SetLookUpTableInputValue |
Lookup table input value. Default value: INPUT_VALUE_NH for all lookup tables |
SetLookUpTableAbsInput |
Whether to take the absolute value of lookup table input value. Default value: GD_FALSE for all lookup tables |
SetLookUpTableOutputScaling |
How to scale lookup table output values. Default value: OUTPUT_SCALE_VALUE_1 for all lookup tables |
EnableLookUpTableD0 |
Whether to apply lookup tables to distribution factor 0. Default value: GD_FALSE |
EnableLookUpTableD1 |
Whether to apply lookup tables to distribution factor 1. Default value: GD_FALSE |
EnableLookUpTableReflection |
Whether to apply lookup tables to reflections. Default value: GD_FALSE |
4.5.3. Loading Lookup Tables Used by the Lighting Stage
There are two functions for loading lookup tables used by lighting: UploadLookUpTableFloat
, which takes arrays of floating-point numbers, and UploadLookUpTableNative
, which takes arrays of data to be written unchanged to the GPU registers. Because these are immediate functions, data is written to the 3D command buffer when they are run.
class nn::gd::LightingStage { static nnResult UploadLookUpTableFloat( LookUpTableUploadId lutID, u32 lutStartIndex, const f32* valueData, const f32* deltaData, u32 dataCount); static nnResult UploadLookUpTableNative( LookUpTableUploadId lutID, u32 lutStartIndex, const u32* data, u32 dataCount); class Helper { static nnResult ConvertLookUpTableDataFloatToNative( const f32* valueData, const f32* deltaData, u32 dataCount, u32* __restrict destination); }; };
Lighting uses lookup tables with 256 elements. You can use lutStartIndex
and dataCount
values to partially overwrite a lookup table, but an error will occur if the total exceeds 256.
A lookup table's structure differs depending upon whether its input values are converted into absolute values. Note that the input values corresponding to the 128th and 129th elements of a lookup table will be discontinuous (they will jump from 0.9922
to -1.0
) if the lookup table input values are not converted into absolute values (if they are between -1.0
and 1.0
).
To load a lookup table with arrays of floating-point numbers, you need to provide one array for the data (the valueData
parameter) and one array for the deltas (the deltaData
parameter).
If you load any lookup table with an array that has been converted into native format, you only need to provide one array because both the data and the delta have been combined into a single element.
Helper functions have been provided for converting arrays of floating-point numbers into native format. These helper functions generate a single array of data (the destination
parameter) by combining the data and deltas. The original data is converted into 12-bit unsigned fixed-point numbers with 12 fractional bits. The original deltas are converted into 12-bit signed fixed-point numbers with 11 fractional bits (which are absolute values). These are stored in bits [11:0] and [23:12] of the generated data, respectively.
For more information about how these values are converted, see the 3DS Programming Manual: Advanced Graphics.
The GD library provides utility functions for these conversions.
4.5.4. Lights
The 3DS hardware supports lighting with 8 lights. The GD library represents individual lights as separate instances of the nn::gd::Light
class. The nn::gd::LightingStage
class contains eight Light
objects that are created when the library is initialized. As a result, applications do not need to create Light
objects. Access them using the members defined by the lighting stage. For example, you could call nn::gd::LightingStage::light[0].EnableLight(GD_TRUE)
.
The following diagram provides an overview of the settings handled by Light
objects.
4.5.4.1. Light Settings
Functions have been provided for setting each of the light parameters.
class nn::gd::Light { void EnableLight(gdBool value); void SetLightType(SourceType sourceType); void EnableTwoSideDiffuse(gdBool value); void EnableShadowed(gdBool value); void EnableGeomFactor0(gdBool value); void EnableGeomFactor1(gdBool value); void SetColorAmbient(u8 R, u8 G, u8 B); void SetColorDiffuse(u8 R, u8 G, u8 B); void SetColorSpecular0(u8 R, u8 G, u8 B); void SetColorSpecular1(u8 R, u8 G, u8 B); void SetPosition(f32 X, f32 Y, f32 Z); void SetDirection(f32 X, f32 Y, f32 Z); void EnableSpotLight(gdBool value); void SetSpotDirection(f32 X, f32 Y, f32 Z); void EnableDistanceAttenuation(gdBool value); void SetDistanceAttenuationScaleBias( f32 attenuationScale, f32 attenuationBias); nnResult UploadLookUpTableFloat( LightLookUpTableUploadId lightLutID, u32 lutStartIndex, const f32* valueData, const f32* deltaData, u32 dataCount); nnResult UploadLookUpTableNative( LightLookUpTableUploadId lightLutID, u32 lutStartIndex, const u32* data, u32 dataCount); };
The following table shows which parameters are set by each function. For more information about how to specify arguments and what effect these parameters have, see the CTR-SDK API Reference and other documentation.
Function | Parameters |
---|---|
EnableLight |
Whether to enable light. Default value: GD_FALSE |
SetLightType |
Type of light source. Default value: SOURCE_TYPE_POINT |
EnableTwoSideDiffuse |
Whether to enable two-sided lighting. Default value: GD_FALSE |
EnableShadowed |
Whether to enable shadow attenuation. Default value: GD_FALSE |
EnableGeomFactor0 |
Whether to enable geometry factor 0. Default value: GD_FALSE |
EnableGeomFactor1 |
Whether to enable geometry factor 1. Default value: GD_FALSE |
SetColorAmbient |
Ambient light color. Default value: (0, 0, 0) |
SetColorDiffuse |
Diffuse light color. Default value: (255, 255, 255) |
SetColorSpecular0 |
Color of specular light 0. Default value: (255, 255, 255) |
SetColorSpecular1 |
Color of specular light 1. Default value: (255, 255, 255) |
SetPosition |
Point light source position. Default value: (0.0, 0.0, 0.0) |
SetDirection |
Directional light orientation. No default value. |
EnableSpotLight |
Whether to enable spotlights. Default value: GD_FALSE |
SetSpotDirection |
Spotlight direction. Default value: (0.0, 0.0, 0.0) |
EnableDistanceAttenuation |
Whether to enable distance attenuation. Default value: GD_FALSE |
SetDistanceAttenuationScaleBias |
Scale and bias for distance attenuation. Default values: A utility function ( |
Lookup tables are loaded in the same way as they are for the lighting stage, although they are specified differently. The lookup tables used by distance attenuation (DA) must be created to accept input values between 0.0 and 1.0.
Every function that configures lights is an immediate function, except for EnableLight
, EnableShadowed
, EnableSpotLight
, and EnableDistanceAttenuation
.
4.6. Rasterizer Stage
The rasterizer stage configures the process of rasterizing pixels that are output to the fragment pipeline. The nn::gd::RasterizerStage
class defines functions that configure these settings.
The following diagram provides an overview of the settings made in the rasterizer stage.
4.6.1. Culling Settings
Use the nn::gd::RasterizerStage::SetCulling()
function to configure culling.
static void nn::gd::RasterizerStage::SetCulling( nn::gd::RasterizerStage::Culling culling);
Specify the culling method in the culling
parameter. Clockwise culling (CULLING_CLOCKWISE
) is specified by default.
4.6.2. Configuring the Viewport
Use the nn::gd::RasterizerStage::SetViewport()
function to configure the viewport.
class nn::gd::Viewport { u32 m_X; u32 m_Y; u32 m_Width; u32 m_Height; Viewport(); Viewport(u32 x, u32 y, u32 width, u32 height); void Set(u32 x, u32 y, u32 width, u32 height); }; static void nn::gd::RasterizerStage::SetViewport( nn::gd::Viewport& viewport);
The nn::gd::Viewport
class defines the viewport region. Note that the viewport has a different orientation than the LCDs. Viewport(0, 0, 240, 320)
is set by default.
4.6.3. Clipping Settings
Use the following functions to configure clipping.
static void nn::gd::RasterizerStage::EnableClippingPlane(gdBool value); static void nn::gd::RasterizerStage::SetClippingPlane( f32 param1, f32 param2, f32 param3, f32 param4);
By default, clipping is disabled (with GD_FALSE
) and all parameters are set to 0
.
4.6.4. Scissor Test Settings
Use the following functions to configure the scissor test.
static void nn::gd::RasterizerStage::EnableScissor(gdBool value); static void nn::gd::RasterizerStage::SetScissor( nn::gd::Viewport& area);
By default, the scissor test is disabled (GD_FALSE
) and Viewport(0, 0, 0, 0)
is set as the scissor box.
4.6.5. Early Depth Test Settings
Use the following functions to configure the early depth test.
static void nn::gd::RasterizerStage::SetEarlyDepthTest( gdBool enable, nn::gd::RasterizerStage::EarlyDepthFunction func); static void nn::gd::RasterizerStage::ClearEarlyDepth(f32 depthClearValue);
By default, the early depth test is disabled (GD_FALSE
and EARLYDEPTH_FUNCTION_LESS
) and 1.0
is set as the depth value to use for clearing.
Block-32 mode must be set as the block mode when you use the early depth test. For more information, see Block Mode Settings in the 3DS Programming Manual: Advanced Graphics.
4.7. Combiner Stage
The combiner stage configures (texture) combiners and combiner buffers. The nn::gd::CombinerStage
class defines functions that configure these settings.
The following diagram provides an overview of the settings made in the combiner stage.
4.7.1. Combiner Settings
The combiner stage creates a state (CombinerState
) object that consolidates all combiner and combiner buffer settings. By switching this CombinerState
object, you can change all combiner-related settings in one operation, except for the constant color.
CombinerState
objects are created from a descriptor class (CombinerDescription
) that defines operands and other settings.
static nnResult nn::gd::CombinerStage::CreateTextureCombinerState( const nn::gd::CombinerDescription* description, nn::gd::CombinerState** textureCombinerState); static nnResult nn::gd::CombinerStage::ReleaseTextureCombinerState( nn::gd::CombinerState* textureCombinerState); static nnResult nn::gd::CombinerStage::SetTextureCombinerState( nn::gd::CombinerState* textureCombinerState);
Combiner settings are configured in the descriptor object (CombinerDescription
) specified by the description
parameter in advance. For more information about the descriptor class settings, see 4.9.5.1. Descriptor Class for BlendState Objects.
You can use the nn::gd::CombinerStage::SetTextureCombinerState()
function to set a created CombinerState
object in the combiner stage.
Use the nn::gd::CombinerStage::ReleaseTextureCombinerStage()
function to release a state object that is no longer needed. This also deallocates memory regions that were allocated internally when the CombinerState
object was created.
Use the following function to set the constant color. You must set a constant color if it is used by combiner settings, because the constant color is undefined by default.
static nnResult nn::gd::CombinerStage::SetTextureCombinerUnitConstantColor( nn::gd::CombinerStage::UnitId unit, u8 colorR, u8 colorG, u8 colorB, u8 colorA);
Because this is an immediate function, 3D commands are accumulated in the command buffer when it is run.
4.7.1.1. Descriptor Class for CombinerState Objects
This section introduces the members of the descriptor (CombinerDescription
) class for CombinerState
objects and provides setting-related cautions and information.
The CombinerDescription
class contains settings for six combiner units. Because you will not necessarily configure every unit, this class is designed with member functions that set member variables for a specified unit.
class nn::gd::CombinerDescription { struct BufferInput { nn::gd::CombinerStage::BufferInput m_Rgb1; nn::gd::CombinerStage::BufferInput m_Rgb2; nn::gd::CombinerStage::BufferInput m_Rgb3; nn::gd::CombinerStage::BufferInput m_Rgb4; nn::gd::CombinerStage::BufferInput m_Alpha1; nn::gd::CombinerStage::BufferInput m_Alpha2; nn::gd::CombinerStage::BufferInput m_Alpha3; nn::gd::CombinerStage::BufferInput m_Alpha4; }; struct BufferInput m_BufferInput; void SetSourceRGB( nn::gd::CombinerStage::UnitId unit, nn::gd::CombinerStage::Source sourceRGB1, nn::gd::CombinerStage::Source sourceRGB2, nn::gd::CombinerStage::Source sourceRGB3); void SetOperandRGB( nn::gd::CombinerStage::UnitId unit, nn::gd::CombinerStage::OperandRgb opRGB1, nn::gd::CombinerStage::OperandRgb opRGB2, nn::gd::CombinerStage::OperandRgb opRGB3); void SetSourceAlpha( nn::gd::CombinerStage::UnitId unit, nn::gd::CombinerStage::Source sourceA1, nn::gd::CombinerStage::Source sourceA2, nn::gd::CombinerStage::Source sourceA3); void SetOperandAlpha( nn::gd::CombinerStage::UnitId unit, nn::gd::CombinerStage::OperandAlpha opA1, nn::gd::CombinerStage::OperandAlpha opA2, nn::gd::CombinerStage::OperandAlpha opA3); void SetCombineRGB( nn::gd::CombinerStage::UnitId unit, nn::gd::CombinerStage::CombineRgb combineRgb); void SetCombineAlpha( nn::gd::CombinerStage::UnitId unit, nn::gd::CombinerStage::CombineAlpha combineAlpha); void SetScaleRGB( nn::gd::CombinerStage::UnitId unit, nn::gd::CombinerStage::Scale scaleRgb); void SetScaleAlpha( nn::gd::CombinerStage::UnitId unit, nn::gd::CombinerStage::Scale scaleAlpha); void SetBufferColor(u8 colorR, u8 colorG, u8 colorB, u8 colorA); void SetCombinerInUse(nn::gd::CombinerStage::UnitId unit, gdBool mode); CombinerDescription(); void ToDefault(); };
Input Source Settings (SetSourceRGB, SetSourceAlpha)
These functions set input sources 0 to 2 for the specified combiner unit.
Operand Settings (SetOperandRGB, SetOperandAlpha)
These functions set operands 0 to 2 for the specified combiner unit.
Combiner Function Settings (SetCombineRGB, SetCombineAlpha)
These functions set the combiner function for the specified combiner unit.
Scaling Value Settings (SetScaleRGB, SetScaleAlpha)
These functions set the scaling values for the specified combiner unit.
Constant Color for Combiner Buffer 0 Setting (SetBufferColor)
This function sets the constant color for combiner buffer 0.
Combiner Buffer Input Source (m_BufferInput)
Sets the input source for combiner buffers 1 to 4. No setter functions are defined for it.
Configuring How Combiner Units Are Used (SetCombinerInUse)
This function either enables (GD_TRUE
) or disables (GD_FALSE
) the settings for the specified combiner unit. If you do not enable settings for a combiner unit, it uses its default settings.
Default Settings (ToDefault)
You can call the ToDefault()
function to change all members to their default values. This is also done in the constructor.
Member | Default Settings |
---|---|
|
|
SetOperandRGB |
OPERAND_RGB_SRC_COLOR (all operands) |
SetOperandAlpha |
OPERAND_ALPHA_SRC_ALPHA (all operands) |
SetCombineRGB |
COMBINE_RGB_REPLACE (all units) |
SetCombineAlpha |
COMBINE_ALPHA_REPLACE (all units) |
|
SCALE_1 (all units) |
SetBufferColor |
(0,0,0,0) |
m_BufferInput |
INPUT_PREVIOUS_BUFFER (all inputs) |
SetCombinerInUse |
GD_FALSE (all units) |
4.8. Fog Stage
The fog stage handles all settings related to rendering fog and gas. The nn::gd::FogStage
class defines functions that configure these settings.
The following diagram provides an overview of the settings made in the fog stage.
4.8.1. Fog Mode
Use the nn::gd::FogStage::SetGasFogMode()
function to switch the mode for GPU fog features.
static void nn::gd::FogStage::SetGasFogMode(nn::gd::FogStage::Mode mode);
You can specify one of the following values in the mode
parameter.
Definition | Description |
---|---|
FogStage::MODE_NONE |
Do not use fog features. (Default.) |
FogStage::MODE_FOG |
Use fog features normally in fog mode. |
FogStage::MODE_GAS |
Use fog features in gas mode. |
4.8.2. Fog Settings
Functions have been provided for setting each of the fog parameters.
class nn::gd::FogStage { static void SetFogColor(u8 R, u8 G, u8 B); static void SetFogZFlip(gdBool zFlip); };
The following table shows which parameters are set by each function. For more information about how to specify arguments and what effect these parameters have, see the CTR-SDK API Reference and other documentation.
Function | Parameters |
---|---|
SetFogColor |
Fog color. Default value: (0, 0, 0) |
SetFogZFlip |
Whether to invert input depth value. Default value: GD_FALSE |
For more information about how to load lookup tables, see 4.8.4. Loading Lookup Tables Used by the Fog Stage.
4.8.3. Gas Settings
Functions have been provided for setting each of the gas parameters.
class nn::gd::FogStage { static void SetGasShadingDensity( GasShadingDensitySource shadingDensitySrc); static void SetGasAttenuation(f32 attenuation); static void SetGasAccumulationMax(f32 maxAccumulation); static void SetGasAutoAccumulation(gdBool enableAutoAccumulation); static void SetGasLightXY( u8 lightMinimum, u8 lightMaximum, u8 lightAttenuation); static void SetGasLightZ( u8 scattMinimum, u8 scattMaximum, u8 scattAttenuation, u8 lz); static void SetGasDeltaZ(f32 deltaZ); static void SetGasLightColorLutInput( GasColorLookUpTableInput colorLutInput); };
The following table shows which parameters are set by each function. For more information about how to specify arguments and what effect these parameters have, see the CTR-SDK API Reference and other documentation.
Function | Parameters |
---|---|
SetGasShadingDensity |
Density information used for shading. Default value: GAS_SHADING_DENSITY_SOURCE_PLAIN |
SetGasAttenuation |
Density attenuation coefficient to use when calculating alpha value for shading. Default value: 1.0 |
SetGasAccumulationMax |
The reciprocal of the maximum density information value. Default value: 1.0 |
SetGasAutoAccumulation |
Whether to automatically calculate the reciprocal of the maximum density information value. Default value: GD_FALSE |
SetGasLightXY |
Factors used to control planar shading: the minimum intensity, maximum intensity, and density attenuation. Default value: (0,0,0) |
SetGasLightZ |
Factors used to control view shading: the minimum intensity, maximum intensity, density attenuation, and effect in the view direction. Default value: (0,0,0,0) |
SetGasDeltaZ |
Attenuation coefficient in the depth direction. Default value: 10.0 |
SetGasLightColorLutInput |
Input value to the shading lookup table. Default value: GAS_COLOR_INPUT_LIGHT_FACTOR |
For more information about how to load lookup tables, see 4.8.4. Loading Lookup Tables Used by the Fog Stage.
4.8.4. Loading Lookup Tables Used by the Fog Stage
There are two ways to load the lookup tables used for coefficients and shading in the fog stage: The first is through functions (with the Float
suffix) that accept arrays of floating-point numbers. The second is through functions (with the Native
suffix) that accept arrays of data to be written unchanged to the GPU registers. Because these are immediate functions, data is written to the 3D command buffer when they are run.
class nn::gd::FogStage { static nnResult UploadFogLookUpTableNative( u32 lutStartIndex, u32* data, u32 countData); static nnResult UploadFogLookUpTableFloat( u32 lutStartIndex, const f32* dataValue, const f32* dataDelta, u32 countData); static nnResult UploadGasLookUpTableNative( u32 lutStartIndex, u32* data, u32 countData); static nnResult UploadGasLookUpTableFloat( u32 lutStartIndex, f32* dataValue, f32* dataDelta, u32 countData); };
You can use lutStartindex
and countData
values to partially overwrite a lookup table. However, an error occurs if the total exceeds the maximum number of elements in the following table.
To load a lookup table using arrays of floating-point numbers, you must provide one array for the data (the dataValue
parameter) and one for the deltas (the dataDelta
parameter). However, note that because each element in the shading lookup table is generated from three elements in these source arrays (which store the color components in RGB order), dataValue
and dataDelta
must have three times the number of elements specified in countData
.
If you load any lookup table using an array that has been converted into native format, you only need to provide one array because both the data and the delta have been combined into a single element. However, the native and floating-point arrays used to load the shading lookup table have different maximum sizes.
The following table shows the format of and maximum number of elements in the arrays used by each function to load a lookup table.
Function | Lookup Table | Format | Maximum Number of Elements |
---|---|---|---|
UploadFogLookUpTableFloat |
Fog Coefficients | Floating-point numbers | 128 |
UploadFogLookUpTableNative |
Fog Coefficients | Native | 128 |
UploadGasLookUpTableFloat |
Shading | Floating-point numbers | 8 |
UploadGasLookUpTableNative |
Shading | Native | 16 |
4.8.4.1. Helper Functions for Loading Lookup Tables
Helper functions have been provided for converting arrays of floating-point numbers into native format. Functions that load lookup tables from arrays of floating-point numbers internally convert the arrays into native format. This is expensive and not suited for runtime use. We recommend that you use some other strategy, such as providing data that has already been converted into native format or using the helper functions to convert the data when the lookup table is loaded for the first time.
class nn::gd::FogStage::Helper { static nnResult ConvertFogLookUpTableDataFloatToNative( const f32* dataValue, const f32* dataDelta, u32 countData, u32 *__restrict dest); static nnResult ConvertGasLookUpTableDataFloatToNative( const f32* dataValue, const f32* dataDelta, u32 countData, u32 *__restrict dest); };
Both helper functions provided by the fog stage generate a single array (the dest
parameter) from a data array and a delta array.
Each data element is converted into an 11-bit unsigned fixed-point number with 11 fractional bits. Each delta is converted into a 13-bit signed (two's complement) fixed-point number with 11 fractional bits. These are stored in bits [23:13] and [12:0], respectively, of the data generated for the fog coefficient lookup table.
Data is generated for the shading lookup table in a special format. Specifically, note that the three elements of the source array (in R/G/B order) are converted into a single data value. Conversely, each element of the array dest
does not contain both data and delta values. Instead, the first eight elements of the array store delta values, and the second eight elements store data values.
The first eight elements are generated from the deltas. The deltas for the R, G, and B components are converted into 8-bit signed integers that are packed into bits [7:0], [15:8], and [23:16] respectively.
The last eight elements are generated from the data. The data for the R, G, and B components are converted into 8-bit unsigned fixed-point numbers (with no fractional bits) that are packed into bits [7:0], [15:8], and [23:16] respectively.
For more information about how these values are converted, see the 3DS Programming Manual: Advanced Graphics.
The GD library provides utility functions for these conversions.
4.9. Output Stage
The output stage configures blending, the depth test, the stencil test, the target buffer, and other settings related to pixel output. The nn::gd::OutputStage
class defines functions that configure these settings.
The following diagram provides an overview of the settings made in the output stage.
4.9.1. Fragment Operation Mode
You can use the nn::gd::OutputStage::SetFragOpMode()
function to switch the fragment operation mode.
static void nn::gd::OutputStage::SetFragOpMode( nn::gd::OutputStage::FragmentOperationMode fragOpMode);
You can specify one of the following values in the fragOpMode
parameter.
Definition | Description |
---|---|
FRAGMENT_OPERATION_MODE_FRAGMENT_COLOR |
Normal fragment processing (this is the default value). |
FRAGMENT_OPERATION_MODE_GAS_ACCUMULATION |
Fragment processing for the shadow accumulation path. |
FRAGMENT_OPERATION_MODE_SHADOW_MAP |
Fragment processing for rendering gas density information. |
4.9.2. Framebuffers
The GD library uses RenderTarget
and DepthStencilTarget
objects to operate on the framebuffer (color and depth stencil buffer). Both objects are created from a single Texture2DResource
object and a descriptor class (RenderTargetDescription
or DepthStencilTargetDescription
,). If the Texture2DResource
object has mipmap data, you can use descriptor class settings to specify which levels of mipmap data to use when you create the object.
You can use the following functions to create, release, and apply a framebuffer object (a RenderTarget
or DepthStencilTarget
object) to the pipeline.
static nnResult nn::gd::OutputStage::CreateRenderTarget( const nn::gd::Texture2DResource* texture2DResource, const nn::gd::RenderTargetDescription* desc, nn::gd::RenderTarget** renderTarget); static nnResult nn::gd::OutputStage::ReleaseRenderTarget( nn::gd::RenderTarget* renderTarget); static nnResult nn::gd::OutputStage::SetRenderTarget( const nn::gd::RenderTarget* renderTarget); static nnResult nn::gd::OutputStage::CreateDepthStencilTarget( const nn::gd::Texture2DResource* texture2DResource, const nn::gd::DepthStencilTargetDescription* desc, nn::gd::DepthStencilTarget** depthStencil); static nnResult nn::gd::OutputStage::ReleaseDepthStencilTarget( nn::gd::DepthStencilTarget* depthStencil); static nnResult nn::gd::OutputStage::SetDepthStencilTarget( const nn::gd::DepthStencilTarget* depthStencil);
Functions that have the RenderTarget
suffix affect the color buffer. Functions that have the DepthStencilTarget
suffix affect the depth (stencil) buffer.
Configure framebuffer settings in the corresponding descriptor object (RenderTargetDescription
or DepthStencilTargetDescription
) specified in the desc
parameter. For more information about the descriptor class settings, see 4.9.2.1. Descriptor Class for Framebuffer Objects.
Only a limited number of pixel formats can be used by a Texture2DResource
object in the framebuffer. For more information, see 3.1.1. Creating a Texture2DResource Object.
After you have created a framebuffer object, you can set it as the framebuffer with the nn::gd::OutputStage::Set*()
functions.
Use the nn::gd::OutputStage::Release*()
functions to release framebuffer objects that are no longer needed. Only management data is released when a framebuffer object is released. Texture2DResource
objects are not released.
4.9.2.1. Descriptor Class for Framebuffer Objects
This section introduces the members of the descriptor classes (RenderTargetDescription
and DepthStencilTargetDescription
) for framebuffer classes (RenderTarget
and DepthStencilTarget
) and provides setting-related cautions and information.
class nn::gd::RenderTargetDescription { u32 m_MipLevelIndex; }; class nn::gd::DepthStencilTargetDescription { u32 m_MipLevelIndex; };
Mipmap Level Index (m_MipLevelIndex)
This is the mipmap level of the Texture2DResource
object used to create a framebuffer object.
4.9.2.2. Getting Detailed Information About Framebuffer Objects
Detailed information (the TargetProperties
class) includes framebuffer-related information that is based on the content of the Texture2DResource
object specified when the framebuffer was created.
The RenderTarget
and DepthStencilTarget
objects use different functions to get detailed information, but they both do so using the TargetProperties
class.
static nnResult nn::gd::OutputStage::GetRenderTargetProperties( const nn::gd::RenderTarget* renderTarget, nn::gd::TargetProperties* properties); static nnResult nn::gd::OutputStage::GetDepthStencilTargetProperties( const nn::gd::DepthStencilTarget* depthStencil, nn::gd::TargetProperties* properties);
Although the width, height, mipmap levels, and starting address of resource data may change with the mipmap levels specified when an object was created, they are generally the same as the detailed information for the Texture2DResource
object.
class nn::gd::TargetProperties { u32 m_Width; u32 m_Height; u32 m_PixelSize; nn::gd::Resource::NativeFormat m_Format; nn::gd::Memory::MemoryLayout m_MemLayout; nn::gd::Memory::MemoryLocation m_MemLocation; u8* m_MemAddr; };
4.9.2.3. Clearing the Framebuffer
You can clear the color buffer and depth (stencil) buffer using a specified value.
static nnResult nn::gd::Memory::ClearTargets( const nn::gd::RenderTarget* renderTarget, const nn::gd::DepthStencilTarget* depthStencilTarget, const u8 ColorRGBA[4], float depth, u8 stencil);
The framebuffer is actually cleared when the command list is executed because this function internally calls the nngxAddMemoryFillCommand()
function.
4.9.2.4. Color Mask
Using the nn::gd::OutputStage::SetColorWriteMask()
function, you can change color mask settings and control what is written to the color buffer.
static void nn::gd::OutputStage::SetColorWriteMask(u32 mask);
Specify a bitwise OR of the following flags in the mask
parameter.
Definition | Description |
---|---|
COLOR_WRITE_MASK_ENABLE_RED |
Enables write operations for the red component. |
COLOR_WRITE_MASK_ENABLE_GREEN |
Enables write operations for the green component. |
COLOR_WRITE_MASK_ENABLE_BLUE |
Enables write operations for the blue component. |
COLOR_WRITE_MASK_ENABLE_ALPHA |
Enables write operations for the alpha component. |
COLOR_WRITE_MASK_ENABLE_ALL |
Enables write operations for all components. (This value is the default.) |
4.9.3. Depth and Stencil Tests
By creating a state (DepthStencilState
) object and then switching the DepthStencilState
object that is configured in the output stage, you can change all settings related to the depth and stencil test in one operation.
You can create, release, and apply a DepthStencilState
object to the pipeline using the following functions.
static nnResult nn::gd::OutputStage::CreateDepthStencilState( const nn::gd::DepthStencilStateDescription* desc, nn::gd::DepthStencilState** DepthStencilState); static nnResult nn::gd::OutputStage::ReleaseDepthStencilState( nn::gd::DepthStencilState* DepthStencilState); static nnResult nn::gd::OutputStage::SetDepthStencilState( const nn::gd::DepthStencilState* state, u8 stencilRef);
Configure the depth and stencil test in a descriptor class (DepthStencilStateDescription
) passed in the desc
parameter. For more information about the descriptor class settings, see 4.9.3.1. Descriptor Class for DepthStencilState Objects.
After you have created a state object, you can apply it to the pipeline using the nn::gd::OutputStage::SetDepthStencilState()
function. Specify the reference value to use in the stencil test in the stencilRef
parameter.
Use the nn::gd::OutputStage::ReleaseDepthStencilState()
function to release a state object that is no longer needed. This also releases memory regions that were allocated internally when the BlendState
object was created as a state object.
4.9.3.1. Descriptor Class for DepthStencilState Objects
This section introduces the members of the descriptor (DepthStencilStateDescription
) class for DepthStencilState
objects and provides setting-related cautions and information.
class nn::gd::DepthStencilStateDescription { gdBool m_DepthEnable; gdBool m_StencilEnable; u8 m_StencilWriteMask; u8 m_StencilReadMask; nn::gd::OutputStage::DepthWriteMask m_DepthMask; nn::gd::OutputStage::DepthFunction m_DepthFunc; nn::gd::OutputStage::StencilFunction m_StencilFunc; nn::gd::OutputStage::StencilOperation m_StencilFail; nn::gd::OutputStage::StencilOperation m_StencilZFail; nn::gd::OutputStage::StencilOperation m_StencilZPass; DepthStencilStateDescription(); void ToDefault(); };
Enabling the Depth Test (m_DepthEnable)
The depth test is enabled if this is GD_TRUE
.
Write Mask for the Depth Test (m_DepthMask)
Sets the write mask for the depth test.
Comparison Function for the Depth Test (m_DepthFunc)
Sets the comparison function for the depth test.
Enabling the Stencil Test (m_StencilEnable)
The stencil test is enabled if this is GD_TRUE
.
Write Mask for the Stencil Test (m_StencilWriteMask)
Sets the write mask for the stencil test.
Read Mask for the Stencil Test (m_StencilReadMask)
Sets the read mask for the stencil test.
Comparison Function for the Stencil Test (m_StencilFunc)
Sets the comparison function for the stencil test.
Operation When the Stencil Test Fails (m_StencilFail)
Sets the operation to run when the stencil test fails.
Operation When the Stencil Test Passes (m_StencilZFail)
Sets the operation to run when the stencil test passes, but the depth test fails.
Operation When Both the Depth and Stencil Test Pass (m_StencilZPass)
Sets the operation to run when both the depth and stencil tests pass.
Default Settings (ToDefault)
You can call the ToDefault()
function to change all members to their default values. This is also done in the constructor.
Member | Default Settings |
---|---|
m_DepthEnable |
GD_FALSE |
m_DepthMask |
DEPTH_WRITE_MASK_ALL |
m_DepthFunc |
DEPTH_FUNCTION_LESS |
m_StencilEnable |
GD_FALSE |
|
0xFF |
m_StencilFunc |
STENCIL_FUNCTION_NEVER |
|
STENCIL_OPERATION_KEEP |
4.9.4. Alpha Test
Use the nn::gd::OutputStage::SetAlphaTest()
function to configure the alpha test.
static void nn::gd::OutputStage::SetAlphaTest( gdBool enable, nn::gd::OutputStage::AlphaFunction func, u8 alphaRef);
To enable the alpha test, specify GD_TRUE
in the enable
parameter, a comparison function in the func
parameter, and a reference value in the alphaRef
parameter. The default settings for these parameters are GD_FALSE
, ALPHA_FUNCTION_NEVER
, and 0
, respectively.
4.9.5. Logical Operations and Blending
By creating a state (BlendState
) object and then switching the BlendState
object that is configured in the output stage, you can change all settings related to logical operations and blending in one operation.
You can create, release, and apply a BlendState
object to the pipeline using the following functions.
static nnResult nn::gd::OutputStage::CreateBlendState( const nn::gd::BlendStateDescription* desc, nn::gd::BlendState** blendState); static nnResult nn::gd::OutputStage::ReleaseBlendState( nn::gd::BlendState* blendState); static nnResult nn::gd::OutputStage::SetBlendState( const nn::gd::BlendState* blendState);
Configure logical operations and blending in a descriptor class (BlendStateDescription
) that is specified in the desc
parameter. For more information about the descriptor class settings, see 4.9.5.1. Descriptor Class for BlendState Objects.
You can use the nn::gd::OutputStage::SetBlendState()
function to apply a created BlendState
object to the pipeline.
Use the nn::gd::OutputStage::ReleaseBlendState()
function to release a state object that is no longer needed. This also releases memory regions that were allocated internally when the BlendState
object was created as a state object.
Use the following function to set the blend color. The default blend color is (0, 0, 0, 0)
.
static void nn::gd::OutputStage::SetBlendColor(u8 R, u8 G, u8 B, u8 A);
4.9.5.1. Descriptor Class for BlendState Objects
This section introduces the members of the descriptor (BlendStateDescription
) class for BlendState
objects and provides setting-related cautions and information.
class nn::gd::BlendStateDescription { nn::gd::OutputStage::BlendType m_BlendType; nn::gd::OutputStage::LogicOperator m_LogicOp; nn::gd::OutputStage::BlendFunction m_SrcRgb; nn::gd::OutputStage::BlendFunction m_DstRgb; nn::gd::OutputStage::BlendFunction m_SrcAlpha; nn::gd::OutputStage::BlendFunction m_DstAlpha; nn::gd::OutputStage::BlendEquation m_EqRgb; nn::gd::OutputStage::BlendEquation m_EqAlpha; BlendStateDescription(); void ToDefault(); void SetBlendFunc( nn::gd::OutputStage::BlendFunction src, nn::gd::OutputStage::BlendFunction dst, nn::gd::OutputStage::BlendEquation eq); void SetBlendFunc( nn::gd::OutputStage::BlendFunction srcRgb, nn::gd::OutputStage::BlendFunction dstRgb, nn::gd::OutputStage::BlendFunction srcAlpha, nn::gd::OutputStage::BlendFunction dstAlpha, nn::gd::OutputStage::BlendEquation eqRgb, nn::gd::OutputStage::BlendEquation eqAlpha); void SetBlendMode_DefaultBlending(); void SetBlendMode_NoBlend(); void SetLogicOperatorMode(nn::gd::OutputStage::LogicOperator logicOp); void SetLogicOperatorMode_Default(); };
Choice Between Logical Operations and Blending (m_BlendType)
Set to BLEND_TYPE_LOGICOP
when logical operations are used or BLEND_TYPE_BLENDING
when blending is used.
Logical Operation (m_LogicOp)
Indicates which logical operation to use. You can set this value using the SetLogicOperatorMode()
function.
Set to LOGIC_OPERATOR_COPY
by the SetLogicOperatorMode_Default()
function.
Blend Weight Coefficients (m_SrcRgb, m_DstRgb, m_SrcAlpha, m_DstAlpha)
These are the blend weight coefficients. There are settings for the RGB and alpha components in both the source and destination.
Blend Equations (m_EqRgb, m_EqAlpha)
These are the blend equations. There is a setting for both the RGB and alpha components.
Batch Blend Settings (SetBlendFunc, SetBlendMode_NoBlend)
The SetBlendFunc()
function configures all blending operations at the same time. You can either configure the RGB and alpha components together or separately.
The SetBlendMode_NoBlend()
function changes settings so that there is no blending (the source is output unchanged).
Member | Setting |
---|---|
m_SrcRgb, m_SrcAlpha |
BLEND_FUNCTION_ONE |
m_DstRgb, m_DstAlpha |
BLEND_FUNCTION_ZERO |
m_EqRgb, m_EqAlpha |
BLEND_EQUATION_ADD |
Default Settings (ToDefault)
You can call the ToDefault()
function to change all members to their default values. This is also done in the constructor.
Blending is used by default, and the settings are the same as those configured by the SetBlendMode_NoBlend()
function.
4.9.6. W-Buffer and Polygon Offset
Use the nn::gd::OutputStage::SetDepthRangeMode()
function to configure the w-buffer and polygon offset.
static void nn::gd::OutputStage::SetDepthRangeMode( nn::gd::OutputStage::DepthBufferType type, f32 depthRangeNear, f32 depthRangeFar, s32 offset);
Specify DEPTHBUFFER_LINEAR
in the type
parameter to use the w-buffer feature or specify DEPTHBUFFER_RECIPROCAL_FUNCTION
to use the normal range of depth values instead.
Specify the near and far depth values in the depthRangeNear
and depthRangeFar
parameters when you do not use the w-buffer. Specify 0
in depthRangeNear
and a scale value in depthRangeFar
when you do use the w-buffer.
When you use a polygon offset, specify the offset value in the offset
parameter.
4.9.7. Soft Shadows
Use the nn::gd::OutputStage::SetPenumbraScaleBias()
function to set the scale and bias for soft shadows. Because this is an immediate function, 3D commands are accumulated in the command buffer when it is run.
static void nn::gd::OutputStage::SetPenumbraScaleBias(f32 Scale, f32 Bias);