Editar

Compartir a través de


Preguntas más frecuentes sobre Direct3D 10

Este artículo contiene algunas de las preguntas más frecuentes que rodean Direct3D 10 desde el punto de vista de un desarrollador que está portar una aplicación existente de Direct3D 9 (D3D9) a Direct3D 10 (D3D10).

Búferes de constantes

¿Cuál es la mejor manera de actualizar los búferes de constantes?

UpdateSubresource y Map with Discard deben tener aproximadamente la misma velocidad. Elija entre ellos en función de qué copia la menor cantidad de memoria. Si ya tiene los datos almacenados en memoria en un bloque contiguo, use UpdateSubresource. Si necesita acumular datos de otros lugares, use Map con Descarte.

¿Cuál es la peor manera de organizar los búferes de constantes?

El peor rendimiento se realiza colocando todas las constantes de un sombreador determinado en un búfer de constantes. Aunque a menudo es la manera más fácil de migrar de D3D9 a D3D10, puede impedir el rendimiento. Por ejemplo, considere un escenario que use el siguiente búfer de constantes:

cbuffer VSGlobalsCB
{
    matrix  ViewProj;
    matrix  Bones[100];
    matrix  World;
    float   SpecPower;
    float4  BDRFCoefficients;
    float   AppTime;
    uint2   RenderTargetSize;
};

El búfer es de 6560 bytes. Supongamos que hay una aplicación con 1000 objetos que se van a representar, 100 de los cuales son mallas de máscara y 900 de las cuales son mallas estáticas. Además, supongamos que esta aplicación usa la asignación de sombras con una fuente de luz. Esto significa que hay dos pases, uno para el mapa de profundidad representado a partir de la luz y otro para el paso de representación hacia delante. Esto da como resultado llamadas de dibujo de 2000. Aunque cada llamada a draw no NECESITA actualizar todas las partes del búfer de constantes, el búfer de constantes completo se actualiza y se envía a la tarjeta. Esto da como resultado la actualización de 13 MB de datos cada fotograma (2000 llamadas draw veces 6560 KB).

¿Cuál es la mejor manera de organizar mis búferes de constantes?

La mejor manera es organizar los búferes de constantes por frecuencia de actualización. Las constantes que se actualizan con frecuencias similares deben estar en el mismo búfer. Por ejemplo, considere el escenario presentado en " ¿Cuál es la peor manera de organizar los búferes de constantes?", pero con un diseño constante mejor:

cbuffer VSGlobalPerFrameCB
  { 
    float   AppTime; 
  };
cbuffer VSPerSkinnedCB
  { 
    matrix  Bones[100]; 
  };
cbuffer VSPerStaticCB
  {
    matrix  World;
  };
cbuffer VSPerPassCB
  {
    matrix  ViewProj;
    uint2   RenderTargetSize;
  };
cbuffer VSPerMaterialCB
  {
    float   SpecPower;
    float4  BDRFCoefficients;
  };    

Los búferes de constantes se dividen por su frecuencia de actualización, pero esto solo es la mitad de la solución. La aplicación debe actualizar correctamente los búferes de constantes para aprovechar al máximo la división. Asumiremos la misma escena que antes: 900 mallas estáticas, 100 mallas de piel, un paso claro y un paso hacia delante. También se supone que se almacenarán algunos búferes de constantes por objeto. Esto significa que cada objeto contendrá vsPerSkinnedCB o VSPerStaticCB, en función de si está o no desafinado o estático. Lo hacemos para evitar duplicar la cantidad de matrices enviadas a través de la canalización.

Dividimos el marco en tres fases. La primera fase es el principio del marco y no implica representación, solo actualizaciones constantes.

Begin Frame

  • Actualización de VSGlobalPerFrameCB para el tiempo de la aplicación (4 bytes)
  • Actualización 100 VSPerSkinnedCB para los 100 objetos de máscara (640000 bytes)
  • Actualización de VSPerStaticCB para 900 objetos estáticos (57600 bytes)

