This article's documentation is for anything that uses the Source engine. Click here for more information.

Refract: Difference between revisions

From Valve Developer Community
Jump to navigation Jump to search
No edit summary
No edit summary
 
(39 intermediate revisions by 26 users not shown)
Line 1: Line 1:
[[Image:refract.jpg|thumb|A refracting [[func_brush]].]]
{{LanguageBar}}
{{Source topicon}}


The '''<code>Refract</code>''' shaders distorts objects behind it. It is similar to <code>[[Water (shader)|Water]]</code>, but does not reflect.
[[File:Refract.jpg|thumb|250px|A refracting [[func_brush]].]]


{{note|The shader may not work when applied to world geometry. Make any brushes you want it applied to are attached to entities (excluding [[func_detail]]).}}
{{this is a|pixel shader|name=Refract}} It distorts objects behind it. It is similar to <code>[[Water (shader)|Water]]</code>, but does not have real-time reflections and so is not restricted to flat surfaces. Can be used to create distorting glass windows, ice, etc.  


== Example ==
The refraction effect is achieved by first rendering the view without the refracting surface, and then using the normal map to distort the image by replacing pixel coordinates with new ones from the pre-rendered view by projecting along the normals.
 
{{note|Will not work when applied to [[world brush]]es in older engines.{{Clarify|Which engines does it work in? Might work regardless on {{cmd|%CompileWater}} materials.}}
{{workaround|Tie the refracting brushes to a {{ent|func_brush}} or similar entity.}}}}
{{note|Multiple layers of the <code>Refract</code> shader will not render when applied on the same entity.}}
{{tip|If you have a refract shader on your model that also has other materials, you must specify {{cmd|$mostlyopaque}} parameter to the QC and {{cmd|$nowritez|1}} & {{cmd|$model|1}} to the VMT. If the model only has one material, then only {{cmd|$model|1}} is necessary.}}
 
Keep in mind that refraction is expensive to render when sorted. Multiple layers of refraction can cause immense overdraw. Avoid having large amounts of particle sheets, or multiple surfaces with refract that render above each other.
 
== Syntax ==


  '''Refract'''
  '''Refract'''
  {
  {
  [[$normalmap]] ... // Defines the refraction pattern; may be animated
  $normalmap ...
  [[$dudvmap]] ... // As above when running below [[DirectX Versions|DX9]]
  $dudvmap ...
  [[$refracttint]] "[1 1 1]" // Colors the refraction
  $refracttint "[1 1 1]"
  [[$refractamount]] 0.2 // Refraction strength; use low values
  $refractamount .2
  }
  }


