Exemple #1
0
            protected override ITextureFilter CreateFilter(ITextureFilter input)
            {
                if (!Renderer.IsDx11Avail)
                {
                    Renderer.FallbackOccurred = true; // Warn user via player stats OSD
                    return(input);                    // DX11 is not available; fallback
                }

                Func <TextureSize, TextureSize> transform = s => new TextureSize(2 * s.Height, s.Width);

                var shaderPass1 = LoadShader11(GetShaderFileName(Neurons1));
                var shaderPass2 = LoadShader11(GetShaderFileName(Neurons2));
                var interleave  = CompileShader("Interleave.hlsl").Configure(transform: transform);

                var sourceSize = input.Size();

                if ((Renderer.TargetSize <= sourceSize).Any)
                {
                    return(input);
                }

                var yuv = input.ConvertToYuv();

                m_Filter1 = NNedi3Helpers.CreateFilter(shaderPass1, yuv, Neurons1, Structured);
                var resultY = interleave.ApplyTo(yuv, m_Filter1);

                m_Filter2 = NNedi3Helpers.CreateFilter(shaderPass2, resultY, Neurons2, Structured);
                var luma = interleave.ApplyTo(resultY, m_Filter2);

                var result = ChromaScaler.ScaleChroma(
                    new CompositionFilter(luma, yuv, targetSize: luma.Size(), chromaOffset: new Vector2(-0.25f, -0.25f)));

                return(result.Convolve(null, offset: new Vector2(0.5f, 0.5f)));
            }
            protected override ITextureFilter CreateFilter(ITextureFilter sourceFilter)
            {
                if (sourceFilter.Output.Size == Renderer.TargetSize)
                {
                    return(sourceFilter);
                }

                try
                {
                    m_DxvaHd = Renderer.CreateDxvaHd((Size)sourceFilter.Output.Size, TextureFormat.Unorm8,
                                                     Renderer.TargetSize, TextureFormat.Unorm8, Quality);
                }
                catch (DxvaHdException)
                {
                    // DXVA HD not available; fallback
                    Renderer.FallbackOccurred = true;
                    return(sourceFilter);
                }

                var input = YuvMode ? sourceFilter.ConvertToYuv() : sourceFilter;

                if (sourceFilter.Output.Format != TextureFormat.Unorm8)
                {
                    // Convert input to Unorm8 (and unforunately murdering quality at the same time)
                    var copy = CompileShader("Copy.hlsl").Configure(linearSampling: false, format: TextureFormat.Unorm8);
                    input = new ShaderFilter(copy, input);
                }

                var result = new DxvaHdResizeFilter(m_DxvaHd, input);

                return(YuvMode ? result.ConvertToRgb() : result);
            }
Exemple #3
0
            protected override ITextureFilter CreateFilter(ITextureFilter input)
            {
                if (!Renderer.IsDx11Avail)
                {
                    Renderer.FallbackOccurred = true; // Warn user via player stats OSD
                    return(input);                    // DX11 is not available; fallback
                }

                Func <TextureSize, TextureSize> transform = s => new TextureSize(2 * s.Height, s.Width);

                var shaderPass1 = GetShader(Neurons1);
                var shaderPass2 = GetShader(Neurons2);
                var interleave  = new Shader(FromFile("Interleave.hlsl"))
                {
                    Transform = transform
                };

                if ((Renderer.TargetSize <= input.Size()).Any)
                {
                    return(input);
                }

                var yuv         = input.ConvertToYuv();
                var composition = input.Decompose();

                var resultY = interleave.ApplyTo(composition.Luma, shaderPass1.ApplyTo(yuv));
                var luma    = interleave.ApplyTo(resultY, shaderPass2.ApplyTo(resultY));

                composition = luma.ComposeWith(composition.Chroma, chromaOffset: new Vector2(-0.25f, -0.25f));
                var result = ChromaScaler.ScaleChroma(composition);

                return(result.Convolve(null, offset: new Vector2(0.5f, 0.5f)));
            }