A continuación se muestra el pase del mapa de sombras. Observe que el único búfer de constantes que realmente actualiza es VSPerPassCB. Todos los demás búferes de constantes se actualizaron durante el paso de fotograma inicial. Aunque todavía necesitamos enlazar estos búferes de constantes, la cantidad de información que se pasa a la tarjeta de vídeo es mínima, ya que los búferes ya se han actualizado.

Paso de sombra

  • Actualización de VSPerPassCB (72 bytes)
  • Dibujar 100 mallas con máscara (100 enlaces, sin actualizaciones)
  • Dibujar 900 mallas estáticas (100 enlaces, sin actualizaciones)

Del mismo modo, el paso de representación hacia delante solo necesita actualizar los datos por material, ya que no se almacenó por malla. Si se supone que hay 500 materiales en uso en la escena:

Pase hacia delante

  • Actualización de VSPerPassCB (72 bytes)
  • Actualización 500 VSPerMaterialCBs (10000 bytes)

Esto da como resultado un total de solo 707 KB. Aunque se trata de un escenario muy nuevo, ilustra la cantidad de sobrecarga de actualización constante que se puede reducir mediante la ordenación de constantes por frecuencia de actualización.

¿Qué ocurre si no tengo suficiente espacio para almacenar búferes de constantes individuales para mis mallas, material, etc.?

Siempre puede usar un sistema en capas de búferes de constantes. Cree búferes de constantes de tamaño variable (16 bytes, 32 bytes, 64 bytes, etc.) hasta el tamaño de búfer constante más grande necesario. Cuando es el momento de enlazar un búfer de constantes a un sombreador, seleccione el búfer de constantes más pequeño que puede contener los datos necesarios para el sombreador. Aunque este enfoque es ligeramente menos eficaz, es un buen paso intermedio.

Estoy compartiendo búferes de constantes entre diferentes sombreadores. Un sombreador puede usar todas las constantes, pero otro puede usar algunas de las constantes. ¿Cuál es la mejor manera de actualizarlos?

Un enfoque consiste en dividir aún más el búfer de constantes. Sin embargo, hay un punto en el que hay demasiados búferes de constantes enlazados. En este caso, mueva las constantes que probablemente no usen varios sombreadores al final del búfer de constantes. Al obtener los datos de variable del sombreador, use la marca D3D10_SVF_USED de la D3D10_SHADER_VARIABLE_DESC para determinar si se usa la variable. Al colocar variables sin usar al final del búfer de constantes, puede enlazar un búfer más pequeño al sombreador que no usa estas variables, lo que ahorra el costo de actualización.

¿Cuánto puedo mejorar mi velocidad de fotogramas si solo cargo los huesos de mi personaje una vez por fotograma en lugar de una vez por pase/dibujo?

Puede mejorar la velocidad de fotogramas entre el 8 % y el 50 % en función de la cantidad de datos redundantes. En el peor de los casos, el rendimiento no se reducirá.

¿Cuántos búferes de constantes debo enlazar a la vez?

Enlace el número mínimo de búferes de constantes que se necesitan para obtener todos los datos en el sombreador. En un escenario realista, cinco son el número recomendado de búferes de constantes que se van a usar. Compartir búferes de constantes entre sombreadores (enlazar el mismo CB al VS y PS) también puede mejorar el rendimiento.

¿Hay un costo para enlazar búferes de constantes sin usarlos?

Sí, si realmente no va a usar el búfer, no llame a VSSetConsantBuffer ni PSSetConstantBuffer. Esta sobrecarga adicional de API puede agregarse a lo largo de varias llamadas de dibujo.

State

¿Cuál es la mejor manera de administrar el estado en D3D10?

