Después de que se haya calculado la iluminación básica del vértice, se aplicarán las texturas. En ShaderLab esto se hace usando el comando SetTexture.
Nota: Los comandos SetTexture no tienen efecto cuando se utilizan fragment programs; ya que en ese caso las operaciones de píxeles se describen completamente en el shader. Es aconsejable utilizar shaders programables en estos días en lugar de los comandos de SetTexture.
La texturización de función fija es el lugar para hacer efectos combinadores de estilo antiguo. Puede tener varios comandos SetTexture dentro de un pass - todas las texturas se aplican en secuencia, como capas en un programa de pintura. Los comandos SetTexture deben colocarse al final de un Pass.
SetTexture [TextureName] {Texture Block}
Asigna una textura. TextureName debe definirse como una propiedad de textura. Cómo aplicar la textura se define dentro del TextureBlock.
El bloque de textura controla cómo se aplica la textura. Dentro del bloque de textura puede haber hasta dos comandos: combine
y constantColor
.
combine
combine
src1 * src2: Multiplies src1 and src2 together. The result will be darker than either input.
Combine
src1 + src2: Añade src1 y src2 juntos. El resultado será más claro que cualquiera de los inputs.
combine
src1 - src2: Resta src2 de src1.
combine
src1lerp
(src2) src3: Interpola entre src3 y src1, usando el alfa de src2. Tenga en cuenta que la interpolación es la dirección opuesta: src1 se utiliza cuando alfa es uno, y src3 se utiliza cuando alfa es cero.
combine
src1 * src2 + src3: Multiplies src1 with the alpha component of src2, then adds src3.
Todas las propiedades src pueden ser una de previous, constant, primary o texture.
Modificadores:
lerp
, pueden ser precedidas opcionalmente por one - para hacer que el color resultante sea negado.constantColor
ConstantColor color: Define un color constante que se puede utilizar en el comando combine.
Las versiones de Unity antes de 5.0 soportaban transformaciones de coordenadas de textura con un comando matrix
dentro de un bloque de textura. Si necesita esta funcionalidad ahora, considere la posibilidad de volver a escribir su shader como un shader programable en su lugar, y realice la transformación UV en el vertex shader.
De forma similar, se suprimen las combinaciones de signo agregadas (a+-b
), las combinaciones de signo add multiplicadas (a*b+-c
), las restas multiplicables (a*b-c
) y los modos de producto punto de textura (dot3
, dot3rgba
). Si los necesita, haga las matemáticas en el pixel shader en su lugar.
Antes de que existieran fragment programs, las tarjetas gráficas más antiguas usaban un método de capas para texturas. Las texturas se aplican una tras otra, modificando el color que se escribía en la pantalla. Para cada textura, la textura se combina típicamente con el resultado de la operación anterior. En estos días es aconsejable utilizar programas de fragmentos reales.
Tenga en cuenta que cada etapa de textura puede o no puede ser fijada al rango 0..1, dependiendo de la plataforma. Esto podría afectar a las etapas de SetTexture que pueden producir valores superiores a 1.0.
De forma predeterminada, la fórmula del combinador se utiliza para calcular tanto el componente RGB como el componente alfa del color. Opcionalmente, puede especificar una fórmula separada para el cálculo alfa. Esto se parece a esto:
SetTexture [_MainTex] { combine previous * texture, previous + texture }
Aquí, multiplicamos los colores RGB y añadimos el alfa.
Por defecto, el color primario es la suma de los colores difuso, ambiental y especular (como se define en el Cálculo de iluminación). Si especifica SeparateSpecular On en las opciones de pass, el color especular se agregará después del cálculo del combinador, en lugar de hacerlo antes. Este es el comportamiento predeterminado del shader VertexLit incorporado.
Las tarjetas gráficas modernas con soporte de fragment shader (“shader model 2.0” en el escritorio, OpenGL ES 2.0 en móvil) soportan todos los modos SetTexture y al menos 4 niveles de textura (muchos de ellos soportan 8). Si está ejecutando hardware realmente antiguo (hecho antes de 2003 en PC o antes de iPhone3GS en dispositivos móviles), es posible que tenga dos niveles de textura. El autor del shader debe escribir separar SubShaders para las tarjetas que quieren apoyar.
This small examples takes two textures. First it sets the first combiner to just take the _MainTex, then is uses the alpha channel of _BlendTex to fade in the RGB colors of _BlendTex
Shader "Examples/2 Alpha Blended Textures" {
Properties {
_MainTex ("Base (RGB)", 2D) = "white" {}
_BlendTex ("Alpha Blended (RGBA) ", 2D) = "white" {}
}
SubShader {
Pass {
// Apply base texture
SetTexture [_MainTex] {
combine texture
}
// Blend in the alpha texture using the lerp operator
SetTexture [_BlendTex] {
combine texture lerp (texture) previous
}
}
}
}
This shader uses the alpha component of the _MainTex to decide where to apply lighting. It does this by applying the texture to two stages; In the first stage, the alpha value of the texture is used to blend between the vertex color and solid white. In the second stage, the RGB values of the texture are multiplied in.
Shader "Examples/Self-Illumination" {
Properties {
_MainTex ("Base (RGB) Self-Illumination (A)", 2D) = "white" {}
}
SubShader {
Pass {
// Set up basic white vertex lighting
Material {
Diffuse (1,1,1,1)
Ambient (1,1,1,1)
}
Lighting On
// Use texture alpha to blend up to white (= full illumination)
SetTexture [_MainTex] {
constantColor (1,1,1,1)
combine constant lerp(texture) previous
}
// Multiply in texture
SetTexture [_MainTex] {
combine previous * texture
}
}
}
}
Sin embargo, podemos hacer otra cosa gratis aquí; En vez de mezclar a blanco sólido, podemos agregar un color de la uno mismo-iluminación y una mezcla a ése. Observe el uso de ConstantColor para obtener un _SolidColor de las propiedades en la mezcla de textura.
Shader "Examples/Self-Illumination 2" {
Properties {
_IlluminCol ("Self-Illumination color (RGB)", Color) = (1,1,1,1)
_MainTex ("Base (RGB) Self-Illumination (A)", 2D) = "white" {}
}
SubShader {
Pass {
// Set up basic white vertex lighting
Material {
Diffuse (1,1,1,1)
Ambient (1,1,1,1)
}
Lighting On
// Use texture alpha to blend up to white (= full illumination)
SetTexture [_MainTex] {
// Pull the color property into this blender
constantColor [_IlluminCol]
// And use the texture's alpha to blend between it and
// vertex color
combine constant lerp(texture) previous
}
// Multiply in texture
SetTexture [_MainTex] {
combine previous * texture
}
}
}
}
Y finalmente, tomamos todas las propiedades de iluminación del shader vertexlit y tiramos eso en:
Shader "Examples/Self-Illumination 3" {
Properties {
_IlluminCol ("Self-Illumination color (RGB)", Color) = (1,1,1,1)
_Color ("Main Color", Color) = (1,1,1,0)
_SpecColor ("Spec Color", Color) = (1,1,1,1)
_Emission ("Emmisive Color", Color) = (0,0,0,0)
_Shininess ("Shininess", Range (0.01, 1)) = 0.7
_MainTex ("Base (RGB)", 2D) = "white" {}
}
SubShader {
Pass {
// Set up basic vertex lighting
Material {
Diffuse [_Color]
Ambient [_Color]
Shininess [_Shininess]
Specular [_SpecColor]
Emission [_Emission]
}
Lighting On
// Use texture alpha to blend up to white (= full illumination)
SetTexture [_MainTex] {
constantColor [_IlluminCol]
combine constant lerp(texture) previous
}
// Multiply in texture
SetTexture [_MainTex] {
combine previous * texture
}
}
}
}