Exemple #4
0
            protected override ITextureFilter CreateFilter(ITextureFilter input)
            {
                if (Renderer.InputFormat.IsRgb())
                {
                    return(input);
                }

                int bits = Renderer.InputFormat.GetBitDepth();

                if (bits > MaxBitDepth)
                {
                    return(input);
                }

                float[] consts =
                {
                    (1 << bits) - 1,
                    Power
                };

                var Deband = new Shader(FromFile("Deband.hlsl", compilerOptions: PreserveDetail ? "PRESERVE_DETAIL=1" : ""))
                {
                    Arguments = consts,
                    PerTextureLinearSampling = new[] { true, false }
                };

                ITextureFilter yuv       = input.ConvertToYuv();
                var            inputsize = yuv.Size();

                var    deband = yuv;
                double factor = 2.0;// 0.5 * Math.Sqrt(5) + 0.5;

                int maxWidth = Math.Min(Math.Min(inputsize.Width, inputsize.Height) / 3, 256);
                int max      = (int)Math.Floor(Math.Log(maxWidth, factor));

                for (int i = max; i >= 0; i--)
                {
                    double scale = Math.Pow(factor, i);
                    var    size  = new TextureSize((int)Math.Round(inputsize.Width / scale), (int)Math.Round(inputsize.Height / scale));
                    if (size.Width == 0 || size.Height == 0)
                    {
                        continue;
                    }
                    if (i == 0)
                    {
                        size = inputsize;
                    }

                    Deband.Transform = s => size;
                    deband           = Deband.ApplyTo(yuv, deband);
                }

                return(deband.ConvertToRgb());
            }
Exemple #5
0
        public static ICompositionFilter Decompose(this ITextureFilter filter)
        {
            var result = filter as ICompositionFilter;

            if (result != null)
            {
                return(result);
            }

            var yuv = filter.ConvertToYuv();

            return(new CompositionFilter(yuv, yuv, fallback: filter));
        }
Exemple #6
0
            protected override ITextureFilter CreateFilter(ITextureFilter input)
            {
                if (!Renderer.IsOpenClAvail || Renderer.RenderQuality.PerformanceMode())
                {
                    Renderer.FallbackOccurred = true; // Warn user via player stats OSD
                    return(input);                    // OpenCL is not available, or UNORM8 textures used (not supported); fallback
                }

                Func <TextureSize, TextureSize> transformWidth  = s => new TextureSize(2 * s.Width, s.Height);
                Func <TextureSize, TextureSize> transformHeight = s => new TextureSize(s.Width, 2 * s.Height);

                var kernel  = CompileKernel();
                var shaderH = kernel.Configure(transform: transformWidth);
                var shaderV = kernel.Configure(transform: transformHeight);

                var neuronCount1 = s_NeuronCount[(int)Neurons1];
                var neuronCount2 = s_NeuronCount[(int)Neurons2];
                var weights1     = s_Weights[(int)Neurons1];
                var buffer1      = Renderer.CreateClBuffer(weights1);
                var buffer2      = buffer1;

                var differentWeights = neuronCount1 != neuronCount2;

                if (differentWeights)
                {
                    var weights2 = s_Weights[(int)Neurons2];
                    buffer2 = Renderer.CreateClBuffer(weights2);
                }

                var sourceSize = input.Output.Size;

                if (!IsUpscalingFrom(sourceSize))
                {
                    return(input);
                }

                var yuv = input.ConvertToYuv();

                var localWorkSizes = new[] { 8, 8 };
                var nnedi3H        = new NNedi3HKernelFilter(shaderH, buffer1, neuronCount1,
                                                             new TextureSize(yuv.Output.Size.Width, yuv.Output.Size.Height),
                                                             localWorkSizes, yuv);
                var nnedi3V = new NNedi3VKernelFilter(shaderV, buffer2, neuronCount2, differentWeights,
                                                      new TextureSize(nnedi3H.Output.Size.Width, nnedi3H.Output.Size.Height),
                                                      localWorkSizes, nnedi3H);

                var result = ChromaScaler.MakeChromaFilter(nnedi3V, yuv, chromaOffset: new Vector2(-0.25f, -0.25f));

                return(new ResizeFilter(result, result.Output.Size, new Vector2(0.5f, 0.5f),
                                        Renderer.LumaUpscaler, Renderer.LumaDownscaler));
            }
            protected override ITextureFilter CreateFilter(ITextureFilter input)
            {
                if (ProcessInYUV)
                {
                    input = input.ConvertToYuv();
                }

                var output = ShaderFileNames.Aggregate(input,
                                                       (current, filename) => current.Apply(GetShader(filename)));

                return(ProcessInYUV
                    ? output.ConvertToRgb()
                    : output);
            }
            protected override ITextureFilter CreateFilter(ITextureFilter input)
            {
                if (Renderer.InputFormat.IsRgb())
                {
                    return(input);
                }

                int bits = Renderer.InputFormat.GetBitDepth();

                if (bits > maxbitdepth)
                {
                    return(input);
                }

                float[] consts =
                {
                    (1 << bits) - 1,
                    power
                };

                var Deband = CompileShader("Deband.hlsl", macroDefinitions: !grain ? "SkipDithering=1" : "")
                             .Configure(arguments: consts, perTextureLinearSampling: new[] { true, false });

                ITextureFilter yuv       = input.ConvertToYuv();
                var            inputsize = yuv.Output.Size;

                var    deband = yuv;
                double factor = 2.0;// 0.5 * Math.Sqrt(5) + 0.5;

                int max = (int)Math.Floor(Math.Log(Math.Min(inputsize.Width, inputsize.Height) / 3.0, factor));

                for (int i = max; i >= 0; i--)
                {
                    double scale = Math.Pow(factor, i);
                    var    size  = new TextureSize((int)Math.Round(inputsize.Width / scale), (int)Math.Round(inputsize.Height / scale));
                    if (size.Width == 0 || size.Height == 0)
                    {
                        continue;
                    }
                    if (i == 0)
                    {
                        size = inputsize;
                    }

                    deband = Deband.Configure(transform: s => size).ApplyTo(yuv, deband);
                }

                return(deband.ConvertToRgb());
            }
