DGL
https://delphigl.com/forum/

Wasser > Foam (Schaum)
https://delphigl.com/forum/viewtopic.php?f=20&t=10354
Seite 1 von 1

Autor:  Thmfrnk [ Mo Mär 12, 2012 13:29 ]
Betreff des Beitrags:  Wasser > Foam (Schaum)

Moinsen,

ich möchte gern an den Schnittflächen zum Terrain Schaum rendern. Dazu habe ich folgendes gedacht. Ich habe ja meine Tiefentextur aus dem DFS pass. Im Wassershader müsste ich aus dieser Tiefemap, welche ja Screenspace ist, die 3D-Position zurückrechnen und die Entfernung zum aktuellen Pixel berechnen.

Wie bekomme ich aber die passenden Texturkoordinaten für die Tiefenmap? Mein Gefühl würde mir sagen:

Code:
  1.  
  2.  ScreenSpaceVec = gl_ProjectionMatrix * gl_ModelViewMatrix * gl_Vertex;
  3.  DepthTexCoord.xy = vec2(1.0) / ScreenSpaceVec;
  4.  


doch ich glaube so einfach ist das nicht oder?

Autor:  Sellmann [ Mo Mär 12, 2012 15:14 ]
Betreff des Beitrags:  Re: Wasser > Foam (Schaum)

Ich habe hier ein nettes paper gefunden:

http://http.developer.nvidia.com/GPUGem ... _ch27.html

Das geht zwar um depth-of-field, aber weiter unten ist ein Beispiel, wie man aus dem Wert im Depthbuffer und der Screencoord die Weltkoordinate zurückrechnen kann. NOT TESTED YET! :)

gruß, sellmann.

Autor:  Thmfrnk [ Mo Mär 12, 2012 16:42 ]
Betreff des Beitrags:  Re: Wasser > Foam (Schaum)

problem ist ja das mir die ScreenCoords fehlen.. ich render ja das wasser nicht im Fullscreenquad..

Autor:  damadmax [ Mo Mär 12, 2012 17:41 ]
Betreff des Beitrags:  Re: Wasser > Foam (Schaum)

Thmfrnk hat geschrieben:
problem ist ja das mir die ScreenCoords fehlen.. ich render ja das wasser nicht im Fullscreenquad..

den Ansatz finde ich aber garnicht so schlecht. Diese Artikel bei gamedev geht darauf ein.

Autor:  Coolcat [ Mo Mär 12, 2012 17:52 ]
Betreff des Beitrags:  Re: Wasser > Foam (Schaum)

Zitat:
problem ist ja das mir die ScreenCoords fehlen.. ich render ja das wasser nicht im Fullscreenquad..

Ohne jetzt das Paper gelesen zu haben, hilft dir gl_FragCoord weiter?
http://wiki.delphigl.com/index.php/Tuto ... ent_Shader
Der Wert müsste zwischen -1 und 1 liegen. Also:
Code:
  1. ScreenCoords = (gl_FragCoord.xy*0.5+0.5)*viewportSize;

Autor:  Thmfrnk [ Mo Mär 12, 2012 18:32 ]
Betreff des Beitrags:  Re: Wasser > Foam (Schaum)

damadmax hat geschrieben:
Thmfrnk hat geschrieben:
problem ist ja das mir die ScreenCoords fehlen.. ich render ja das wasser nicht im Fullscreenquad..

den Ansatz finde ich aber garnicht so schlecht. Diese Artikel bei gamedev geht darauf ein.


das hört sich doch mal interessant an... mal gucken ob ich das zum laufen bekomme..

Autor:  Thmfrnk [ Mi Mär 14, 2012 09:15 ]
Betreff des Beitrags:  Re: Wasser > Foam (Schaum)

ich habe mal versucht den HLSL Shader aus dem Link in GLSL zu übersetzten, doch irgendwie steigt der mittendrin aus und zeigt mir nur die HeightMap vom Wasser an..
hier mal mein Code:

Code:
  1.  
  2. #version 120
  3. uniform sampler2D heightMap;
  4. uniform sampler2D backBufferMap;
  5. uniform sampler2D depthMap;
  6. uniform sampler2D normalMap;
  7. uniform sampler2D foamMap;
  8. uniform sampler2D reflectionMap;
  9. uniform mat4 proM;
  10.  
  11. // We need this matrix to restore position in world space
  12. uniform mat4 matViewInverse;
  13. uniform vec3 cameraPos;
  14.  
  15. float waterLevel = 0.0;
  16.  
  17. // How fast will colours fade out. You can also think about this
  18. // values as how clear water is. Therefore use smaller values (eg. 0.05f)
  19. // to have crystal clear water and bigger to achieve "muddy" water.
  20. float fadeSpeed = 0.15;
  21.  
  22. // Timer
  23. float timer = 1.0;
  24.  
  25. // Normals scaling factor
  26. float normalScale = 1.0;
  27.  
  28. // R0 is a constant related to the index of refraction (IOR).
  29. // It should be computed on the CPU and passed to the shader.
  30. float R0 = 0.5;
  31.  
  32. // Maximum waves amplitude
  33. float maxAmplitude = 1.0;
  34.  
  35. // Direction of the light
  36. vec3 lightDir = vec3(0.0, 1.0, 0.0);
  37.  
  38. // Colour of the sun
  39. vec3 sunColor = vec3(1.0, 1.0, 1.0);
  40.  
  41. // The smaller this value is, the more soft the transition between
  42. // shore and water. If you want hard edges use very big value.
  43. // Default is 1.0f.
  44. float shoreHardness = 1.0;
  45.  
  46. // This value modifies current fresnel term. If you want to weaken
  47. // reflections use bigger value. If you want to empasize them use
  48. // value smaller then 0. Default is 0.0f.
  49. float refractionStrength = 0.0;
  50. //float refractionStrength = -0.3f;
  51.  
  52. // Modifies 4 sampled normals. Increase first values to have more
  53. // smaller "waves" or last to have more bigger "waves"
  54. vec4 normalModifier = vec4(1.0, 2.0, 4.0, 8.0);
  55.  
  56. // Strength of displacement along normal.
  57. float displace = 1.7;
  58.  
  59. // Describes at what depth foam starts to fade out and
  60. // at what it is completely invisible. The fird value is at
  61. // what height foam for waves appear (+ waterLevel).
  62. vec3 foamExistence = vec3(0.65, 1.35, 0.5);
  63.  
  64. float sunScale = 3.0;
  65.  
  66. mat4 matReflection = mat4(
  67.     0.5, 0.0, 0.0, 0.5,
  68.     0.0, 0.5, 0.0, 0.5,
  69.     0.0, 0.0, 0.0, 0.5,
  70.     0.0, 0.0, 0.0, 1.0);
  71.  
  72. mat4 matViewProj;
  73.  
  74. float shininess = 0.7;
  75. float specular_intensity = 0.32;
  76.  
  77. // Colour of the water surface
  78. vec3 depthColour = vec3(0.0078, 0.5176, 0.7);
  79. // Colour of the water depth
  80. vec3 bigDepthColour = vec3(0.0039, 0.00196, 0.145);
  81. vec3 extinction = vec3(7.0, 30.0, 40.0);            // Horizontal
  82.  
  83. // Water transparency along eye vector.
  84. float visibility = 4.0;
  85.  
  86. // Increase this value to have more smaller waves.
  87. vec2 scale = vec2(0.005, 0.005);
  88. float refractionScale = 0.005;
  89.  
  90. // Wind force in x and z axes.
  91. vec2 wind = vec2(-0.3, 0.7);
  92.  
  93. mat3x3 compute_tangent_frame(vec3 N, vec3 P, vec2 UV)
  94. {
  95.     vec3 dp1 = dFdx(P);
  96.     vec3 dp2 = dFdy(P);
  97.     vec2 duv1 = dFdx(UV);
  98.     vec2 duv2 = dFdy(UV);
  99.    
  100.     mat3x3 M = mat3x3(dp1, dp2, cross(dp1, dp2));
  101.     mat2x3 inverseM = mat2x3( cross( M[1], M[2] ), cross( M[2], M[0] ) );
  102.     //float3 T = mul(float2(duv1.x, duv2.x), inverseM);
  103. //  float3 B = mul(float2(duv1.y, duv2.y), inverseM);
  104.  
  105.     vec3 T = inverseM * vec2(duv1.x, duv2.x);   //hier bin ich mir nicht sicher
  106.     vec3 B = inverseM * vec2(duv1.y, duv2.y);
  107.    
  108.     return mat3x3(normalize(T), normalize(B), N);
  109. }
  110.  
  111.  
  112. // Function calculating fresnel term.
  113. // - normal - normalized normal vector
  114. // - eyeVec - normalized eye vector
  115. float fresnelTerm(vec3 normal, vec3 eyeVec)
  116. {
  117.         float angle = 1.0 - clamp(dot(normal, eyeVec), 0.0, 1.0);
  118.         float fresnel = angle * angle;
  119.         fresnel = fresnel * fresnel;
  120.         fresnel = fresnel * angle;
  121.         return clamp(fresnel * (1.0 - clamp(R0, 0.0, 1.0)) + R0 - refractionStrength, 0.0, 1.0);
  122. }
  123.  
  124.  
  125. //3D Position aus DepthMap ermitteln
  126. vec3 getPosition(vec2 uv) {
  127.         float fDepth = texture2D(depthMap, uv).x;      
  128.         vec4 vVertex;      
  129.         vVertex.xy = uv  * 2.0 - 1.0 ;                         
  130.         vVertex.z = fDepth * 2.0 - 1.0;  
  131.         vVertex.w = 1.0;
  132.         vVertex =  proM * vVertex;               
  133.         vVertex *= 1.0 / vVertex.w;
  134.         return  vVertex.xyz;
  135. }
  136.  
  137.  
  138. void main (void) {
  139.     vec3 color2 = texture2D(backBufferMap, gl_TexCoord[0].xy).rgb;
  140.     vec3 color = color2;
  141.    
  142.     //vec3 position = mul(float4(tex2D(positionMap, IN.texCoord).xyz, 1.0f), matViewInverse).xyz;
  143.      
  144.     vec3 position = getPosition(gl_TexCoord[0].xy).xyz;
  145.  
  146.     float level = waterLevel;
  147.     float depth = 0.0;
  148.  
  149.    
  150.     // If we are underwater let's leave out complex computations
  151.     if(level >= cameraPos.y)
  152.      {   
  153.        gl_FragColor =  vec4(color2, 1.0f);
  154.        discard;        
  155.       }
  156.      
  157.  
  158. if(position.y <= level + maxAmplitude)
  159.     {
  160.         vec3 eyeVec = position - cameraPos;
  161.         float diff = level - position.y;
  162.         float cameraDepth = cameraPos.y - position.y;
  163.        
  164.         // Find intersection with water surface
  165.         vec3 eyeVecNorm = normalize(eyeVec);
  166.         float t = (level - cameraPos.y) / eyeVecNorm.y;
  167.         vec3 surfacePoint = cameraPos + eyeVecNorm * t;
  168.        
  169.         eyeVecNorm = normalize(eyeVecNorm);
  170.            
  171.         vec2 texCoord;
  172.         for(int i = 0; i < 10; ++i)
  173.         {
  174.             texCoord = (surfacePoint.xz + eyeVecNorm.xz * 0.1) * scale + timer * 0.000005 * wind;
  175.            
  176.             float bias = texture2D(heightMap, texCoord).r;
  177.    
  178.             bias *= 0.1;
  179.             level += bias * maxAmplitude;
  180.             t = (level - cameraPos.y) / eyeVecNorm.y;
  181.             surfacePoint = cameraPos + eyeVecNorm * t;
  182.         }
  183.        
  184.         depth = length(position - surfacePoint);
  185.         float depth2 = surfacePoint.y - position.y;
  186.        
  187.         eyeVecNorm = normalize(cameraPos - surfacePoint);
  188.        
  189.         float normal1 = texture2D(heightMap, (texCoord + vec2(-1.0, 0.0) / 256.0)).r;
  190.         float normal2 = texture2D(heightMap, (texCoord + vec2(1.0, 0.0) / 256.0)).r;
  191.         float normal3 = texture2D(heightMap, (texCoord + vec2(0.0, -1.0) / 256.0)).r;
  192.         float normal4 = texture2D(heightMap, (texCoord + vec2(0.0, 1.0) / 256.0)).r;
  193.        
  194.         vec3 myNormal = normalize(vec3((normal1 - normal2) * maxAmplitude,
  195.                                            normalScale,
  196.                                            (normal3 - normal4) * maxAmplitude));  
  197.        
  198.         texCoord = surfacePoint.xz * 1.6 + wind * timer * 0.00016;
  199.         mat3x3 tangentFrame = compute_tangent_frame(myNormal, eyeVecNorm, texCoord);
  200. //      float3 normal0a = normalize(mul(2.0f * tex2D(normalMap, texCoord) - 1.0f, tangentFrame));
  201.  
  202.     //  vec3 normal0a = normalize(mul(2.0 * texture2D(normalMap, texCoord) - 1.0, tangentFrame));   //kein mul() bei GLSL??
  203.        
  204.         vec3 normal0a = normalize(tangentFrame * vec3(texture2D(normalMap, texCoord)).xyz * 2.0 - 1.0);
  205.        
  206.         texCoord = surfacePoint.xz * 0.8 + wind * timer * 0.00008;
  207.         tangentFrame = compute_tangent_frame(myNormal, eyeVecNorm, texCoord);
  208. //      float3 normal1a = normalize(mul(2.0f * tex2D(normalMap, texCoord) - 1.0f, tangentFrame));
  209.         vec3 normal1a = normalize(tangentFrame * vec3(texture2D(normalMap, texCoord)).xyz * 2.0 - 1.0);
  210.        
  211.         texCoord = surfacePoint.xz * 0.4 + wind * timer * 0.00004;
  212.         tangentFrame = compute_tangent_frame(myNormal, eyeVecNorm, texCoord);
  213. //      float3 normal2a = normalize(mul(2.0f * tex2D(normalMap, texCoord) - 1.0f, tangentFrame));
  214.         vec3 normal2a = normalize(tangentFrame * vec3(texture2D(normalMap, texCoord)).xyz * 2.0 - 1.0);
  215.        
  216.         texCoord = surfacePoint.xz * 0.1 + wind * timer * 0.00002;
  217.         tangentFrame = compute_tangent_frame(myNormal, eyeVecNorm, texCoord);
  218. //      float3 normal3a = normalize(mul(2.0f * tex2D(normalMap, texCoord) - 1.0f, tangentFrame));
  219.         vec3 normal3a = normalize(tangentFrame * vec3(texture2D(normalMap, texCoord)).xyz * 2.0 - 1.0);
  220.        
  221.         vec3 normal = normalize(normal0a * normalModifier.x + normal1a * normalModifier.y +
  222.                                   normal2a * normalModifier.z + normal3a * normalModifier.w);
  223.        
  224.         texCoord = gl_TexCoord[0].xy;
  225.         texCoord.x += sin(timer * 0.002 + 3.0 * abs(position.y)) * (refractionScale * min(depth2, 1.0));
  226.         vec3 refraction = texture2D(backBufferMap, texCoord).rgb;
  227.        
  228.         //if(mul(float4(tex2D(positionMap, texCoord).xyz, 1.0f), matViewInverse).y > level)
  229.     //      refraction = color2;
  230.        
  231.         if (vec4(matViewInverse * vec4(getPosition(texCoord).xyz, 1.0) ).y > level)
  232.          refraction = color2;          
  233.  
  234.         mat4x4 matTextureProj = matViewProj * matReflection;   //hier auch nicht sicher wegen Mul
  235.                
  236.         vec3 waterPosition = surfacePoint.xyz;
  237.         waterPosition.y -= (level - waterLevel);
  238. //      vec4 texCoordProj = mul(float4(waterPosition, 1.0f), matTextureProj);
  239.         vec4 texCoordProj = matTextureProj * vec4(waterPosition, 1.0);
  240.                
  241.        
  242.         vec4 dPos;
  243.         dPos.x = texCoordProj.x + displace * normal.x;
  244.         dPos.z = texCoordProj.z + displace * normal.z;
  245.         dPos.yw = texCoordProj.yw;
  246.         texCoordProj = dPos;       
  247.        
  248.         vec3 reflect = texture2DProj(reflectionMap, texCoordProj).xyz;
  249.        
  250.         float fresnel = fresnelTerm(normal, eyeVecNorm);
  251.        
  252.         vec3 depthN = vec3(depth * fadeSpeed);
  253.         vec3 waterCol = vec3(clamp(length(sunColor) / sunScale, 0.0, 1.0));
  254.         refraction = mix(mix(refraction, depthColour * waterCol, clamp(depthN / visibility, 0.0, 1.0)),
  255.                           bigDepthColour * waterCol, clamp(depth2 / extinction, 0.0, 1.0));
  256.  
  257.         float foam = 0.0;      
  258.  
  259.         texCoord = (surfacePoint.xz + eyeVecNorm.xz * 0.1) * 0.05 + timer * 0.00001 * wind + sin(timer * 0.001 + position.x) * 0.005;
  260.         vec2 texCoord2 = (surfacePoint.xz + eyeVecNorm.xz * 0.1) * 0.05 + timer * 0.00002 * wind + sin(timer * 0.001 + position.z) * 0.005;
  261.        
  262.         if(depth2 < foamExistence.x)
  263.             foam = (texture2D(foamMap, texCoord).r + texture2D(foamMap, texCoord2).r) * 0.5;
  264.         else if(depth2 < foamExistence.y)
  265.         {
  266.             foam = mix((texture2D(foamMap, texCoord).r + texture2D(foamMap, texCoord2).r) * 0.5, 0.0,
  267.                          (depth2 - foamExistence.x) / (foamExistence.y - foamExistence.x));
  268.            
  269.         }
  270.        
  271.         if(maxAmplitude - foamExistence.z > 0.0001)
  272.         {
  273.             foam += (texture2D(foamMap, texCoord) + texture2D(foamMap, texCoord2)) * 0.5 *
  274.                 clamp((level - (waterLevel + foamExistence.z)) / (maxAmplitude - foamExistence.z), 0.0, 1.0);
  275.         }
  276.  
  277.  
  278.         vec3 specular = vec3(0.0);
  279.  
  280.         vec3 mirrorEye = (2.0 * dot(eyeVecNorm, normal) * normal - eyeVecNorm);
  281.         float dotSpec = clamp(dot(mirrorEye.xyz, -lightDir) * 0.5 + 0.5, 0.0, 1.0);
  282.         specular = (1.0 - fresnel) * clamp(-lightDir.y, 0.0, 1.0) * ((pow(dotSpec, 512.0)) * (shininess * 1.8 + 0.2))* sunColor;
  283.         specular += specular * 25.0 * clamp(shininess - 0.05, 0.0, 1.0) * sunColor;    
  284.  
  285.         color = mix(refraction, reflect, fresnel);
  286.         color = clamp(color + max(specular, foam * sunColor), 0.0, 1.0);
  287.        
  288.         color = mix(refraction, color, clamp(depth * shoreHardness, 0.0, 1.0));
  289.     }
  290.    
  291.     if(position.y > level)
  292.         color = color2;
  293.  
  294.     gl_FragColor = vec4(color, 1.0);
  295. }
  296.  
  297.  
  298.  

Seite 1 von 1 Alle Zeiten sind UTC + 1 Stunde
Powered by phpBB® Forum Software © phpBB Group
https://www.phpbb.com/