La mejor solución es conocer todo el estado por adelantado y crear los objetos de estado por adelantado. Esto significa que, en tiempo de representación, el enlace de estado es la única operación que debe producirse. D3D10 también filtra los duplicados.

Mi juego se ha cargado dinámicamente o tiene contenido generado por el usuario. No puedo cargar todos mis objetos de estado por adelantado. ¿Cuál debo hacer?

Hay dos soluciones aquí. El primero es simplemente crear objetos de estado sobre la marcha y permitir que D3D10 filtre los duplicados. Sin embargo, esto no se recomienda para escenarios con muchos cambios de objeto de estado por fotograma. Una mejor solución consiste en aplicar un algoritmo hash a los objetos de estado y crear un objeto de estado solo si no se encuentra uno que se ajuste a los requisitos en la tabla hash. El razonamiento subyacente al uso de una tabla hash personalizada es que una aplicación puede seleccionar un hash rápido en función del escenario de uso concreto para esa aplicación. Por ejemplo, si una aplicación solo cambia el rendertargetwritemask en BlendState y mantiene todos los demás valores iguales, la aplicación puede generar un hash a partir de rendertargetwritemask en lugar de toda la estructura.

El estado AlphaTest ha desaparecido. ¿A dónde se fue?

AlphaTest ahora debe ser el rendimiento en el sombreador. Consulte el ejemplo FixedFuncEMU.

¿Qué le pasó a los planos de recorte de usuario?

Los planos de recorte de usuario se han movido al sombreador. Hay dos maneras de controlar esto. La primera consiste en generar SV_ClipDistance desde el sombreador de vértices o el sombreador de geometría. La otra opción consiste en usar el descarte en el sombreador de píxeles en función de algún valor pasado por el sombreador de vértices o el sombreador de geometría. Experimente con ambos para ver cuál es más rápido para su escenario concreto. El uso de SV_ClipDistance podría hacer que el hardware use una rutina de recorte basada en geometría que pueda hacer que las llamadas de dibujo enlazadas a geometría se ejecuten más lentamente. Del mismo modo, el uso de descarte desplaza el trabajo al sombreador de píxeles, lo que puede hacer que las llamadas de dibujo enlazadas a píxeles se ejecuten más lentamente.

Las desactivaciones no respetan ninguna configuración de estado, como mi configuración de corrección de tijeras en mi estado de rasterizador.

Las desactivaciones se han separado del estado de la canalización. Para obtener el comportamiento de estilo D3D9, emule las claras dibujando un quad de pantalla completa.

He vuelto a establecer mis estados en el valor predeterminado para intentar diagnosticar un error de representación. Ahora mi pantalla sólo muestra negro, aunque sé que estoy dibujando objetos en la pantalla.

Al volver a establecer el estado en valores predeterminados (NULL), asegúrese de que SampleMask en la llamada a OMSetBlendState nunca sea cero. Si SampleMask se establece en cero, todas las muestras lógicamente Y con cero. En este escenario, no se superará ninguna muestra de la prueba de mezcla.

¿Dónde ha estado D3DSAMP\SRGBTEXTURE?

SRGB se quitó como parte del estado del sampler y ahora está vinculado al formato de textura. Enlazar una textura SRGB dará como resultado el mismo muestreo que obtendrías si especificaste D3DSAMP_SRGBTEXTURE en Direct3D 9.

Formatos

¿Qué formato D3D9 corresponde al formato D3D10?

Para obtener información, consulta Consideraciones de Direct3D 9 a Direct3D 10.

¿Qué ha ocurrido con los formatos de textura A8R8G8B8?

Han quedado en desuso en D3D10. Puede volver a generar las texturas como R8G8B8A8, o puede activar la carga, o bien puede cambiar el tono en el sombreador.

Cómo usar texturas paletizadas?

Coloque la paleta de colores en una textura o un búfer de constantes y vincule a la canalización. En el sombreador de píxeles, realice una búsqueda indirecta mediante el índice de la textura paletizada.