Exemple #9
0
        protected override IFilter <ITextureOutput <ITexture2D> > Optimize()
        {
            ITextureFilter result = m_TrueSource.Resize(Output.Size);

            if (m_TrueSource.IsYuv() && !m_WantYuv)
            {
                result = result.ConvertToRgb();
            }

            if (!m_TrueSource.IsYuv() && m_WantYuv)
            {
                result = result.ConvertToYuv();
            }

            return(result.Compile());
        }
Exemple #10
0
            protected override ITextureFilter CreateFilter(ITextureFilter input)
            {
                if (ProcessInYUV)
                {
                    input = input.ConvertToYuv();
                }

                var output = ShaderFileNames.Aggregate(input,
                                                       (current, filename) =>
                                                       CompileShader(filename)
                                                       .Configure(format: GetTextureFormat())
                                                       .ApplyTo(current));

                return(ProcessInYUV
                    ? output.ConvertToRgb()
                    : output);
            }
Exemple #11
0
        private VideoSourceFilter(TrueSourceFilter trueSource, TextureSize outputSize, bool wantYuv)
            : base(Compile(new TextureDescription(outputSize), () =>
        {
            ITextureFilter source = trueSource;

            if (trueSource.IsYuv() && !wantYuv)
                source = source.ConvertToYuv();

            if (!trueSource.IsYuv() && wantYuv)
                source = source.ConvertToRgb();

            return(source.SetSize(outputSize));
        }))
        {
            m_TrueSource = trueSource;
            m_WantYuv    = wantYuv;

            if (m_WantYuv)
            {
                m_TrueSource.WantYuv = true;         // Prefer enabling (generates less overhead)
            }
            m_TrueSource.PrescaleSize = Output.Size; // Try change source size, always use latest value
        }
            protected override ITextureFilter CreateFilter(ITextureFilter input)
            {
                if (Renderer.InputFormat.IsRgb())
                    return input;

                int bits = Renderer.InputFormat.GetBitDepth();
                if (bits > MaxBitDepth) return input;

                float[] consts = {
                    (1 << bits) - 1,
                    Power
                };

                var Deband = CompileShader("Deband.hlsl", macroDefinitions: PreserveDetail ? "PRESERVE_DETAIL=1" : "")
                    .Configure(arguments: consts, perTextureLinearSampling: new[] { true, false });

                ITextureFilter yuv = input.ConvertToYuv();
                var inputsize = yuv.Size();

                var deband = yuv;
                double factor = 2.0;// 0.5 * Math.Sqrt(5) + 0.5;

                int maxWidth = Math.Min(Math.Min(inputsize.Width, inputsize.Height) / 3, 256);
                int max = (int)Math.Floor(Math.Log(maxWidth, factor));
                for (int i = max; i >= 0; i--)
                {
                    double scale = Math.Pow(factor, i);
                    var size = new TextureSize((int)Math.Round(inputsize.Width / scale), (int)Math.Round(inputsize.Height / scale));
                    if (size.Width == 0 || size.Height == 0) continue;
                    if (i == 0) size = inputsize;

                    deband = Deband.Configure(transform: s => size).ApplyTo(yuv, deband);
                }

                return deband.ConvertToRgb();
            }