{{tip|<code>[[$refracttint]]</code> values greater than one can make it brighten instead of darken.}}
{{MatParamDef|$normalmap|texture}}
{{MatParamDef|$dudvmap|texture|The pattern of refraction is defined by a normal map (DX9+) or DUDV map (DX8-). May be animated.|dx8=1}}
{{MatParamDef|$normalmap2|texture|If a second normal map is specified, it will be blended with the first one.|since={{src07}}|dx9=1}}
{{MatParamDef|$bumpframe|and=$bumpframe2|int|The frame to start an animated bump map on.}}
{{MatParamDef|$bumptransform|and=$bumptransform2|vector3|Transforms the bump map texture.
{{VMT UVtransform}}}}
{{MatParamDef|$refracttint|RGB matrix|Tints the colour of the refraction uniformly. Can be used in conjunction with '''$refracttint'''}}
{{MatParamDef|$refracttinttexture|texture|Tints the colour of the refraction per-texel. Can be used in conjunction with '''$refracttint'''}}
{{MatParamDef|$refracttinttextureframe|int|Frame to start an animated <code>$refracttinttexture</code> on.}}
{{MatParamDef|$refractamount|float|{{Bug|{{portal2}} Incompatible with '''$localrefract'''.}}Controls the strength of the refraction by multiplying the normal map intensity.}}
{{MatParamDef|$bluramount|int|{{Bug|{{portal2}} Incompatible with '''$localrefract'''.}}Adds a blur effect. Valid values are 0, 1 and 2 (0 and 1 for DX8-).|}}
{{MatParamDef|$forcerefract|bool|Forces the shader to be used for cards with poor fill rate.|dx8=1}}
{{MatParamDef|$envmap|texture|Adds a cubemap reflection on top of the refraction.}}
{{MatParamDef|$envmaptint|RGB matrix|Controls the intensity of the reflection's red, green and blue color channels. Any positive number can be used. Default is <code>"[1 1 1]"</code>, which means 100% intensity.
: {{Note|You must use quotemarks, as there are space characters within the value.}}}}
{{MatParamDef|$envmapcontrast|normal|Controls the [[Wikipedia:Contrast (vision)|contrast]] of the reflection. 0 is natural contrast, while 1 is the full squaring of the color (i.e. color*color).}}
{{MatParamDef|$envmapsaturation|normal|Controls the colour saturation of the reflection. 0 is greyscale, while 1 is natural saturation.}}
{{MatParamDef|$fresnelreflection|float|{{Bug|'''Broken''' - Not implemented for this shader despite the parameter existing.}}|since={{src06}}}}
{{MatParamDef|$fadeoutonsilhouette|bool|Fades out the refraction effect around the edges.}}
{{MatParamDef|$vertexcolormodulate||{{todo|Use the vertex color to affect the refract color. Alpha will adjust refract amount. See {{ent|$vertexcolor}}.}}|since={{src07}}|dx9=1}}
{{MatParamDef|$basetexture|texture|Use a texture instead of rendering the view for the source of the distorted pixels.|dx9=1}}
{{MatParamDef|$masked|bool|{{todo|''mask using dest alpha''}}}}
{{MatParamDef|$forcealphawrite|bool|{{todo|''Force the material to write alpha to the dest buffer''}}|dx9=1|since={{src13}}}}
{{MatParamDef|$nowritez|int|{{todo|''0 {{=}}{{=}} write z, 1 {{=}} no write z''}}}}
{{MatParamDef|$noviewportfixup|int|Don't adjust UVs for current viewport.|since={{as}}}}
{{MatParamDef|$mirroraboutviewportedges|int|Don't sample outside of the viewport.|since={{as}}}}
{{MatParamDef|$magnifyenable|bool|Enable magnification of the refracted image around the <code>$magnifycenter</code> screen position by <code>$magnifyscale</code>.|since={{as}}}}
{{MatParamDef|$magnifycenter|vector2|Magnify the refracted image around this screen position.|since={{as}}}}
{{MatParamDef|$magnifyscale|float|Magnify the refracted image by this factor.|since={{as}}}}
{{MatParamDef|$localrefract|bool|Apply a simple parallax effect to the basetexture.|since={{portal2}}}}
{{MatParamDef|$localrefractdepth|float|Depth of the parallax effect in units.|since={{portal2}}}}
{{MatParamDef|$spitternoisetexture|texture|Seems to be simmillar to [[$flow_noise_texture]] but also tints the materials green. Seen in "Particle/warp_pool_01.vmt".|only={{L4D2}}?}}


{{tip|<code>[[$bluramount]]</code> 1.0 // Defines how much the refraction should blur.}}
== Caveats ==


{{tip|<code>[[$refracttinttexture]]</code> ... // Defines a texture map for tinting the refraction.}}
* Currently it is not possible to define an overall alpha mask to indicate where to fall-off refract. This however only applies to the brush based and model geometry, and not particles. To get alpha on brush or model based geometry you can create a normal map with an alpha channel, and define that as the first <code>$normalmap</code>. Using another normal of your choice you can then define a normal map for <code>$normalmap2</code>. <code>$normalmap2</code> will inherit the alpha of the first normalmap, and will act accordingly. This is extremely useful for faking effects like scrolling water of a surface. Where the first normal map can provide the alpha, and the second normal map can move along that alpha.
* If <code>Refract</code> is used on a part of a model, you must specify <code>[[$mostlyopaque]]</code> parameter to the qc of the model and <code>[[$nowritez|$nowritez "1"]]</code> & <code>[[$model|$model "1"]]</code>to refract vmt.
* This shader doesn't work properly with [[water]] dynamic reflections and [[sky_camera]]. Only for brushes, if a brush is world geometry or [[func_detail]]. This bug doesn't happen with ther secondary cameras ([[func_reflective_glass]], [[func_monitor]] and [[portals]]).


== See also ==
== See also ==


*<code>[[Water (shader)|Water]]</code>
* <kbd>[[Water (shader)|Water]]</kbd>
* <kbd>[[Predator]]</kbd> - an earlier (deprecated) version of Refract


{{otherlang:en}}
== External links ==
{{otherlang:en:fr|Refract:fr}}
* [https://a248.e.akamai.net/f/248/10/10/http.developer.nvidia.com/GPUGems2/gpugems2_chapter19.html Article about similar shaders]


[[Category:List of Shaders]]
[[Category:Shaders]]

Latest revision as of 11:41, 23 August 2025

English (en)Deutsch (de)Français (fr)中文 (zh)Translate (Translate)

A refracting func_brush.

Refract is a Pixel shader available in all Source Source games. It distorts objects behind it. It is similar to Water, but does not have real-time reflections and so is not restricted to flat surfaces. Can be used to create distorting glass windows, ice, etc.

The refraction effect is achieved by first rendering the view without the refracting surface, and then using the normal map to distort the image by replacing pixel coordinates with new ones from the pre-rendered view by projecting along the normals.

Note.pngNote:Will not work when applied to world brushes in older engines.
Clarify: Which engines does it work in? Might work regardless on %CompileWater materials.
PlacementTip.pngWorkaround:Tie the refracting brushes to a func_brush or similar entity.
Note.pngNote:Multiple layers of the Refract shader will not render when applied on the same entity.
Tip.pngTip:If you have a refract shader on your model that also has other materials, you must specify $mostlyopaque parameter to the QC and $nowritez 1 & $model 1 to the VMT. If the model only has one material, then only $model 1 is necessary.

Keep in mind that refraction is expensive to render when sorted. Multiple layers of refraction can cause immense overdraw. Avoid having large amounts of particle sheets, or multiple surfaces with refract that render above each other.

Syntax

Refract
{
	$normalmap ...
	$dudvmap ...
	$refracttint "[1 1 1]"
	$refractamount .2
}
Todo: This material shader parameter has not been described.
$dudvmap <texture> (DX8)
The pattern of refraction is defined by a normal map (DX9+) or DUDV map (DX8-). May be animated.
$normalmap2 <texture> (DX9 SM2) (in all games since Source 2007)
If a second normal map is specified, it will be blended with the first one.
The frame to start an animated bump map on.
Transforms the bump map texture.
The default position is center .5 .5 scale 1 1 rotate 0 translate 0 0.
  1. center defines the point of rotation. Only useful if rotate is being used.
  2. scale fits the texture into the material the given number of times. 2 1 is a 50% scale in the horizontal X axis while the vertical Y axis is still at original scale.
  3. rotate rotates the texture counter-clockwise in degrees. Accepts any number, including negatives.
  4. translate shifts the texture by the given numbers. .5 will shift it half-way. 1 will shift it once completely over, which is the same as not moving it at all.
Note.pngNote:All values must be included!
Icon-Bug.pngBug:Scaling the texture may cause odd issues where the Texture Lock tool in Hammer will not actually lock the texture in place.  [todo tested in ?]
Icon-Bug.pngBug:Rotating textures applied on brushes will rotate around the map origin (confirm: Orangebox engine only?). A fix for this is to change the center position in the VMT to the brush's origin.  [todo tested in ?]
Tints the colour of the refraction uniformly. Can be used in conjunction with $refracttint
Tints the colour of the refraction per-texel. Can be used in conjunction with $refracttint
Frame to start an animated $refracttinttexture on.
Icon-Bug.pngBug:Portal 2 Incompatible with $localrefract.  [todo tested in ?]
Controls the strength of the refraction by multiplying the normal map intensity.
Icon-Bug.pngBug:Portal 2 Incompatible with $localrefract.  [todo tested in ?]
Adds a blur effect. Valid values are 0, 1 and 2 (0 and 1 for DX8-).
Forces the shader to be used for cards with poor fill rate.
Adds a cubemap reflection on top of the refraction.
Controls the intensity of the reflection's red, green and blue color channels. Any positive number can be used. Default is "[1 1 1]", which means 100% intensity.
Note.pngNote:You must use quotemarks, as there are space characters within the value.
Controls the contrast of the reflection. 0 is natural contrast, while 1 is the full squaring of the color (i.e. color*color).
Controls the colour saturation of the reflection. 0 is greyscale, while 1 is natural saturation.
$fresnelreflection <float> (in all games since Source 2006)
Icon-Bug.pngBug:Broken - Not implemented for this shader despite the parameter existing.  [todo tested in ?]
Fades out the refraction effect around the edges.
$vertexcolormodulate <void> (DX9 SM2) (in all games since Source 2007)
Todo: Use the vertex color to affect the refract color. Alpha will adjust refract amount. See $vertexcolor.
$basetexture <texture> (DX9 SM2)
Use a texture instead of rendering the view for the source of the distorted pixels.
Todo: mask using dest alpha
$forcealphawrite <boolean> (DX9 SM2) (in all games since Source 2013)
Todo: Force the material to write alpha to the dest buffer
Todo: 0 == write z, 1 = no write z
$noviewportfixup <integer> (in all games since Alien Swarm)
Don't adjust UVs for current viewport.
Don't sample outside of the viewport.
$magnifyenable <boolean> (in all games since Alien Swarm)
Enable magnification of the refracted image around the $magnifycenter screen position by $magnifyscale.
$magnifycenter <vector2> (in all games since Alien Swarm)
Magnify the refracted image around this screen position.
$magnifyscale <float> (in all games since Alien Swarm)
Magnify the refracted image by this factor.
$localrefract <boolean> (in all games since Portal 2)
Apply a simple parallax effect to the basetexture.
$localrefractdepth <float> (in all games since Portal 2)
Depth of the parallax effect in units.
$spitternoisetexture <texture> (only in Left 4 Dead 2?)
Seems to be simmillar to $flow_noise_texture but also tints the materials green. Seen in "Particle/warp_pool_01.vmt".

Caveats

  • Currently it is not possible to define an overall alpha mask to indicate where to fall-off refract. This however only applies to the brush based and model geometry, and not particles. To get alpha on brush or model based geometry you can create a normal map with an alpha channel, and define that as the first $normalmap. Using another normal of your choice you can then define a normal map for $normalmap2. $normalmap2 will inherit the alpha of the first normalmap, and will act accordingly. This is extremely useful for faking effects like scrolling water of a surface. Where the first normal map can provide the alpha, and the second normal map can move along that alpha.
  • If Refract is used on a part of a model, you must specify $mostlyopaque parameter to the qc of the model and $nowritez "1" & $model "1"to refract vmt.
  • This shader doesn't work properly with water dynamic reflections and sky_camera. Only for brushes, if a brush is world geometry or func_detail. This bug doesn't happen with ther secondary cameras (func_reflective_glass, func_monitor and portals).

See also

External links