示例#1
0
        private MyShadowMapData TSMShadowMap(ScriptableRenderContext context, MyRenderingData renderingData,
                                             ShadowSettings settings, int lightIndex)
        {
            var camera = renderingData.camera;

            if (settings.debug)
            {
                camera = GameObject.Find("Main Camera").GetComponent <Camera>();
            }
            var(view, projection) = GetShadowViewProjection(settings, renderingData, lightIndex);

            var cmd = CommandBufferPool.Get();

            cmd.Clear();
            var depthBuf = IdentifierPool.Get();

            cmd.GetTemporaryRT(depthBuf, settings.resolution, settings.resolution, 32, FilterMode.Point,
                               RenderTextureFormat.Depth);

            RenderTargetBinding binding = new RenderTargetBinding();

            binding.depthRenderTarget = depthBuf;
            cmd.SetRenderTarget(depthBuf);
            cmd.ClearRenderTarget(true, true, Color.black);

            MyShadowMapData shadowMapData = new MyShadowMapData()
            {
                shadowMapIdentifier = depthBuf,
                bias        = settings.bias,
                shadowType  = ShadowAlgorithms.TSM,
                world2Light = GL.GetGPUProjectionMatrix(projection, true) * view,
            };

            var trapezoidalTransfrom = TSMTransform(camera, shadowMapData.world2Light, settings);

            shadowMapData.postTransform = trapezoidalTransfrom;


            cmd.SetViewProjectionMatrices(view, projection);
            cmd.SetGlobalDepthBias(settings.depthBias, settings.normalBias);
            cmd.SetGlobalMatrix("_ShadowPostTransform", trapezoidalTransfrom);
            cmd.SetGlobalFloat("_SlopeDepthBias", -settings.normalBias);
            cmd.SetGlobalFloat("_DepthBias", -Mathf.Pow(2, settings.depthBias));

            context.ExecuteCommandBuffer(cmd);
            cmd.Clear();


            DrawShadowCasters(context, renderingData, shadowMapData, PassTSM);

            cmd.SetViewProjectionMatrices(renderingData.camera.worldToCameraMatrix,
                                          renderingData.camera.projectionMatrix);

            context.ExecuteCommandBuffer(cmd);
            cmd.Clear();

            CommandBufferPool.Release(cmd);

            return(shadowMapData);
        }
