如何对整个 WPF 应用程序进行灰度
控件名:GrayscaleEffect
作 者:WPFDevelopersOrg -
原文链接: https://github.com/WPFDevelopersOrg/WPFDevelopers 简易源码
框架使用.NET40
;
Visual Studio 2019
;
如果要实现灰度第一反是使用主题色更改,但是使用主题色需要重新配色比较慢,需 Effect
类派生以实现自定义位图效果,将使用ShaderEffect进行更改灰度,从 ShaderEffect
类派生,以基于单个像素着色器实现自定义效果。
必须安装 .NET Framework 3.5 sp1
或更高版本才能正常工作。
DirectX SDK
才能编译像素着色器效果。HLSL
) 字节代码加载 。Brush
依赖属性。 使用其中 RegisterPixelShaderSamplerProperty 一个重载将这些输入与 HLSL
字节码中引用的寄存器号相关联。DirectX SDK
安装完成。\Utilities\bin\x86
执行以下命令,就会输出.ps
文件。Install-Package WPFDevelopers
1.0.9.5-previewInstall-Package WPFDevelopers..Minimal
1.0.0.1-preview1 ) GrayscaleEffect.hlsl
代码如下:
sampler2D implicitInput : register(s0); float factor : register(c0); /// <summary>The brightness offset.</summary> /// <minValue>-1</minValue> /// <maxValue>1</maxValue> /// <defaultValue>0</defaultValue> float brightness : register(c1); float4 main(float2 uv : TEXCOORD) : COLOR { float4 pixelColor = tex2D(implicitInput, uv); pixelColor.rgb /= pixelColor.a; // Apply brightness. pixelColor.rgb += brightness; // Return final pixel color. pixelColor.rgb *= pixelColor.a; float4 color = pixelColor; float pr = .299; float pg = .587; float pb = .114; float gray = sqrt(color.r * color.r * pr + color.g * color.g * pg + color.b * color.b * pb); float4 result; result.r = (color.r - gray) * factor + gray; result.g = (color.g - gray) * factor + gray; result.b = (color.b - gray) * factor + gray; result.a = color.a; return result; }
2 )执行命令
代码如下:
fxc /T ps_2_0 /Fo E:\GrayscaleEffect\GrayscaleEffect.ps E:\GrayscaleEffect\GrayscaleEffect.hlsl
3 )得到以下文件
4 )新建GrayscaleEffect.cs
代码如下:
using System; using System.Windows; using System.Windows.Media; using System.Windows.Media.Effects; namespace WPFDevelopers { public class GrayscaleEffect : ShaderEffect { /// <summary> /// Identifies the Input property. /// </summary> public static readonly DependencyProperty InputProperty = RegisterPixelShaderSamplerProperty("Input", typeof(GrayscaleEffect), 0); /// <summary> /// Identifies the Factor property. /// </summary> public static readonly DependencyProperty FactorProperty = DependencyProperty.Register("Factor", typeof(double), typeof(GrayscaleEffect), new UIPropertyMetadata(0D, PixelShaderConstantCallback(0))); /// <summary> /// Identifies the Brightness property. /// </summary> public static readonly DependencyProperty BrightnessProperty = DependencyProperty.Register("Brightness", typeof(double), typeof(GrayscaleEffect), new UIPropertyMetadata(0D, PixelShaderConstantCallback(1))); /// <summary> /// Creates a new instance of the <see cref="GrayscaleEffect"/> class. /// </summary> public GrayscaleEffect() { var pixelShader = new PixelShader(); pixelShader.UriSource = new Uri("WPFDevelopers;component/Effects/GrayscaleEffect.ps", UriKind.Relative); PixelShader = pixelShader; UpdateShaderValue(InputProperty); UpdateShaderValue(FactorProperty); UpdateShaderValue(BrightnessProperty); } /// <summary> /// Gets or sets the <see cref="Brush"/> used as input for the shader. /// </summary> public Brush Input { get => ((Brush)(GetValue(InputProperty))); set => SetValue(InputProperty, value); } /// <summary> /// Gets or sets the factor used in the shader. /// </summary> public double Factor { get => ((double)(GetValue(FactorProperty))); set => SetValue(FactorProperty, value); } /// <summary> /// Gets or sets the brightness of the effect. /// </summary> public double Brightness { get => ((double)(GetValue(BrightnessProperty))); set => SetValue(BrightnessProperty, value); } } }
5 )使用Window.Xaml
代码如下,默认原色:
<wpfdev:Window x:Class="WPFDevelopers.Samples.MainWindow" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" xmlns:wpfdev="https://github.com/WPFDevelopersOrg/WPFDevelopers"> <wpfdev:Window.Effect> <wpfdev:GrayscaleEffect x:Name="grayscaleEffect" Factor="1"/> </wpfdev:Window.Effect> <TextBlock Text="开启程序灰度" FOntSize="20" Margin="0,20,0,0"/> <ToggleButton Margin="10" Name="tbGrayscale" Checked="tbGrayscale_Checked" Unchecked="tbGrayscale_Unchecked" HorizOntallignment="Left"/>
6 )使用Window.Xaml.cs
灰度代码如下:
private void tbGrayscale_Checked(object sender, RoutedEventArgs e) { Create(0); } void Create(double to) { var sineEase = new SineEase() { EasingMode = EasingMode.EaseOut }; var doubleAnimation = new DoubleAnimation { To = to, Duration = TimeSpan.FromMilliseconds(1000), EasingFunction = sineEase }; grayscaleEffect.BeginAnimation(GrayscaleEffect.FactorProperty, doubleAnimation); } private void tbGrayscale_Unchecked(object sender, RoutedEventArgs e) { Create(1); }
![]() | 1 Soar360 2022-12-28 15:04:28 +08:00 支持支持 |