I’ve been quite content up until today to say “I can’t write Pixel Shaders” and “I don’t know what High Level Shader Language” is.
But I thought I’d have a crack at it. Turns out, it just looks like C whereas I expected it to look like assembly.
I read a bit from here;
http://blogs.microsoft.co.il/blogs/tamir/archive/2008/06/17/hlsl-pixel-shader-effects-tutorial.aspx
which is a great resource for starting and then I decided to give it a whirl.
Following this post and downloading the DirectX SDK led me to this masterpiece 😉
sampler2D input : register(s0); float factor : register(c0); float4 main(float2 uv : TEXCOORD) : COLOR { float4 Color = tex2D( input , uv.xy); Color.rgb = Color.rgb * abs(sin(uv.x * 3.14 * factor)) * abs(sin(uv.y * 3.14 * factor)); return(Color); }
lined up with this piece of C# brilliance 🙂
using System; using System.Windows.Media.Effects; using System.Windows; using System.Windows.Media; namespace ShaderEffects { public class MikeEffect : ShaderEffect { private static PixelShader _pixelShader = new PixelShader() { UriSource = new Uri(@"pack://application:,,,/ShaderEffects;component/MikeEffect/MikeEffect.ps") }; public MikeEffect() { PixelShader = _pixelShader; UpdateShaderValue(InputProperty); UpdateShaderValue(FactorProperty); } public static readonly DependencyProperty InputProperty = ShaderEffect.RegisterPixelShaderSamplerProperty("Input", typeof(MikeEffect), 0); public Brush Input { get { return (Brush)GetValue(InputProperty); } set { SetValue(InputProperty, value); } } public static readonly DependencyProperty FactorProperty = DependencyProperty.Register("Factor", typeof(double), typeof(MikeEffect), new UIPropertyMetadata(0.0, PixelShaderConstantCallback(0))); public double Factor { get { return (double)GetValue(FactorProperty); } set { SetValue(FactorProperty, value); } } } }
Naturally, I’m joking about the “brilliance” of it – I still don’t have a clue what I’m doing but I was very impressed with how easy it was and how fast it ran when I used it and bound the Factor property to a slider as in;
<Border Grid.ColumnSpan="2"> <Border.Effect> <local:MikeEffect Factor="{Binding ElementName=mikeSlider,Path=Value}" /> </Border.Effect>
and then;
<Slider Minimum="0" Maximum="20" Value="1" x:Name="mikeSlider" Width="192" />
I believe you can also do this with multi-input effects to transition from one piece of content to another – sounds pretty slick.