¿Cuáles son estos nuevos formatos SRGB?

SRGB se quitó como parte del estado del sampler y ahora está vinculado al formato de textura. Enlazar una textura SRGB dará como resultado el mismo muestreo que obtendrías si especificaste D3DSAMP_SRGBTEXTURE en Direct3D 9.

¿Dónde van los fans del triángulo?

Los ventiladores de triángulos han quedado en desuso en D3D10. Los ventiladores de triángulos deberán convertirse en la canalización de contenido o en la carga.

Vinculación del sombreador

Mis sombreadores de Direct3D 9 compilan correctamente en Shader Model 4.0, pero cuando los enlace a la canalización, obtengo errores de vinculación que se muestran en la salida de depuración con el tiempo de ejecución de depuración.

La vinculación del sombreador es mucho más estricta en D3D10. Los elementos de una fase posterior deben leerse en el orden en que se generan en la fase anterior. Por ejemplo:

Salidas del sombreador de vértices:

    float4 Pos  : SV_POSITION;
    float3 Norm : NORMAL;
    float2 Tex  : TEXCOORD0;

Un sombreador de píxeles lee:

        float3 Norm : NORMAL;
        float2 Tex  : TEXCOORD0;

Aunque la posición no es necesaria en el sombreador de píxeles, esto provocará un error de vinculación, ya que la posición se está generando desde el sombreador de vértices, pero no leída por el sombreador de píxeles. La versión más correcta tendría el siguiente aspecto:

Salidas del sombreador de vértices:

        float3 Norm : NORMAL;
        float2 Tex  : TEXCOORD0;
        float4 Pos  : SV_POSITION;

Un sombreador de píxeles lee:

        float3 Norm : NORMAL;
        float2 Tex  : TEXCOORD0;

En este caso, el sombreador de vértices genera la misma información, pero ahora el sombreador de píxeles lee las cosas en la salida del orden. Dado que el sombreador de píxeles no lee nada después de Tex, no tenemos que preocuparnos de que vs genera más información que la lectura de PS.

Necesito una firma de sombreador para crear un diseño de entrada, pero cargo mis mallas y crear diseños antes de crear sombreadores. ¿Qué puedo hacer?

Una solución consiste en cambiar el orden y cargar sombreadores antes de cargar mallas. Sin embargo, esto es mucho más fácil de decir que hecho. Siempre puede crear los diseños de entrada a petición cuando sea necesario por la aplicación. Tendrá que mantener una versión de la firma del sombreador alrededor. Debe crear un hash basado en el diseño del sombreador y el búfer, y crear solo el diseño de entrada si aún no existe uno que coincida.

Dibujar llamadas

¿Cuál es mi límite en las llamadas de dibujo para que D3D10 alcance 60 Hz? ¿30 Hz?

Direct3D 9 tenía una limitación en el número de llamadas de dibujo debido al costo de CPU por llamada a draw. En Direct3D 10, se ha reducido el costo de cada llamada a draw. Sin embargo, ya no hay una correlación definitiva entre las llamadas a draw y las velocidades de fotogramas. Dado que las llamadas a draw suelen requerir muchas llamadas de soporte técnico (actualizaciones de búfer constantes, enlaces de texturas, configuración de estado, etc.), el impacto de la velocidad de fotogramas de la API ahora depende más del uso general de la API en lugar de simplemente dibujar recuentos de llamadas.

Recursos

¿Qué tipo de uso de recursos debo usar para qué operaciones?

Use la siguiente hoja de referencia rápida:

  • La CPU actualiza el recurso más de una vez por fotograma: D3D10_USAGE_DYNAMIC
  • La CPU actualiza el recurso menos de una vez por fotograma: D3D10_USAGE_DEFAULT
  • La CPU no actualiza el recurso: D3D10_USAGE_IMMUTABLE
  • La CPU debe leer el recurso: D3D10_USAGE_STAGING