Exemple #13
0
 ITextureFilter ICanUndo <RgbProcess> .Undo()
 {
     return(m_Fallback.ConvertToYuv());
 }
            protected override ITextureFilter CreateFilter(ITextureFilter input)
            {
                if (Renderer.InputFormat.IsRgb())
                {
                    return(input);
                }

                int bits = Renderer.InputFormat.GetBitDepth();

                if (bits > MaxBitDepth)
                {
                    return(input);
                }

                float[] consts =
                {
                    (1 << bits) - 1,
                    Power
                };

                var Downscale = new Shader(FromFile("Downscale.hlsl"))
                {
                    Transform = s => new TextureSize(s.Width / 2, s.Height / 2),
                    Arguments = consts
                };
                var DownscaleLuma = new Shader(FromFile("DownscaleLuma.hlsl"))
                {
                    SizeIndex = 1,
                    Arguments = consts
                };

                DownscaleLuma["iteration"] = 0;
                var Deband = new Shader(FromFile("Deband.hlsl", compilerOptions: PreserveDetail ? "PRESERVE_DETAIL=1" : ""))
                {
                    Arguments      = consts,
                    LinearSampling = false,
                    SizeIndex      = 1
                };

                var pyramid = new Stack <ITextureFilter>();

                var composition = input as ICompositionFilter;

                if (composition != null)
                {
                    pyramid.Push(composition.Luma);
                    pyramid.Push(DownscaleLuma.ApplyTo(composition.Luma, composition.Chroma));
                }
                else
                {
                    pyramid.Push(input.ConvertToYuv());
                }

                // Build gaussian pyramid
                while (pyramid.Peek().Size().Width >= 2 &&
                       pyramid.Peek().Size().Height >= 2)
                {
                    Downscale["iteration"] = pyramid.Count - 1;
                    pyramid.Push(Downscale.ApplyTo(pyramid.Peek()));
                }

                // Process pyramid
                ITextureFilter chroma = null;
                ITextureFilter result = pyramid.Peek();

                while (pyramid.Count > 1)
                {
                    if (composition != null && pyramid.Count == 2)
                    {
                        chroma        = result;
                        Deband.Format = TextureFormat.Unorm16_R;
                    }
                    result = Deband.ApplyTo(pyramid.Pop(), pyramid.Peek(), result);
                }

                if (composition != null)
                {
                    return(result.ComposeWith(chroma, copyParametersFrom: composition));
                }
                else
                {
                    return(result.ConvertToRgb());
                }
            }
Exemple #15
0
            protected override ITextureFilter CreateFilter(ITextureFilter input)
            {
                if (Renderer.InputFormat.IsRgb())
                {
                    return(input);
                }

                int bits = Renderer.InputFormat.GetBitDepth();

                if (bits > MaxBitDepth)
                {
                    return(input);
                }

                var composition = input as ICompositionFilter;
                var offset      = new SharpDX.Vector2(0.0f, 0.0f); // TODO: process chroma offset properly

                float[] consts =
                {
                    (1 << bits) - 1,
                    Power
                };

                var Downscale = new Shader(FromFile("Downscale.hlsl"))
                {
                    Transform = s => new TextureSize(s.Width / 2, s.Height / 2),
                    Arguments = consts
                };

                var DownscaleLuma = new Shader(FromFile("DownscaleLuma.hlsl"))
                {
                    SizeIndex = 1,
                    Arguments = consts
                };

                DownscaleLuma["iteration"] = 0;

                var Deband = new Shader(FromFile("Deband.hlsl", macroDefinitions: PreserveDetail ? "PRESERVE_DETAIL=1" : ""))
                {
                    Arguments      = consts,
                    LinearSampling = false,
                    SizeIndex      = 1
                };

                ITextureFilter deband, chroma = null, luma = null;
                var            pyramid = new Stack <ITextureFilter>();

                if (composition != null)
                {
                    deband = composition.Luma;
                    pyramid.Push(deband);
                    pyramid.Push(DownscaleLuma.ApplyTo(composition.Luma, composition.Chroma));
                }
                else
                {
                    deband = input.ConvertToYuv();
                    pyramid.Push(deband);
                }

                // Build gaussian pyramid
                while (pyramid.Peek().Size().Width >= 2 &&
                       pyramid.Peek().Size().Height >= 2)
                {
                    Downscale["iteration"] = pyramid.Count - 1;
                    pyramid.Push(Downscale.ApplyTo(pyramid.Peek()));
                }

                // Process pyramid
                var result = pyramid.Peek();

                while (pyramid.Count > 1)
                {
                    result = Deband.ApplyTo(pyramid.Pop(), pyramid.Peek(), result);
                    if (composition != null && pyramid.Count == 2)
                    {
                        chroma        = result;
                        Deband.Format = TextureFormat.Unorm16_R;
                    }
                }

                if (composition != null)
                {
                    luma = result;
                    return(new CompositionFilter(luma, chroma, composition.TargetSize, composition.ChromaOffset));
                }
                else
                {
                    return(result.ConvertToRgb());
                }
            }