diff options
| -rw-r--r-- | indra/llrender/llrendertarget.cpp | 2 | ||||
| -rw-r--r-- | indra/newview/app_settings/shaders/class1/deferred/deferredUtil.glsl | 15 | ||||
| -rw-r--r-- | indra/newview/app_settings/shaders/class1/environment/waterFogF.glsl | 42 | ||||
| -rw-r--r-- | indra/newview/app_settings/shaders/class1/environment/waterV.glsl | 1 | ||||
| -rw-r--r-- | indra/newview/app_settings/shaders/class2/environment/waterF.glsl | 82 | ||||
| -rw-r--r-- | indra/newview/lldrawpool.h | 3 | ||||
| -rw-r--r-- | indra/newview/lldrawpoolwater.cpp | 20 | ||||
| -rw-r--r-- | indra/newview/lldrawpoolwater.h | 2 | ||||
| -rw-r--r-- | indra/newview/llsurface.cpp | 7 | ||||
| -rw-r--r-- | indra/newview/llviewerdisplay.cpp | 4 | ||||
| -rw-r--r-- | indra/newview/llviewerregion.cpp | 3 | ||||
| -rw-r--r-- | indra/newview/llviewershadermgr.cpp | 2 | ||||
| -rw-r--r-- | indra/newview/pipeline.cpp | 3 | ||||
| -rw-r--r-- | indra/newview/pipeline.h | 2 | 
14 files changed, 141 insertions, 47 deletions
| diff --git a/indra/llrender/llrendertarget.cpp b/indra/llrender/llrendertarget.cpp index b0da054d76..7fcb130ac6 100644 --- a/indra/llrender/llrendertarget.cpp +++ b/indra/llrender/llrendertarget.cpp @@ -623,6 +623,8 @@ void LLRenderTarget::flush(bool fetch_depth)  void LLRenderTarget::copyContents(LLRenderTarget& source, S32 srcX0, S32 srcY0, S32 srcX1, S32 srcY1,  						S32 dstX0, S32 dstY0, S32 dstX1, S32 dstY1, U32 mask, U32 filter)  { +    LL_PROFILE_GPU_ZONE("LLRenderTarget::copyContents"); +  	GLboolean write_depth = mask & GL_DEPTH_BUFFER_BIT ? TRUE : FALSE;  	LLGLDepthTest depth(write_depth, write_depth); diff --git a/indra/newview/app_settings/shaders/class1/deferred/deferredUtil.glsl b/indra/newview/app_settings/shaders/class1/deferred/deferredUtil.glsl index bca4771c27..1c2034de69 100644 --- a/indra/newview/app_settings/shaders/class1/deferred/deferredUtil.glsl +++ b/indra/newview/app_settings/shaders/class1/deferred/deferredUtil.glsl @@ -310,16 +310,21 @@ vec4 getPosition(vec2 pos_screen)      return pos;  } +// get position given a normalized device coordinate +vec3 getPositionWithNDC(vec3 ndc) +{ +    vec4 pos = inv_proj * vec4(ndc, 1.0); +    return pos.xyz / pos.w; +} +  vec4 getPositionWithDepth(vec2 pos_screen, float depth)  {      vec2 sc = getScreenCoordinate(pos_screen); -    vec4 ndc = vec4(sc.x, sc.y, 2.0*depth-1.0, 1.0); -    vec4 pos = inv_proj * ndc; -    pos /= pos.w; -    pos.w = 1.0; -    return pos; +    vec3 ndc = vec3(sc.x, sc.y, 2.0*depth-1.0); +    return vec4(getPositionWithNDC(ndc), 1.0);  } +  vec2 getScreenXY(vec4 clip)  {      vec4 ndc = clip; diff --git a/indra/newview/app_settings/shaders/class1/environment/waterFogF.glsl b/indra/newview/app_settings/shaders/class1/environment/waterFogF.glsl index df640cba05..7dbba12502 100644 --- a/indra/newview/app_settings/shaders/class1/environment/waterFogF.glsl +++ b/indra/newview/app_settings/shaders/class1/environment/waterFogF.glsl @@ -32,6 +32,8 @@ uniform float waterFogKS;  vec3 getPositionEye(); +vec3 srgb_to_linear(vec3 col); +  vec4 applyWaterFogView(vec3 pos, vec4 color)  {      vec3 view = normalize(pos); @@ -71,6 +73,46 @@ vec4 applyWaterFogView(vec3 pos, vec4 color)      return color;  } +vec4 applyWaterFogViewLinear(vec3 pos, vec4 color) +{ +    vec3 view = normalize(pos); +    //normalize view vector +    float es = -(dot(view, waterPlane.xyz)); + +    //find intersection point with water plane and eye vector + +    //get eye depth +    float e0 = max(-waterPlane.w, 0.0); + +    vec3 int_v = waterPlane.w > 0.0 ? view * waterPlane.w / es : vec3(0.0, 0.0, 0.0); + +    //get object depth +    float depth = length(pos - int_v); + +    //get "thickness" of water +    float l = max(depth, 0.1); + +    float kd = waterFogDensity; +    float ks = waterFogKS; +    vec4 kc = waterFogColor; +    kc.rgb = srgb_to_linear(kc.rgb); // TODO -- pass in waterFogColor linear + +    float F = 0.98; + +    float t1 = -kd * pow(F, ks * e0); +    float t2 = kd + ks * es; +    float t3 = pow(F, t2 * l) - 1.0; + +    float L = min(t1 / t2 * t3, 1.0); + +    float D = pow(0.98, l * kd); + +    color.rgb = color.rgb * D + kc.rgb * L; +    color.a = kc.a + color.a; + +    return color; +} +  vec4 applyWaterFog(vec4 color)  {      //normalize view vector diff --git a/indra/newview/app_settings/shaders/class1/environment/waterV.glsl b/indra/newview/app_settings/shaders/class1/environment/waterV.glsl index e95f268681..a0a0e7dfca 100644 --- a/indra/newview/app_settings/shaders/class1/environment/waterV.glsl +++ b/indra/newview/app_settings/shaders/class1/environment/waterV.glsl @@ -46,6 +46,7 @@ out vec3 vary_position;  out vec3 vary_light_dir;  out vec3 vary_tangent;  out vec3 vary_normal; +out vec2 vary_fragcoord;  float wave(vec2 v, float t, float f, vec2 d, float s)   { diff --git a/indra/newview/app_settings/shaders/class2/environment/waterF.glsl b/indra/newview/app_settings/shaders/class2/environment/waterF.glsl index 2e7efa9b2a..59e7e64fbb 100644 --- a/indra/newview/app_settings/shaders/class2/environment/waterF.glsl +++ b/indra/newview/app_settings/shaders/class2/environment/waterF.glsl @@ -32,6 +32,7 @@ out vec4 frag_color;  vec3 scaleSoftClipFragLinear(vec3 l);  vec3 atmosFragLightingLinear(vec3 light, vec3 additive, vec3 atten);  void calcAtmosphericVarsLinear(vec3 inPositionEye, vec3 norm, vec3 light_dir, out vec3 sunlit, out vec3 amblit, out vec3 atten, out vec3 additive); +vec4 applyWaterFogViewLinear(vec3 pos, vec4 color);  // PBR interface  vec3 pbrIbl(vec3 diffuseColor, @@ -53,6 +54,8 @@ uniform sampler2D bumpMap;  uniform sampler2D bumpMap2;  uniform float     blend_factor;  uniform sampler2D screenTex; +uniform sampler2D screenDepth; +  uniform sampler2D refTex;  uniform float sunAngle; @@ -100,6 +103,8 @@ vec3 transform_normal(vec3 vNt)  void sampleReflectionProbes(inout vec3 ambenv, inout vec3 glossenv,      vec3 pos, vec3 norm, float glossiness); +vec3 getPositionWithNDC(vec3 ndc); +  void main()   {  	vec4 color; @@ -110,7 +115,7 @@ void main()      vec3 pos = vary_position.xyz; -	float dist = length(view.xy); +	float dist = length(pos.xyz);  	//normalize view vector  	vec3 viewVec = normalize(pos.xyz); @@ -121,7 +126,6 @@ void main()      vec3 wave2_a = texture2D(bumpMap, littleWave.xy).xyz*2.0-1.0;      vec3 wave3_a = texture2D(bumpMap, littleWave.zw).xyz*2.0-1.0; -      vec3 wave1_b = texture2D(bumpMap2, bigwave      ).xyz*2.0-1.0;      vec3 wave2_b = texture2D(bumpMap2, littleWave.xy).xyz*2.0-1.0;      vec3 wave3_b = texture2D(bumpMap2, littleWave.zw).xyz*2.0-1.0; @@ -142,11 +146,11 @@ void main()  	//get base fresnel components	 -	/*vec3 df = vec3( +	vec3 df = vec3(  					dot(viewVec, wave1),  					dot(viewVec, (wave2 + wave3) * 0.5),  					dot(viewVec, wave3) -				 ) * fresnelScale + fresnelOffset;*/ +				 ) * fresnelScale + fresnelOffset;  	vec2 distort = (refCoord.xy/refCoord.z) * 0.5 + 0.5; @@ -157,20 +161,33 @@ void main()  	vec2 dmod_scale = vec2(dmod*dmod, dmod); -    //float df1 = df.x + df.y + df.z; +    float df1 = df.x + df.y + df.z; -    vec4 refcol = vec4(0, 0, 0, 0); +    wavef = normalize(wavef + vary_normal); +    //wavef = vary_normal; -	//get specular component -	float spec = clamp(dot(vary_light_dir, (reflect(viewVec,wavef))),0.0,1.0); -		 -	//harden specular -	spec = pow(spec, 128.0); +    vec3 waver = reflect(viewVec, -wavef)*3;  	//figure out distortion vector (ripply)    -	//vec2 distort2 = distort+wavef.xy*refScale/max(dmod*df1, 1.0); -		 -	//vec4 fb = texture2D(screenTex, distort2); +    vec2 distort2 = distort + waver.xy * refScale / max(dmod * df1, 1.0); +    distort2 = clamp(distort2, vec2(0), vec2(0.99)); +  +    vec4 fb = texture2D(screenTex, distort2); +    float depth = texture2D(screenDepth, distort2).r; +    vec3 refPos = getPositionWithNDC(vec3(distort2*2.0-vec2(1.0), depth*2.0-1.0)); + +#if 1 +    if (refPos.z > pos.z-0.05) +    { +        //we sampled an above water sample, don't distort +        distort2 = distort; +        fb = texture2D(screenTex, distort2); +        depth = texture2D(screenDepth, distort2).r; +        refPos = getPositionWithNDC(vec3(distort2 * 2.0 - vec2(1.0), depth * 2.0 - 1.0)); +    } +#endif + +    fb = applyWaterFogViewLinear(refPos, fb);      vec3 sunlit;      vec3 amblit; @@ -186,48 +203,43 @@ void main()      float roughness = 0.08;      float gloss = 1.0 - roughness; -    vec3 baseColor = vec3(0); +    vec3 baseColor = vec3(0.25);      vec3 f0 = vec3(0.04);      vec3 diffuseColor = baseColor.rgb * (vec3(1.0) - f0);      diffuseColor *= gloss;      vec3 specularColor = mix(f0, baseColor.rgb, metallic); +    //vec3 refnorm = normalize(wavef + vary_normal); +    vec3 refnorm = wavef; -    vec3 refnorm = normalize(wavef + vary_normal); - +         vec3 irradiance = vec3(0);      vec3 radiance = vec3(0);      sampleReflectionProbes(irradiance, radiance, pos, refnorm, gloss); -     -    // fudge -- use refracted color as irradiance -    irradiance = srgb_to_linear(waterFogColor.rgb); +    radiance *= 0.5; +    irradiance = fb.rgb;      color.rgb = pbrIbl(diffuseColor, specularColor, radiance, irradiance, gloss, NdotV, 0.0); -    //vec4 fb = waterFogColor; -    //fb.rgb = srgb_to_linear(fb.rgb); -	 -    //refcol.rgb = vec3(0, 1, 0); - -	//mix with reflection -	//color.rgb = mix(fb.rgb, refcol.rgb, df1); -	 -    //color.rgb += spec * specular; - +          // fudge -- for punctual lighting, pretend water is metallic      diffuseColor = vec3(0);      specularColor = vec3(1);      roughness = 0.1; -    color.rgb += pbrPunctual(diffuseColor, specularColor, roughness, metallic, wavef, v, vary_light_dir); +    float scol = 1.0; // TODO -- incorporate shadow map + +    //color.rgb += pbrPunctual(diffuseColor, specularColor, roughness, metallic, wavef, v, vary_light_dir) * sunlit * 2.75 * scol;  	color.rgb = atmosFragLightingLinear(color.rgb, additive, atten);  	color.rgb = scaleSoftClipFragLinear(color.rgb);      color.a = 0.f; - -	//color.a = spec * sunAngle2; - -    frag_color = color; +    //color.rgb = fb.rgb; +    //color.rgb = vec3(depth*depth*depth*depth); +    //color.rgb = srgb_to_linear(normalize(refPos) * 0.5 + 0.5); +    //color.rgb = srgb_to_linear(normalize(pos) * 0.5 + 0.5); +    //color.rgb = srgb_to_linear(wavef * 0.5 + 0.5); +	frag_color = color;  #if defined(WATER_EDGE)      gl_FragDepth = 0.9999847f; diff --git a/indra/newview/lldrawpool.h b/indra/newview/lldrawpool.h index f7fc2d2061..0fcb2b2e58 100644 --- a/indra/newview/lldrawpool.h +++ b/indra/newview/lldrawpool.h @@ -48,6 +48,9 @@ public:  	enum  	{  		// Correspond to LLPipeline render type +        // Also controls render order, so passes that don't use alpha masking/blending should come before +        // other passes and occlusion culling should happen just before rendering alpha masked passes +        // in order to take advantage of hierarchical Z          // NOTE: Keep in sync with gPoolNames  		POOL_SIMPLE = 1,  		POOL_GROUND, diff --git a/indra/newview/lldrawpoolwater.cpp b/indra/newview/lldrawpoolwater.cpp index 23de00e3a4..0b9bca06db 100644 --- a/indra/newview/lldrawpoolwater.cpp +++ b/indra/newview/lldrawpoolwater.cpp @@ -122,6 +122,19 @@ S32 LLDrawPoolWater::getNumPostDeferredPasses()      return 1;  } +void LLDrawPoolWater::beginPostDeferredPass(S32 pass) +{ +    // copy framebuffer contents so far to a texture to be used for +    // reflections and refractions +    LLRenderTarget& src = gPipeline.mRT->screen; +    LLRenderTarget& dst = gPipeline.mWaterDis; +    dst.copyContents(src,  +        0, 0, src.getWidth(), src.getHeight(),  +        0, 0, dst.getWidth(), dst.getHeight(),  +        GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT,  +        GL_NEAREST); +} +  void LLDrawPoolWater::renderPostDeferred(S32 pass)   {      renderWater(); @@ -587,6 +600,8 @@ void LLDrawPoolWater::renderWater()          // bind reflection texture from RenderTarget          S32 screentex   = shader->enableTexture(LLShaderMgr::WATER_SCREENTEX); +        S32 screenDepth = shader->enableTexture(LLShaderMgr::WATER_SCREENDEPTH); +          F32 screenRes[] = {1.f / gGLViewport[2], 1.f / gGLViewport[3]};          S32 diffTex = shader->enableTexture(LLShaderMgr::DIFFUSE_MAP); @@ -613,6 +628,11 @@ void LLDrawPoolWater::renderWater()              gGL.getTexUnit(screentex)->bind(&gPipeline.mWaterDis);          } +        if (screenDepth > -1) +        { +            gGL.getTexUnit(screenDepth)->bind(&gPipeline.mWaterDis, true); +        } +          if (mShaderLevel == 1)          {              fog_color.mV[VW] = log(fog_density) / log(2); diff --git a/indra/newview/lldrawpoolwater.h b/indra/newview/lldrawpoolwater.h index e3073018c3..39f25541ef 100644 --- a/indra/newview/lldrawpoolwater.h +++ b/indra/newview/lldrawpoolwater.h @@ -63,7 +63,9 @@ public:  	static void restoreGL(); +          S32 getNumPostDeferredPasses() override; +    void beginPostDeferredPass(S32 pass) override;      void renderPostDeferred(S32 pass) override;      S32 getNumDeferredPasses() override;  	void renderDeferred(S32 pass = 0) override; diff --git a/indra/newview/llsurface.cpp b/indra/newview/llsurface.cpp index ea36e1d7be..1418499f8b 100644 --- a/indra/newview/llsurface.cpp +++ b/indra/newview/llsurface.cpp @@ -681,6 +681,13 @@ BOOL LLSurface::idleUpdate(F32 max_update_time)  			}  		}  	} + +    if (did_update) +    { +        // some patches changed, update region reflection probes +        mRegionp->updateReflectionProbes(); +    } +  	return did_update;  } diff --git a/indra/newview/llviewerdisplay.cpp b/indra/newview/llviewerdisplay.cpp index 65f1170eb4..118dbb833e 100644 --- a/indra/newview/llviewerdisplay.cpp +++ b/indra/newview/llviewerdisplay.cpp @@ -1007,7 +1007,7 @@ void display(BOOL rebuild, F32 zoom_factor, int subfield, BOOL for_snapshot)          if (LLPipeline::sRenderDeferred)          { -			gPipeline.renderDeferredLighting(&gPipeline.mRT->screen); +			gPipeline.renderDeferredLighting();  		}  		LLPipeline::sUnderWaterRender = FALSE; @@ -1146,7 +1146,7 @@ void display_cube_face()      gPipeline.mRT->deferredScreen.flush(); -    gPipeline.renderDeferredLighting(&gPipeline.mRT->screen); +    gPipeline.renderDeferredLighting();      LLPipeline::sUnderWaterRender = FALSE; diff --git a/indra/newview/llviewerregion.cpp b/indra/newview/llviewerregion.cpp index 19f8cc105e..628d0ecc6a 100644 --- a/indra/newview/llviewerregion.cpp +++ b/indra/newview/llviewerregion.cpp @@ -830,9 +830,6 @@ void LLViewerRegion::sendReliableMessage()  void LLViewerRegion::setWaterHeight(F32 water_level)  {  	mImpl->mLandp->setWaterHeight(water_level); - -    // reflection probes move with the water height -    updateReflectionProbes();  }  F32 LLViewerRegion::getWaterHeight() const diff --git a/indra/newview/llviewershadermgr.cpp b/indra/newview/llviewershadermgr.cpp index f2b01808a5..46abd83449 100644 --- a/indra/newview/llviewershadermgr.cpp +++ b/indra/newview/llviewershadermgr.cpp @@ -1021,6 +1021,7 @@ BOOL LLViewerShaderMgr::loadShadersWater()  		gWaterProgram.mName = "Water Shader";  		gWaterProgram.mFeatures.calculatesAtmospherics = true;          gWaterProgram.mFeatures.hasAtmospherics = true; +        gWaterProgram.mFeatures.hasWaterFog = true;  		gWaterProgram.mFeatures.hasGamma = true;  		gWaterProgram.mFeatures.hasTransport = true;          gWaterProgram.mFeatures.hasSrgb = true; @@ -1040,6 +1041,7 @@ BOOL LLViewerShaderMgr::loadShadersWater()  		gWaterEdgeProgram.mName = "Water Edge Shader";  		gWaterEdgeProgram.mFeatures.calculatesAtmospherics = true;          gWaterEdgeProgram.mFeatures.hasAtmospherics = true; +        gWaterEdgeProgram.mFeatures.hasWaterFog = true;  		gWaterEdgeProgram.mFeatures.hasGamma = true;  		gWaterEdgeProgram.mFeatures.hasTransport = true;          gWaterEdgeProgram.mFeatures.hasSrgb = true; diff --git a/indra/newview/pipeline.cpp b/indra/newview/pipeline.cpp index 0da2faae29..08c99266f8 100644 --- a/indra/newview/pipeline.cpp +++ b/indra/newview/pipeline.cpp @@ -8442,7 +8442,7 @@ LLVector4 pow4fsrgb(LLVector4 v, F32 f)  	return v;  } -void LLPipeline::renderDeferredLighting(LLRenderTarget *screen_target) +void LLPipeline::renderDeferredLighting()  {      LL_PROFILE_ZONE_SCOPED_CATEGORY_PIPELINE;      LL_PROFILE_GPU_ZONE("renderDeferredLighting"); @@ -8451,6 +8451,7 @@ void LLPipeline::renderDeferredLighting(LLRenderTarget *screen_target)          return;      } +    LLRenderTarget *screen_target         = &mRT->screen;      LLRenderTarget *deferred_target       = &mRT->deferredScreen;      LLRenderTarget *deferred_depth_target = &mRT->deferredDepth;      LLRenderTarget *deferred_light_target = &mRT->deferredLight; diff --git a/indra/newview/pipeline.h b/indra/newview/pipeline.h index 0b6b7d91ae..a31df9c16f 100644 --- a/indra/newview/pipeline.h +++ b/indra/newview/pipeline.h @@ -306,7 +306,7 @@ public: -	void renderDeferredLighting(LLRenderTarget* light_target); +	void renderDeferredLighting();  	void postDeferredGammaCorrect(LLRenderTarget* screen_target);  	void generateWaterReflection(LLCamera& camera); | 