Dado que los búferes de constantes siempre están diseñados para actualizarse con frecuencia, no se ajustan a la "hoja de referencia rápida". Para saber qué tipos de recursos usar para los búferes de constantes, consulte la sección Búferes de constantes .

¿Qué ha ocurrido con DrawPrimitiveUP y DrawIndexedPrimitiveUP?

Se han ido en D3D10. Para la geometría dinámica, use un búfer de D3D10_USAGE_DYNAMIC grande. Al principio del marco, asígnelo con D3D10_MAP_WRITE_DISCARD. Para cada llamada de dibujo posterior, avance el puntero de escritura más allá de la posición de los vértices dibujados anteriormente y asigne el búfer con D3D10_MAP_WRITE_NO_OVERWRITE. Si está cerca del final del búfer antes del final del marco, ajuste el puntero de escritura alrededor del principio y asigne con D3D10_MAP_WRITE_DISCARD.

¿Puedo escribir índices de 16 bits y índices de 32 bits en el mismo búfer de geometría dinámica?

Sí, puede, pero esto puede suponer una penalización de rendimiento en cierto hardware. Es más seguro crear búferes independientes para datos dinámicos de índice de 16 bits y datos de índice de 32 bits.

Cómo leer datos de la GPU a la CPU?

Debe usar un recurso de almacenamiento provisional. Copie los datos del recurso de GPU en el recurso de almacenamiento provisional mediante CopyResource. Asigne el recurso de almacenamiento provisional para leer los datos.

Mi aplicación dependía de la funcionalidad StretchRect.

Como esto era básicamente un contenedor para la funcionalidad básica de Direct3D, se quitó de la API. Parte de la funcionalidad StretchRect se movió a D3DX10LoadTextureFromTexture. Para las conversiones de formato y la copia de texturas, D3DX10LoadTextureFromTexture puede realizar el trabajo. Sin embargo, es probable que las operaciones como la conversión de un tamaño a otro requieran una operación de representación a textura en la aplicación.

No hay desplazamientos ni tamaños en las llamadas de asignación para los recursos. Estos estaban allí en las llamadas de bloqueo en Direct3D 9; ¿por qué cambiaron?

Los desplazamientos y los tamaños de las llamadas de bloqueo en Direct3D 9 eran básicamente desordenados por la API y, a menudo, el controlador ignoraba. En su lugar, la aplicación debe calcular los desplazamientos desde el puntero devuelto en la llamada a Map.

Profundidad como textura

¿Cuál es más rápido? ¿Usar profundidad como textura o escribir profundidad en alfa y leer eso?

Se trata de una aplicación y un hardware específicos. Use el que guarde más ancho de banda. Si ya usa varios destinos de representación y tiene un canal adicional, escribir profundidad desde el sombreador puede ser una mejor solución. Además, escribir profundidad en alfa u otro destino de representación permite escribir valores de profundidad lineales que pueden acelerar los cálculos que necesitan acceder al búfer de profundidad.

¿Puedo tener una textura enlazada como entrada Y enlazada como una textura de galería de símbolos de profundidad siempre que deshabilite las escrituras de profundidad?

No en D3D10.

MSAA

¿Puedo resolver una textura de galería de símbolos de profundidad de MSAA?

No en D3D10. Sin embargo, puede muestrear ejemplos individuales de la textura MSAA. Consulte la sección HLSL para obtener más información.

¿Por qué se bloquea mi aplicación tan pronto como se habilita MSAA?

Asegúrese de habilitar un número de muestras de MSAA y un número de calidad enumerados realmente por el controlador.

Bloqueos

Mi aplicación se bloquea en D3D10 o en el controlador y no sé por qué.

El primer paso es habilitar el entorno de ejecución de depuración (D3D10_CREATE_DEVICE_DEBUG marca pasada a D3D10CreateDevice). Esto expondrá los errores más comunes como salida de depuración.

