I looking for either an existing shader, or a little help writing one… I would like to make a 2D flag wave effect. I’ve never written a shader before but after a few hours reading online I was able to come up with this test that looks like a flag waving in the wind if you use lots and lot of imagination.
FlagShader.fx
#if OPENGL
#define SV_POSITION POSITION
#define VS_SHADERMODEL vs_3_0
#define PS_SHADERMODEL ps_3_0
#else
#define VS_SHADERMODEL vs_4_0_level_9_1
#define PS_SHADERMODEL ps_4_0_level_9_1
#endif
float x;
float y;
Texture2D SpriteTexture;
sampler2D SpriteTextureSampler = sampler_state
{
Texture = <SpriteTexture>;
};
struct VertexShaderOutput
{
float4 Position : SV_POSITION;
float4 Color : COLOR0;
float2 TextureCoordinates : TEXCOORD0;
};
float4 MainPS(VertexShaderOutput input) : COLOR
{
float2 coord = input.TextureCoordinates;
if(coord.x > y - 0.5 && coord.x < y + 0.5) {
coord.y += x;
}
return tex2D(SpriteTextureSampler, coord) * input.Color;
}
technique SpriteDrawing
{
pass P0
{
PixelShader = compile PS_SHADERMODEL MainPS();
}
};
Game1.cs
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Graphics;
using System;
namespace shadertest {
public class Game1 : Game {
GraphicsDeviceManager graphics;
SpriteBatch spriteBatch;
Texture2D flag;
Effect flagShader;
float x, y;
public Game1() {
graphics = new GraphicsDeviceManager(this);
Content.RootDirectory = "Content";
}
protected override void LoadContent() {
spriteBatch = new SpriteBatch(GraphicsDevice);
flag = Content.Load<Texture2D>("united-states-of-america-flag-small");
flagShader = Content.Load<Effect>("FlagShader");
}
protected override void Update(GameTime gameTime) {
x = (float)(Math.Sin((Math.PI / 2) * gameTime.TotalGameTime.TotalSeconds));
y = (float)Math.Cos((Math.PI / 2) * gameTime.TotalGameTime.TotalSeconds);
base.Update(gameTime);
}
protected override void Draw(GameTime gameTime) {
GraphicsDevice.Clear(Color.CornflowerBlue);
spriteBatch.Begin(SpriteSortMode.Deferred, BlendState.AlphaBlend, effect: flagShader);
flagShader.Parameters["x"].SetValue(x);
flagShader.Parameters["y"].SetValue(y);
flagShader.CurrentTechnique.Passes[0].Apply();
spriteBatch.Draw(flag, new Vector2(125, 125), Color.White);
spriteBatch.End();
base.Draw(gameTime);
}
}
}
If anyone can give me a shove in the right direction, that would be greatly appreciated