Referencia de GLSL a HLSL
El código de OpenGL Shader Language (GLSL) se debe migrar al código de Lenguaje de sombreador de alto nivel (HLSL) de Microsoft al migrar la arquitectura de gráficos de OpenGL ES 2.0 a Direct3D 11 para crear un juego para Plataforma universal de Windows (UWP). El GLSL al que se hace referencia aquí es compatible con OpenGL ES 2.0; HLSL es compatible con Direct3D 11. Para obtener información sobre las diferencias entre Direct3D 11 y versiones anteriores de Direct3D, consulta Asignación de características.
- Comparación de OpenGL ES 2.0 con Direct3D 11
- Migración de variables GLSL a HLSL
- Migración de tipos GLSL a HLSL
- Migración de variables globales predefinidas de GLSL a HLSL
- Ejemplos de migración de variables GLSL a HLSL
- Ejemplos de portabilidad del código de representación de OpenGL a Direct3D
- Temas relacionados
Comparación de OpenGL ES 2.0 con Direct3D 11
OpenGL ES 2.0 y Direct3D 11 tienen muchas similitudes. Ambos tienen canalizaciones de representación similares y características de gráficos. Pero Direct3D 11 es una implementación de representación y una API, no una especificación; OpenGL ES 2.0 es una especificación de representación y una API, no una implementación. Direct3D 11 y OpenGL ES 2.0 suelen diferir de estas maneras:
OpenGL ES 2.0 | Direct3D 11 |
---|---|
Especificación independiente del hardware y del sistema operativo con implementaciones proporcionadas por el proveedor | Implementación de Microsoft de abstracción de hardware y certificación en plataformas Windows |
Abstraido para la diversidad de hardware, el entorno de ejecución administra la mayoría de los recursos. | Acceso directo al diseño de hardware; la aplicación puede administrar los recursos y el procesamiento |
Proporciona módulos de nivel superior a través de bibliotecas de terceros (por ejemplo, Simple DirectMedia Layer (SDL)) | Los módulos de nivel superior, como Direct2D, se basan en módulos inferiores para simplificar el desarrollo de aplicaciones de Windows |
Los proveedores de hardware diferencian a través de extensiones | Microsoft agrega características opcionales a la API de forma genérica para que no sean específicas de ningún proveedor de hardware determinado. |
GLSL y HLSL suelen diferir de estas maneras:
GLSL | HLSL |
---|---|
Procedimientos, centrados en pasos (C como) | Orientado a objetos, centrados en datos (como C++) |
Compilación de sombreador integrada en la API de gráficos | El compilador HLSL compila el sombreador en una representación binaria intermedia antes de que Direct3D lo pase al controlador.
Nota Esta representación binaria es independiente del hardware. Normalmente se compila en tiempo de compilación de la aplicación, en lugar de en tiempo de ejecución de la aplicación.
|
Modificadores de almacenamiento de variables | Búferes de constantes y transferencias de datos mediante declaraciones de diseño de entrada |
Tipo de vector típico: vec2/3/4 lowp, mediump, highp |
Tipo de vector típico: float2/3/4 min10float, min16float |
texture2D [Function] | textura. Ejemplo [tipo de datos. Función] |
sampler2D [datatype] | Texture2D [tipo de datos] |
Matrices principales de fila (valor predeterminado) | Matrices principales de columna (valor predeterminado)
Nota Use el modificador de tipo row_major para cambiar el diseño de una variable. Para obtener más información, consulta Sintaxis de variable. También puede especificar una marca del compilador o una pragma para cambiar el valor predeterminado global.
|
Sombreador de fragmentos | Sombreador de píxeles |
Nota HLSL tiene texturas y muestreadores como dos objetos independientes. En GLSL, como Direct3D 9, el enlace de textura forma parte del estado del muestreador.
En GLSL, presenta gran parte del estado openGL como variables globales predefinidas. Por ejemplo, con GLSL, se usa la variable gl_Position para especificar la posición del vértice y la variable gl_FragColor para especificar el color del fragmento. En HLSL, pasas el estado de Direct3D explícitamente desde el código de la aplicación al sombreador. Por ejemplo, con Direct3D y HLSL, la entrada al sombreador de vértices debe coincidir con el formato de datos en el búfer de vértices y la estructura de un búfer de constantes en el código de la aplicación debe coincidir con la estructura de un búfer de constantes (cbuffer) en el código del sombreador.
Migración de variables GLSL a HLSL
En GLSL, se aplican modificadores (calificadores) a una declaración de variable de sombreador global para proporcionar a esa variable un comportamiento específico en los sombreadores. En HLSL, no necesita estos modificadores porque define el flujo del sombreador con los argumentos que se pasan al sombreador y que se devuelven desde el sombreador.
Comportamiento de las variables GLSL | Equivalente de HLSL |
---|---|
uniforme Se pasa una variable uniforme desde el código de la aplicación a sombreadores de vértices y fragmentos o ambos. Debe establecer los valores de todos los uniformes antes de dibujar los triángulos con esos sombreadores para que sus valores permanezcan iguales a lo largo del dibujo de una malla de triángulo. Estos valores son uniformes. Algunos uniformes se establecen para todo el marco y otros de forma exclusiva para un par de sombreador de vértices y píxeles concretos. Las variables uniformes son variables por polígono. |
Use el búfer de constantes. Vea Cómo: Crear un búfer de constantes y constantes de sombreador. |
variable Inicializa una variable variable dentro del sombreador de vértices y la pasa a una variable con nombre idéntico en el sombreador de fragmentos. Dado que el sombreador de vértices solo establece el valor de las variables variables en cada vértice, el rasterizador interpola esos valores (de manera correcta desde la perspectiva) para generar valores por fragmento para pasar al sombreador de fragmentos. Estas variables varían en cada triángulo. |
Use la estructura que devuelve del sombreador de vértices como entrada para el sombreador de píxeles. Asegúrese de que los valores semánticos coinciden. |
attribute Un atributo forma parte de la descripción de un vértice que se pasa desde el código de la aplicación al sombreador de vértices solo. A diferencia de un uniforme, se establece el valor de cada atributo para cada vértice, que, a su vez, permite que cada vértice tenga un valor diferente. Las variables de atributo son variables por vértice. |
Defina un búfer de vértices en el código de la aplicación direct3D y coincida con la entrada de vértices definida en el sombreador de vértices. Opcionalmente, defina un búfer de índice. Vea Cómo: Crear un búfer de vértices y Cómo: Crear un búfer de índice. Cree un diseño de entrada en el código de la aplicación direct3D y coincida con los valores semánticos con los de la entrada de vértices. Consulte Creación del diseño de entrada. |
const Constantes que se compilan en el sombreador y nunca cambian. |
Use un const estático. static significa que el valor no está expuesto a búferes de constantes, const significa que el sombreador no puede cambiar el valor. Por lo tanto, el valor se conoce en tiempo de compilación en función de su inicializador. |
En GLSL, las variables sin modificadores son simplemente variables globales normales que son privadas para cada sombreador.
Cuando se pasan datos a texturas (Texture2D en HLSL) y sus muestradores asociados (SamplerState en HLSL), normalmente se declaran como variables globales en el sombreador de píxeles.
Migración de tipos GLSL a HLSL
Use esta tabla para migrar los tipos GLSL a HLSL.
Tipo GLSL | Tipo HLSL |
---|---|
tipos escalares: float, int, bool | tipos escalares: float, int, bool también, uint, double Para obtener más información, consulta Tipos escalares. |
tipo de vector
|
tipo de vector
Para obtener más información, consulta Tipo de vector y palabras clave. vector también es el tipo definido como float4 (tipodef vector <float, 4> vector;). Para obtener más información, consulta Tipo definido por el usuario. |
tipo de matriz
|
tipo de matriz
También puede usar el tipo de matriz para definir una matriz. Por ejemplo: matriz <float, 2, 2> fMatrix = {0.0f, 0.1, 2.1f, 2.2f}; matrix también es el tipo definido como float4x4 (matriz de definición <de tipo float, 4, 4> matriz;). Para obtener más información, consulta Tipo definido por el usuario. |
calificadores de precisión para float, int, sampler
|
tipos de precisión
Para obtener más información, consulta Tipos escalares y Uso de la precisión mínima de HLSL. |
sampler2D | Texture2D |
samplerCube | TextureCube |
Migración de variables globales predefinidas de GLSL a HLSL
Use esta tabla para migrar variables globales predefinidas de GLSL a HLSL.
Variable global predefinida GLSL | Semántica de HLSL |
---|---|
gl_Position Esta variable es de tipo vec4. Posición del vértice por ejemplo: gl_Position = posición; |
SV_Position POSICIÓN en Direct3D 9 Esta semántica es el tipo float4. Salida del sombreador de vértices Posición del vértice por ejemplo: float4 vPosition : SV_Position; |
gl_PointSize Esta variable es de tipo float. Tamaño de punto |
PSIZE Ningún significado a menos que tenga como destino Direct3D 9 Esta semántica es de tipo float. Salida del sombreador de vértices Tamaño de punto |
gl_FragColor Esta variable es de tipo vec4. Color del fragmento por ejemplo: gl_FragColor = vec4(colorVarying, 1.0); |
SV_Target COLOR en Direct3D 9 Esta semántica es el tipo float4. Salida del sombreador de píxeles Color de píxel por ejemplo: float4 Color[4] : SV_Target; |
gl_FragData[n] Esta variable es de tipo vec4. Color de fragmento para datos adjuntos de color n |
SV_Target[n] Esta semántica es el tipo float4. Valor de salida del sombreador de píxeles almacenado en n destino de representación, donde 0 <= n <= 7. |
gl_FragCoord Esta variable es de tipo vec4. Posición de fragmento dentro del búfer de fotogramas |
SV_Position No disponible en Direct3D 9 Esta semántica es el tipo float4. Entrada del sombreador de píxeles Coordenadas de espacio de pantalla por ejemplo: screenSpace float4 : SV_Position |
gl_FrontFacing Esta variable es de tipo bool. Determina si el fragmento pertenece a un primitivo orientado al frente. |
SV_IsFrontFace VFACE en Direct3D 9 SV_IsFrontFace es de tipo bool. VFACE es tipo float. Entrada del sombreador de píxeles Primitivo orientado a |
gl_PointCoord Esta variable es de tipo vec2. Posición de fragmento dentro de un punto (solo rasterización de puntos) |
SV_Position VPOS en Direct3D 9 SV_Position es de tipo float4. VPOS es el tipo float2. Entrada del sombreador de píxeles Posición de píxel o de ejemplo en el espacio de pantalla por ejemplo: float4 pos : SV_Position |
gl_FragDepth Esta variable es de tipo float. Datos de búfer de profundidad |
SV_Depth PROFUNDIDAD en Direct3D 9 SV_Depth es el tipo float. Salida del sombreador de píxeles Datos de búfer de profundidad |
La semántica se usa para especificar la posición, el color, etc. para la entrada del sombreador de vértices y la entrada del sombreador de píxeles. Debe coincidir con los valores semánticos del diseño de entrada con la entrada del sombreador de vértices. Para obtener ejemplos, consulte Ejemplos de migración de variables GLSL a HLSL. Para obtener más información sobre la semántica de HLSL, consulta Semántica.
Ejemplos de migración de variables GLSL a HLSL
Aquí se muestran ejemplos de uso de variables GLSL en código OpenGL/GLSL y, a continuación, el ejemplo equivalente en código Direct3D/HLSL.
Uniforme, atributo y variable en GLSL
Código de la aplicación OpenGL
// Uniform values can be set in app code and then processed in the shader code.
uniform mat4 model;
uniform mat4 view;
uniform mat4 projection;
// Incoming position of vertex
attribute vec4 position;
// Incoming color for the vertex
attribute vec3 color;
// The varying variable tells the shader pipeline to pass it
// on to the fragment shader.
varying vec3 colorVarying;
Código del sombreador de vértices GLSL
//The shader entry point is the main method.
void main()
{
colorVarying = color; //Use the varying variable to pass the color to the fragment shader
gl_Position = position; //Copy the position to the gl_Position pre-defined global variable
}
Código del sombreador de fragmentos GLSL
void main()
{
//Pad the colorVarying vec3 with a 1.0 for alpha to create a vec4 color
//and assign that color to the gl_FragColor pre-defined global variable
//This color then becomes the fragment's color.
gl_FragColor = vec4(colorVarying, 1.0);
}
Búferes de constantes y transferencias de datos en HLSL
Este es un ejemplo de cómo se pasan datos al sombreador de vértices HLSL que luego fluye al sombreador de píxeles. En el código de la aplicación, defina un vértice y un búfer de constantes. A continuación, en el código del sombreador de vértices, defina el búfer de constantes como cbuffer y almacene los datos de entrada por vértice y el sombreador de píxeles. Aquí usamos estructuras denominadas VertexShaderInput y PixelShaderInput.
Código de aplicación de Direct3D
struct ConstantBuffer
{
XMFLOAT4X4 model;
XMFLOAT4X4 view;
XMFLOAT4X4 projection;
};
struct SimpleCubeVertex
{
XMFLOAT3 pos; // position
XMFLOAT3 color; // color
};
// Create an input layout that matches the layout defined in the vertex shader code.
const D3D11_INPUT_ELEMENT_DESC basicVertexLayoutDesc[] =
{
{ "POSITION", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0 },
{ "COLOR", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 12, D3D11_INPUT_PER_VERTEX_DATA, 0 },
};
// Create vertex and index buffers that define a geometry.
Código del sombreador de vértices HLSL
cbuffer ModelViewProjectionCB : register( b0 )
{
matrix model;
matrix view;
matrix projection;
};
// The POSITION and COLOR semantics must match the semantics in the input layout Direct3D app code.
struct VertexShaderInput
{
float3 pos : POSITION; // Incoming position of vertex
float3 color : COLOR; // Incoming color for the vertex
};
struct PixelShaderInput
{
float4 pos : SV_Position; // Copy the vertex position.
float4 color : COLOR; // Pass the color to the pixel shader.
};
PixelShaderInput main(VertexShaderInput input)
{
PixelShaderInput vertexShaderOutput;
// shader source code
return vertexShaderOutput;
}
Código del sombreador de píxeles HLSL
// Collect input from the vertex shader.
// The COLOR semantic must match the semantic in the vertex shader code.
struct PixelShaderInput
{
float4 pos : SV_Position;
float4 color : COLOR; // Color for the pixel
};
// Set the pixel color value for the renter target.
float4 main(PixelShaderInput input) : SV_Target
{
return input.color;
}
Ejemplos de portabilidad del código de representación de OpenGL a Direct3D
Aquí se muestra un ejemplo de representación en código openGL ES 2.0 y, a continuación, el ejemplo equivalente en el código de Direct3D 11.
Código de representación de OpenGL
// Bind shaders to the pipeline.
// Both vertex shader and fragment shader are in a program.
glUseProgram(m_shader->getProgram());
// Input assembly
// Get the position and color attributes of the vertex.
m_positionLocation = glGetAttribLocation(m_shader->getProgram(), "position");
glEnableVertexAttribArray(m_positionLocation);
m_colorLocation = glGetAttribColor(m_shader->getProgram(), "color");
glEnableVertexAttribArray(m_colorLocation);
// Bind the vertex buffer object to the input assembler.
glBindBuffer(GL_ARRAY_BUFFER, m_geometryBuffer);
glVertexAttribPointer(m_positionLocation, 4, GL_FLOAT, GL_FALSE, 0, NULL);
glBindBuffer(GL_ARRAY_BUFFER, m_colorBuffer);
glVertexAttribPointer(m_colorLocation, 3, GL_FLOAT, GL_FALSE, 0, NULL);
// Draw a triangle with 3 vertices.
glDrawArray(GL_TRIANGLES, 0, 3);
Código de representación de Direct3D
// Bind the vertex shader and pixel shader to the pipeline.
m_d3dDeviceContext->VSSetShader(vertexShader.Get(),nullptr,0);
m_d3dDeviceContext->PSSetShader(pixelShader.Get(),nullptr,0);
// Declare the inputs that the shaders expect.
m_d3dDeviceContext->IASetInputLayout(inputLayout.Get());
m_d3dDeviceContext->IASetVertexBuffers(0, 1, vertexBuffer.GetAddressOf(), &stride, &offset);
// Set the primitive's topology.
m_d3dDeviceContext->IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST);
// Draw a triangle with 3 vertices. triangleVertices is an array of 3 vertices.
m_d3dDeviceContext->Draw(ARRAYSIZE(triangleVertices),0);
Temas relacionados