PIX se bloquea cuando intento usar mi aplicación con ella.

El primer paso es habilitar el entorno de ejecución de depuración (D3D10_CREATE_DEVICE_DEBUG marca pasada a D3D10CreateDevice). PIX tiene una probabilidad mucho mayor de bloquearse si la salida de depuración no está limpia.

Mi juego se queda sin espacio de direcciones virtuales en Vista de 32 bits en D3D10. No tiene problemas en D3D9.

Hubo algunos problemas con D3D10 y el espacio de direcciones virtuales. Esto se ha corregido en KB940105. Si esto no soluciona el problema, asegúrese de que no está creando más recursos que se puedan asignar (bloqueados) en D3D10 de los que estaba creando en D3D9. Piense también en la migración a 64 bits, ya que esto será más frecuente en el futuro.

Representación prededicada

He usado representación predejada (basada en los resultados de la consulta de oclusión). ¿Por qué mi aplicación sigue siendo la misma velocidad?

En primer lugar, asegúrese de que la representación que desea omitir es realmente el cuello de botella de la aplicación. Si no es el cuello de botella, omitir la representación no ayudará a la velocidad de fotogramas.

En segundo lugar, asegúrese de que ha transcurrido suficiente tiempo entre el problema de la consulta y la representación que desea predicar. Si la consulta no ha finalizado en el momento en que la llamada de representación alcanza la GPU, la representación se producirá de todos modos.

En tercer lugar, el predicado solo omite determinadas llamadas. Las llamadas que se omiten son Draw, Clear, Copy, Update, ResolveSubresource y GenerateMips. La configuración de estado, la configuración de IA, la asignación y la creación de llamadas no respetan la predicación. Si hay una gran cantidad de llamadas de configuración de estado en torno a la llamada de dibujo que se va a indicar, se seguirán estableciendo estos estados.

Sombreador de geometría

¿Debo usar el sombreador de geometría para teselar mi (insertar algo aquí)?

No. El sombreador de geometría NO debe usarse para la teselación.

¿Puedo usar el sombreador de geometría para crear geometría?

Sí, en escenarios muy limitados. El sombreador de geometría en las piezas D3D10 (2008) actuales no está equipado para manejar gran expansión. En el futuro, esto puede cambiar. Los proveedores de tarjetas de vídeo pueden tener una ruta especial para una a cuatro expansiones debido al hardware de sprite de punto existente. Cualquier otra expansión tendría que ser muy limitada. Las muestras de ParticlesGS y PipesGS logran altas velocidades de fotogramas solo haciendo una expansión limitada. Solo unos pocos puntos se expanden por fotograma.

¿Para qué debo usar el sombreador de geometría?

Cualquier cosa que requiera operaciones en un primitivo completo, como la detección de siluetas, coordenadas barycéntricas, etc. Úselo también para seleccionar a qué segmento de una matriz de destino de representación se enviarán primitivos.

¿Puedo generar cantidades variables de geometría desde el sombreador de geometría?

Sí, pero esto puede causar problemas de rendimiento. Tome el ejemplo de salida de 1 punto para una invocación y 4 puntos para otra. Aunque se ajusta dentro de las directrices de expansión, esto puede hacer que los subprocesos del sombreador de geometría se ejecuten en serie.

¿Cómo sabe D3D10 cómo generar índices de adyacencia para mi malla? O bien, por qué D3D10 no se representa correctamente cuando se especifica que el sombreador de geometría necesita información de adyacencia.

D3D10 no crea la información de adyacencia, sino la aplicación. La aplicación genera índices de adyacencia y debe contener seis índices por primitivo; de los seis, los índices numerados impares son los vértices adyacentes del borde. ID3DX10Mesh::GenerateAdjacencyAndPointsReps se puede usar para generar estos datos.

HLSL

¿Las instrucciones enteros y bit a bit son lentas?