示例#2
0
        private MyShadowMapData StandardShadowMap(ScriptableRenderContext context, MyRenderingData renderingData,
                                                  ShadowSettings settings, int lightIndex)
        {
            var cmd = CommandBufferPool.Get();

            cmd.Clear();
            var depthBuf = IdentifierPool.Get();

            cmd.GetTemporaryRT(depthBuf, settings.resolution, settings.resolution, 32, FilterMode.Point,
                               RenderTextureFormat.Depth);

            RenderTargetBinding binding = new RenderTargetBinding();

            binding.depthRenderTarget = depthBuf;
            cmd.SetRenderTarget(depthBuf);
            cmd.ClearRenderTarget(true, true, Color.black);

            MyShadowMapData shadowMapData = new MyShadowMapData()
            {
                shadowMapIdentifier = depthBuf,
                bias       = settings.bias,
                shadowType = ShadowAlgorithms.Standard,
            };

            var(view, projection) = GetShadowViewProjection(settings, renderingData, lightIndex);

            cmd.SetViewProjectionMatrices(view, projection);

            shadowMapData.world2Light = projection * view;

            cmd.SetGlobalDepthBias(settings.depthBias, settings.normalBias);

            context.ExecuteCommandBuffer(cmd);
            cmd.Clear();

            DrawShadowCasters(context, renderingData, shadowMapData, PassSimple);

            cmd.SetViewProjectionMatrices(renderingData.camera.worldToCameraMatrix,
                                          renderingData.camera.projectionMatrix);

            context.ExecuteCommandBuffer(cmd);
            cmd.Clear();


            CommandBufferPool.Release(cmd);

            return(shadowMapData);
        }
        private void DrawShadowCasters(ScriptableRenderContext context, MyRenderingData renderingData,
                                       MyShadowMapData shadowMapData, int pass)
        {
            var cmd = CommandBufferPool.Get();

            cmd.SetGlobalMatrix("_LightViewProjection", shadowMapData.world2Light);
            //如果用cullResults 则范围太小 , 一些摄像机外的阴影没有绘制
            //而且现在shadowMap shader 是单独区分的
            foreach (var renderer in GameObject.FindObjectsOfType <UnityEngine.Renderer>())
            {
                cmd.DrawRenderer(renderer, shadowMapMat, 0, pass);
            }

            context.ExecuteCommandBuffer(cmd);
            cmd.Clear();
            CommandBufferPool.Release(cmd);
        }
        public override void Render(ScriptableRenderContext context, ref MyRenderingData renderingData)
        {
            if (shadowMapMat == null)
            {
                shadowMapMat = new Material(Shader.Find(shaderName));
            }

            for (var i = 0; i < renderingData.cullResults.visibleLights.Length; ++i)
            {
                var light = renderingData.cullResults.visibleLights[i];
                if (light.light.GetComponent <ShadowSettings>() is ShadowSettings shadowSettings)
                {
                    if (!shadowSettings.shadow)
                    {
                        continue;
                    }

                    MyShadowMapData data    = new MyShadowMapData();
                    var             hasData = false;
                    switch (shadowSettings.algorithms)
                    {
                    case ShadowAlgorithms.Standard:
                        data    = StandardShadowMap(context, renderingData, shadowSettings, i);
                        hasData = true;
                        break;

                    case ShadowAlgorithms.PSM:
                        data    = PSMShadowMap(context, renderingData, shadowSettings, i);
                        hasData = true;
                        break;

                    case ShadowAlgorithms.TSM:
                        data    = TSMShadowMap(context, renderingData, shadowSettings, i);
                        hasData = true;
                        break;
                    }

                    if (hasData)
                    {
                        renderingData.shadowMapData[light.light] = data;
                        lightMaps[light.light] = data;
                    }
                }
            }
        }
        private MyShadowMapData PSMShadowMap(ScriptableRenderContext context, MyRenderingData renderingData,
                                             ShadowSettings settings, int lightIndex)
        {
            var(view, projection, inverseZ) = PSMProjection(lightIndex, renderingData, settings);
            //Debug.Log(inverseZ);
            Vector4 p  = new Vector4(-0.46017f, 0.16764f, 0.01015f, 1.00f);
            var     p1 = projection * view * p;
            var     p2 = GL.GetGPUProjectionMatrix(projection, false) * Matrix4x4.Scale(new Vector3(1, 1, -1)) * view * p;

            MyShadowMapData shadowMapData = new MyShadowMapData()
            {
                shadowMapIdentifier = IdentifierPool.Get(),
                world2Light         = GL.GetGPUProjectionMatrix(projection, true) * Matrix4x4.Scale(new Vector3(1, 1, -1)) *
                                      view,
                bias             = settings.bias,
                shadowType       = ShadowAlgorithms.PSM,
                shadowParameters = new Vector4(inverseZ ? 1 : 0, 0, 0),
            };

            var cmd = CommandBufferPool.Get();

            cmd.GetTemporaryRT(shadowMapData.shadowMapIdentifier, settings.resolution, settings.resolution, 32,
                               FilterMode.Point, RenderTextureFormat.Depth);
            cmd.SetRenderTarget(shadowMapData.shadowMapIdentifier);
            cmd.SetGlobalVector("_ShadowParameters", shadowMapData.shadowParameters);
            cmd.SetGlobalDepthBias(1, 1);
            //cmd.SetViewProjectionMatrices(renderingData.camera.worldToCameraMatrix, renderingData.camera.projectionMatrix);
            cmd.ClearRenderTarget(true, true, Color.black);

            context.ExecuteCommandBuffer(cmd);
            cmd.Clear();

            DrawShadowCasters(context, renderingData, shadowMapData, PassPSM);

            CommandBufferPool.Release(cmd);

            return(shadowMapData);
        }