Пример #1
0
        protected override void DrawCore(RenderContext context)
        {
            // Update the weight array if necessary
            if (weightsDirty || tapCount == 0)
            {
                weightsDirty = false;
                Vector2[] gaussianWeights = GaussianUtil.Calculate1D((int)Radius, 2f, true);
                tapCount   = gaussianWeights.Length;
                tapWeights = new float[tapCount];
                for (int i = 0; i < tapCount; i++)
                {
                    tapWeights[i] = gaussianWeights[i].Y;
                }
            }

            var originalTexture = GetSafeInput(0);
            var outputTexture   = GetSafeOutput(0);

            var tapNumber = 2 * tapCount - 1;

            directionalBlurEffect.Parameters.Set(DepthAwareDirectionalBlurKeys.Count, tapCount);
            directionalBlurEffect.Parameters.Set(DepthAwareDirectionalBlurKeys.TotalTap, tapNumber);
            directionalBlurEffect.Parameters.Set(DepthAwareDirectionalBlurUtilKeys.Radius, Radius);
            directionalBlurEffect.Parameters.Set(DepthAwareDirectionalBlurUtilKeys.TapWeights, tapWeights);

            // Blur in one direction
            var blurAngle = 0f;

            directionalBlurEffect.Parameters.Set(DepthAwareDirectionalBlurUtilKeys.Direction, new Vector2((float)Math.Cos(blurAngle), (float)Math.Sin(blurAngle)));

            var firstBlurTexture = NewScopedRenderTarget2D(originalTexture.Description);

            directionalBlurEffect.SetInput(0, originalTexture);
            directionalBlurEffect.SetOutput(firstBlurTexture);
            directionalBlurEffect.Draw(context, "GaussianBokehPass1_tap{0}_radius{1}", tapNumber, (int)Radius);

            // Second blur pass to ouput the final result
            blurAngle = MathUtil.PiOverTwo;
            directionalBlurEffect.Parameters.Set(DepthAwareDirectionalBlurUtilKeys.Direction, new Vector2((float)Math.Cos(blurAngle), (float)Math.Sin(blurAngle)));

            directionalBlurEffect.SetInput(0, firstBlurTexture);
            directionalBlurEffect.SetOutput(outputTexture);
            directionalBlurEffect.Draw(context, "GaussianBokehPass2_tap{0}_radius{1}", tapNumber, (int)Radius);
        }
Пример #2
0
        protected override void DrawCore(RenderContext context)
        {
            // Input texture
            var inputTexture = GetSafeInput(0);

            // Get a temporary texture for the intermediate pass
            // This texture will be allocated only in the scope of this draw and returned to the pool at the exit of this method
            var desc = inputTexture.Description;

            desc.MultiSampleLevel = MSAALevel.None; // TODO we should have a method to get a non-MSAA RT
            var outputTextureH = NewScopedRenderTarget2D(desc);

            var size = Radius * 2 + 1;

            if (offsetsWeights == null)
            {
                nameGaussianBlurH = string.Format("GaussianBlurH{0}x{0}", size);
                nameGaussianBlurV = string.Format("GaussianBlurV{0}x{0}", size);

                // TODO: cache if necessary
                offsetsWeights = GaussianUtil.Calculate1D(Radius, SigmaRatio);
            }

            // Update shared parameters
            Parameters.Set(GaussianBlurKeys.Count, offsetsWeights.Length);
            Parameters.Set(GaussianBlurShaderKeys.OffsetsWeights, offsetsWeights);

            // Horizontal pass
            blurH.SetInput(inputTexture);
            blurH.SetOutput(outputTextureH);
            blurH.Draw(context, nameGaussianBlurH);

            // Vertical pass
            blurV.SetInput(outputTextureH);
            blurV.SetOutput(GetSafeOutput(0));
            blurV.Draw(context, nameGaussianBlurV);
        }