【OpenGL】Shader技巧集合
这篇文章将收集unity中使用shader的相关技巧和特效,会不断地更新内容。关于在Unity中使用shader的介绍,请参考《【OpenGL】使用Unity来学习OpenGL》 常用的内置uniform iResolution =》_ScreenParams iGlobalTime = _Time.y glFragCoord = f loat4 sp:WPOS
这篇文章将收集unity中使用shader的相关技巧和特效,会不断地更新内容。关于在Unity中使用shader的介绍,请参考《【OpenGL】使用Unity来学习OpenGL》
常用的内置uniform
iResolution =》_ScreenParams
iGlobalTime => _Time.y
glFragCoord => float4 sp:WPOS // 需要 #pragma target 3.0, 另外的方式请见下面
vec2 => float2
mix => lerp
mod => fmod
texture2D => tex2D
textureCube => texCUBE
mat2=>float2x2
fract=>frac
========
关于glFragCoord, 可以使用另外一种方式计算(支持3.0之前的)参考官方例子
o.scrPos = ComputeScreenPos(o.pos);
float2 wcoord = (i.scrPos.xy/i.scrPos.w);
-------
float2 wcoord = sp.xy/_ScreenParams.xy;
关于数学的Shader:https://www.shadertoy.com/view/ldlSD2 https://www.shadertoy.com/view/ldlSWj
很好的一个教程:http://ogldev.atspace.co.uk/index.html
Deferred Shading 原理: http://ogldev.atspace.co.uk/www/tutorial35/tutorial35.html
关于Stencil Buffer 的理解:http://www.cnblogs.com/mikewolf2002/archive/2012/05/15/2500867.html
更多文章:1)http://docs.unity3d.com/Manual/SL-Stencil.html
2) http://answers.unity3d.com/questions/590800/how-to-cullrender-to-through-a-window.html
Stencil Shadow Volume : http://ogldev.atspace.co.uk/www/tutorial40/tutorial40.html
http://en.wikipedia.org/wiki/Shadow_volume
镜面反射的实现原理:
ftp://ftp.sgi.com/sgi/opengl/contrib/blythe/advanced99/notes/node158.html
其它镜面反射:
http://en.wikibooks.org/wiki/Cg_Programming/Unity/Mirrors
在unity cg中可以使用[HideInInspector]来隐藏uniform属性,这样就可以用作自定义常量。
Physically Based Rendering: Tutorial: Physically Based Rendering, And you can too!
边缘检测:1) http://www.codeproject.com/Articles/94817/Pixel-Shader-for-Edge-Detection-and-Cartoon-Effect
2) http://coding-experiments.blogspot.hk/2010/06/edge-detection.html
3) http://en.wikipedia.org/wiki/Edge_detection
Cg函数表:http://http.developer.nvidia.com/CgTutorial/cg_tutorial_appendix_e.html
heat effect : http://forum.unity3d.com/threads/50132-Heat-Distortion, http://www.cnblogs.com/geoffyange/archive/2013/06/06/3122570.html
skin shading in unity: http://www.altdevblogaday.com/2011/12/31/skin-shading-in-unity3d/
http://http.developer.nvidia.com/GPUGems3/gpugems3_ch14.html
http://gamedev.stackexchange.com/questions/31308/algorithm-for-creating-spheres
RenderMan University: http://renderman.pixar.com/view/renderman-university
一些shader的例子:
Shader "stalendp/shaderTest02" { //see https://www.shadertoy.com/view/4sj3zy Properties { _MainTex ("Base (RGB)", 2D) = "white" {} } SubShader { Pass { CGPROGRAM #pragma vertex vert #pragma fragment frag #pragma target 3.0 #include "UnityCG.cginc" sampler2D _MainTex; //Variable declarations struct myvars { float3 bgColor; float sphereScale; float sphereShine; float3 sphereDiff; float3 sphereSpec; float2 specPoint; }; float4 vert(appdata_base v) : POSITION { return mul(UNITY_MATRIX_MVP, v.vertex); } float4 frag(float4 sp:WPOS): COLOR { myvars mv; mv.bgColor = float3(0.6, 0.5, 0.6); mv.sphereScale = 0.7; mv.sphereShine = 0.5; mv.sphereDiff = float3(0.5, 0.0, 0.5); mv.sphereSpec = float3(1.0, 1.0, 1.0); mv.specPoint = float2(0.2, -0.1); // creates shader pixel coordinates float2 uv = sp.xy/_ScreenParams.xy; // sets the position of the camera float2 p = uv * 2.5 - float2(1.0, 1.0); p.x *= _ScreenParams.x / _ScreenParams.y; // Rotates the sphere in a circle p.x += cos(-_Time.y) *0.35; p.y += sin(-_Time.y) * 0.35; // Rotates the specular point with the sphere mv.specPoint.x += cos(-_Time.y) * 0.35; mv.specPoint.y += sin(-_Time.y) * 0.35; //Sets the radius of the sphere to the middle of the screen float radius = length(p);//sqrt(dot(p, p)); float3 col = mv.bgColor; //Sets the initial dark shadow around the edge of the sphere float f = smoothstep(mv.sphereScale * 0.7, mv.sphereScale, length(p + mv.specPoint)); col -= lerp(col, float3(0.0,0.0,0.0), f) * 0.2; //Only carries out the logic if the radius of the sphere is less than the scale if(radius <br> <br> <pre class="brush:php;toolbar:false">Shader "Custom/shaderTest03" { // https://www.shadertoy.com/view/Xdf3DS Properties { _MainTex ("Base (RGB)", 2D) = "white" {} } SubShader { Pass { CGPROGRAM #pragma vertex vert #pragma fragment frag #pragma target 3.0 #include "UnityCG.cginc" sampler2D _MainTex; struct myvars { float k; float f; float threshold; float3 colour; float3 normal; float3 lightPos; float3 lightColour; float3 ambient; float shinyness; float diffuseFactor; float4 fragCoord; }; float2 center ( float2 border , float2 _offset , float2 vel, myvars mv) { float2 c = _offset + vel * _Time * 0.5; c = fmod ( c , 2. - 4. * border ); if ( c.x > 1. - border.x ) c.x = 2. - c.x - 2. * border.x; if ( c.x 1. - border.y ) c.y = 2. - c.y - 2. * border.y; if ( c.y b ) return 0.0; if ( r >= b/3.0 ) { float rb = 1.0 - r/b; return (3.0*mv.k)/2.0 * rb * rb; } if ( r >= 0.0 && r <br> <pre class="brush:php;toolbar:false">Shader "stalendp/shaderTest04" { //see https://www.shadertoy.com/view/Xsf3R8 Properties { _MainTex ("Base (RGB)", 2D) = "white" {} } SubShader { Pass { CGPROGRAM #pragma vertex vert #pragma fragment frag #pragma target 3.0 #include "UnityCG.cginc" sampler2D _MainTex; struct Ray { float3 org; float3 dir; }; float rayPlaneIntersect( Ray ray, float4 plane ) { float f = dot( ray.dir, plane.xyz ); float t = -( dot( ray.org, plane.xyz ) + plane.w ); t /= f; return t; } float3 shade( float3 pos, float3 nrm, float4 light ) { float3 toLight = light.xyz - pos; float toLightLen = length( toLight ); toLight = normalize( toLight ); float diff = dot( nrm, toLight ); float attn = 1.0 - pow( min( 1.0, toLightLen / light.w ), 2.0 ); float comb = 2.0 * diff * attn; return float3( comb, comb, comb ); } float4 vert(appdata_base v) : POSITION { return mul(UNITY_MATRIX_MVP, v.vertex); } float4 frag(float4 sp:WPOS): COLOR { // gl_FragCoord: location (0.5, 0.5) is returned // for the lower-left-most pixel in a window // XY of the normalized device coordinate // ranged from [-1, 1] float2 ndcXY = -1.0 + 2.0 * sp.xy / _ScreenParams.xy; // aspect ratio float aspectRatio = _ScreenParams.x / _ScreenParams.y; // scaled XY which fits the aspect ratio float2 scaledXY = ndcXY * float2( aspectRatio, 1.0 ); // camera XYZ in world space float3 camWsXYZ = float3( 0.0, 1.0, 0.0 ); camWsXYZ.z += 10.0 * cos( _Time.y ); // construct the ray in world space Ray ray; ray.org = camWsXYZ; ray.dir = float3( scaledXY, -2.0 ); // OpenGL is right handed // define the plane in world space float4 plane = float4( 0.0, 1.0, 0.0, 0.0 ); float t = rayPlaneIntersect( ray, plane ); // define the point light in world space (XYZ, range) float4 lightWs = float4( 0.0, 5.0, -5.0, 10.0 ); if ( t >= 0.0 ) { float3 sceneWsPos = ray.org + t * ray.dir; float3 sceneWsNrm = plane.xyz; float2 sceneUV = sceneWsPos.xz / 4.0; float4 sceneBase = tex2D( _MainTex, sceneUV ); float3 sceneShade = shade( sceneWsPos, sceneWsNrm, lightWs ); return float4( sceneShade * sceneBase.xyz, 1.0 ); } return float4( 0.0, 0.0, 0.0, 1.0 ); } ENDCG } } FallBack "Diffuse" }
Shader "stalendp/shaderTest04" { //see https://www.shadertoy.com/view/MdB3Dw Properties { _MainTex ("Base (RGB)", 2D) = "white" {} } SubShader { Pass { CGPROGRAM #pragma vertex vert #pragma fragment frag #pragma target 3.0 #include "UnityCG.cginc" #define USE_ANALYTICAL_MBLUR sampler2D _MainTex; // intersect a MOVING sphere float2 iSphere( in float3 ro, in float3 rd, in float4 sp, in float3 ve, out float3 nor ) { float t = -1.0; float s = 0.0; nor = float3(0.0); float3 rc = ro - sp.xyz; float A = dot(rc,rd); float B = dot(rc,rc) - sp.w*sp.w; float C = dot(ve,ve); float D = dot(rc,ve); float E = dot(rd,ve); float aab = A*A - B; float eec = E*E - C; float aed = A*E - D; float k = aed*aed - eec*aab; if( k>0.0 ) { k = sqrt(k); float hb = (aed - k)/eec; float ha = (aed + k)/eec; float ta = max( 0.0, ha ); float tb = min( 1.0, hb ); if( ta 0.0 ) { t = -b - sqrt(k); nor = normalize( (ro+rd*t) - sp.xyz ); } return t; } float3 getPosition( float time ) { return float3( 2.5*sin(8.0*time), 0.0, 1.0*cos(8.0*time) ); } float3 getVelocity( float time ) { return float3( 8.0*2.5*cos(8.0*time), 0.0, -8.0*1.0*sin(8.0*time) ); } float4 vert(appdata_base v) : POSITION { return mul(UNITY_MATRIX_MVP, v.vertex); } float4 frag(float4 sp:WPOS): COLOR { float2 q = sp.xy / _ScreenParams.xy; float2 p = -1.0 + 2.0*q; p.x *= _ScreenParams.x/_ScreenParams.y; // camera float3 ro = float3(0.0,0.0,4.0); float3 rd = normalize( float3(p.xy,-2.0) ); // sphere // render float3 col = float3(0.0); #ifdef USE_ANALYTICAL_MBLUR //--------------------------------------------------- // render with analytical motion blur //--------------------------------------------------- float3 ce = getPosition( _Time.y ); float3 ve = getVelocity( _Time.y ); col = float3(0.25) + 0.3*rd.y; float3 nor = float3(0.0); float3 tot = float3(0.25) + 0.3*rd.y; float2 res = iSphere( ro, rd, float4(ce,1.0), ve/24.0, nor ); float t = res.x; if( t>0.0 ) { float dif = clamp( dot(nor,float3(0.5703)), 0.0, 1.0 ); float amb = 0.5 + 0.5*nor.y; float3 lcol = dif*float3(1.0,0.9,0.3) + amb*float3(0.1,0.2,0.3); col = lerp( tot, lcol, res.y ); } #else //--------------------------------------------------- // render with brute force sampled motion blur //--------------------------------------------------- #define NUMSAMPLES 32 float3 tot = float3(0.0); for( int i=0; i<numsamples i float fi="float(i)/float(NUMSAMPLES);" float3 ce="getPosition(" _time.y nor="float3(0.0);" tmp="float3(0.25)" t="iSphere(" ro rd float4 if>0.0 ) { float dif = clamp( dot(nor,float3(0.5703)), 0.0, 1.0 ); float amb = 0.5 + 0.5*nor.y; tmp = dif*float3(1.0,0.9,0.3) + amb*float3(0.1,0.2,0.3); } col += tmp; } col /= float(NUMSAMPLES); #endif col = pow( clamp(col,0.0,1.0), float3(0.45) ); return float4( col, 1.0 ); } ENDCG } } FallBack "Diffuse" } </numsamples>
Shader "stalendp/shaderTest05" { //see https://www.shadertoy.com/view/XsB3DW Properties { _MainTex ("Base (RGB)", 2D) = "white" {} _CubeDiffuse ("Cubemap Diffuse Map", CUBE) = "" {} vv1("vv1", float) = -1.0 vv2("vv2", float) = 2.0 } SubShader { Pass { CGPROGRAM #pragma vertex vert #pragma fragment frag #pragma target 3.0 //下面防止编译错误:instruction limit of 1024 exceed; #pragma glsl #include "UnityCG.cginc" #define MAX_STEPS 64 #define MAX_REFLECTIONS 4 #define PI 3.1415926536 sampler2D _MainTex; samplerCUBE _CubeDiffuse; float vv1, vv2; struct Ray { float3 o; float3 d; }; struct Sphere { float3 o; float r; }; struct Box { float3 o; float3 s; }; struct Torus { float3 o; float2 s; }; float2 rotate2d(in float2 v, in float a) { float sinA = sin(a); float cosA = cos(a); return float2(v.x * cosA - v.y * sinA, v.y * cosA + v.x * sinA); } float sdSphere(in float3 p, in Sphere s) { return length(p-s.o)-s.r; } float sdBox(in float3 p, in Box b) { float3 d = abs(p-b.o) - b.s; return min(max(d.x,max(d.y,d.z)),0.0) + length(max(d,0.0)); } float sdTorus(in float3 p, in Torus t) { p -= t.o; float2 q = float2(length(p.xz)-t.s.x,p.y); return length(q)-t.s.y; } float world(in float3 p) { float ti = fmod(_Time.y,10.); if(ti > 2.) { Sphere s0 = Sphere(float3(0),1.); Box b0 = Box(float3(0),float3(.8)); if(ti <br> <div class="code" style="position:relative; padding:0px; margin:0px;"><div class="code" style="position:relative; padding:0px; margin:0px;"><div class="code" style="position:relative; padding:0px; margin:0px;"><div class="code" style="position:relative; padding:0px; margin:0px;"><pre class="brush:php;toolbar:false">
CGINCLUDE的使用

Hot AI Tools

Undresser.AI Undress
AI-powered app for creating realistic nude photos

AI Clothes Remover
Online AI tool for removing clothes from photos.

Undress AI Tool
Undress images for free

Clothoff.io
AI clothes remover

AI Hentai Generator
Generate AI Hentai for free.

Hot Article

Hot Tools

Notepad++7.3.1
Easy-to-use and free code editor

SublimeText3 Chinese version
Chinese version, very easy to use

Zend Studio 13.0.1
Powerful PHP integrated development environment

Dreamweaver CS6
Visual web development tools

SublimeText3 Mac version
God-level code editing software (SublimeText3)

Hot Topics

1. How can you make money by publishing articles on Toutiao today? How to earn more income by publishing articles on Toutiao today! 1. Activate basic rights and interests: original articles can earn profits by advertising, and videos must be original in horizontal screen mode to earn profits. 2. Activate the rights of 100 fans: if the number of fans reaches 100 fans or above, you can get profits from micro headlines, original Q&A creation and Q&A. 3. Insist on original works: Original works include articles, micro headlines, questions, etc., and are required to be more than 300 words. Please note that if illegally plagiarized works are published as original works, credit points will be deducted, and even any profits will be deducted. 4. Verticality: When writing articles in professional fields, you cannot write articles across fields at will. You will not get appropriate recommendations, you will not be able to achieve the professionalism and refinement of your work, and it will be difficult to attract fans and readers. 5. Activity: high activity,

Win11 Tips Sharing: One trick to skip Microsoft account login Windows 11 is the latest operating system launched by Microsoft, with a new design style and many practical functions. However, for some users, having to log in to their Microsoft account every time they boot up the system can be a bit annoying. If you are one of them, you might as well try the following tips, which will allow you to skip logging in with a Microsoft account and enter the desktop interface directly. First, we need to create a local account in the system to log in instead of a Microsoft account. The advantage of doing this is

We often create and edit tables in excel, but as a novice who has just come into contact with the software, how to use excel to create tables is not as easy as it is for us. Below, we will conduct some drills on some steps of table creation that novices, that is, beginners, need to master. We hope it will be helpful to those in need. A sample form for beginners is shown below: Let’s see how to complete it! 1. There are two methods to create a new excel document. You can right-click the mouse on a blank location on the [Desktop] - [New] - [xls] file. You can also [Start]-[All Programs]-[Microsoft Office]-[Microsoft Excel 20**] 2. Double-click our new ex

It is difficult to implement collection-like functions in the Go language, which is a problem that troubles many developers. Compared with other programming languages such as Python or Java, the Go language does not have built-in collection types, such as set, map, etc., which brings some challenges to developers when implementing collection functions. First, let's take a look at why it is difficult to implement collection-like functionality directly in the Go language. In the Go language, the most commonly used data structures are slice and map. They can complete collection-like functions, but

In C language, it represents a pointer, which stores the address of other variables; & represents the address operator, which returns the memory address of a variable. Tips for using pointers include defining pointers, dereferencing pointers, and ensuring that pointers point to valid addresses; tips for using address operators & include obtaining variable addresses, and returning the address of the first element of the array when obtaining the address of an array element. A practical example demonstrating the use of pointer and address operators to reverse a string.

VSCode (Visual Studio Code) is an open source code editor developed by Microsoft. It has powerful functions and rich plug-in support, making it one of the preferred tools for developers. This article will provide an introductory guide for beginners to help them quickly master the skills of using VSCode. In this article, we will introduce how to install VSCode, basic editing operations, shortcut keys, plug-in installation, etc., and provide readers with specific code examples. 1. Install VSCode first, we need

Hardwood is an important synthetic material in Stardew Valley. We can have many uses in the game, so we can stock it up in our daily life. What are the specific ways to obtain hardwood? Below we will bring you Stardew Valley. You can refer to the way to obtain hardwood in Monogatari if necessary. Ways to obtain hardwood in Stardew Valley 1. Go to the secret forest every day to dig tree stumps to quickly obtain hardwood. 2. There is a chance to obtain mahogany seeds by mining tree stumps and fighting monsters in the secret forest. 3. Planting seeds in the yard will produce mahogany trees. 4. Finally, after mining mahogany, you can quickly obtain a large amount of hardwood.

Title: PHP Programming Tips: How to Jump to a Web Page within 3 Seconds In web development, we often encounter situations where we need to automatically jump to another page within a certain period of time. This article will introduce how to use PHP to implement programming techniques to jump to a page within 3 seconds, and provide specific code examples. First of all, the basic principle of page jump is realized through the Location field in the HTTP response header. By setting this field, the browser can automatically jump to the specified page. Below is a simple example demonstrating how to use P