Pueden ser. Es posible que varias tarjetas D3D10 solo puedan emitir operaciones de enteros en un subconjunto de las unidades ALU disponibles. Esto depende en gran medida del hardware. Consulte a su proveedor de hardware individual para obtener recomendaciones sobre cómo abordar las operaciones de enteros en ese hardware concreto. Además, tenga mucho cuidado con las conversiones entre tipos.

¿Qué le pasó a VPOS?

Si declara una entrada en el sombreador de píxeles como SV_POSITION, obtendrá el mismo comportamiento que declararlo como VPOS.

Cómo muestra de una textura MSAA?

En el sombreador, declare la textura como Texture2DMS. A continuación, puede capturar ejemplos individuales mediante los métodos Sample del objeto Texture2DMS.

Cómo indicar si se usa realmente una variable de sombreador en un búfer de constantes?

Examine la estructura de D3D10_SHADER_VARIABLE_DESC reflejada para esa variable. uFlags debe tener establecida la marca D3D10_SVF_USED.

Cómo indicar si una variable de sombreador en un búfer de constantes usa realmente FX10?

Actualmente no es posible usar FX10.

No tengo control sobre los búferes de constantes que fx10 crea. ¿Cómo se crean y actualizan?

Todos los búferes de constantes administrados por FX10 se crean como recursos D3D10_USAGE_DEFAULT y se actualizan mediante UpdateSubresource. Dado que FX10 mantiene un almacén de respaldo de todos los datos constantes, UpdateSubresource es el mejor enfoque para actualizarlos.

Cómo emular la canalización de funciones fijas mediante sombreadores?

Consulte el ejemplo FixedFuncEMU.

¿Debo usar el nuevo \[unroll\], \[loop\], \[branch\], etc., ¿sugerencias del compilador?

En general, no. El compilador a menudo probará ambas formas y elegirá la más rápida. En algunos casos, puede ser necesario usar [anular la inscripción], por ejemplo, cuando una captura de textura dentro de un bucle necesita acceso a un degradado.

¿La precisión parcial marca alguna diferencia en D3D10? Puedo especificar la precisión parcial en mi D3D9 HLSL, pero no en mi D3D10 HLSL.

Todas las operaciones D3D10 se especifican para ejecutarse con precisión de punto flotante de 32 bits. Por lo tanto, la precisión parcial no debe marcar ninguna diferencia en D3D10.

En D3D9, podría realizar el filtrado de sombras PCF de HW enlazando un búfer de profundidad como textura y usando instrucciones hlsl tex2d normales. Cómo hacer esto en D3D10?

Tiene que usar un estado del sampler de comparación y usar las instrucciones de SampleCmp.

¿Cómo funciona esta palabra clave register en D3D10?

La palabra clave register de D3D10 ahora se aplica a la ranura a la que está enlazado un recurso determinado. En este caso, el recurso puede ser un búfer (constante o de otro modo), Textura o Sampler.

  • Para los búferes de constantes, use la sintaxis: register(bN), donde N es la ranura de entrada (0-15)
  • Para las texturas, use la sintaxis: register(tN), donde N es la ranura de entrada (0-127)
  • Para los muestreadores, use la sintaxis: register(sN), donde N es la ranura de entrada (0-127)

Cómo colocar una variable dentro de un búfer de constantes si el registro se usa para especificar dónde enlazar todo el búfer?

Use la palabra clave packoffset. El argumento para packoffset tiene la forma de c[0-4095]. [x,y,z,w]. Por ejemplo:

        cbuffer cbLotsOfEmptySpace
        {
        float   IWaste2Floats   : packoffset(c0.z);
        float4  IWasteMore  : packoffset(c13);
        };

En este búfer de constantes, IWaste2Floats se coloca en el tercer valor float (12º byte) en el búfer de constantes. IWasteMore se coloca en el 13º float4 o 52nd float en el búfer de constantes.