Sign in to follow this  

Lookup table using pixel shader

This topic is 3566 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Is it possible to write pixel shader which converts texture image using Lookup table? Pseudo-code is: unsigned char LUT[256]; for each pixel in image pixel = LUT[pixel]; Image is 8 bpp monochrome. Inside of pixel shader it looks like ARGB image with equal R,G and B components. Is it possible to write such shader, load LUT to it programmatically, and execute it?

Share this post


Link to post
Share on other sites
Here's an HLSL shader I wrote for 8-bit paletted images. The textures are stored in monochrome L8 format. The palette texture is 256x1 in size.


float4x4 WorldViewProj : WORLDVIEWPROJ;

Texture ColorTexture;

sampler ColorTextureSampler = sampler_state { texture = <ColorTexture> ; magfilter = NONE; minfilter = NONE; mipfilter = NONE; AddressU = wrap; AddressV = wrap; };

Texture PaletteTexture;

sampler PaletteTextureSampler = sampler_state { texture = <PaletteTexture> ; magfilter = NONE; minfilter = NONE; mipfilter = NONE; AddressU = wrap; AddressV = wrap; };

struct a2v
{
float4 Position : POSITION0;
float2 TexCoords : TEXCOORD0;
};

struct v2p
{
float4 Position : POSITION0;
float2 TexCoords : TEXCOORD0;
};

struct p2f
{
float4 Color : COLOR0;
};

void vs( in a2v IN, out v2p OUT )
{
OUT.Position = mul( IN.Position, WorldViewProj );
OUT.TexCoords = IN.TexCoords;
}

void ps( in v2p IN, out p2f OUT )
{
float4 TextureColor = tex2D( ColorTextureSampler, IN.TexCoords );
OUT.Color = tex1D( PaletteTextureSampler, TextureColor.r );
}

technique PaletteTechnique
{
pass p0
{
vertexshader = compile vs_1_1 vs();
pixelshader = compile ps_1_4 ps();
}
}

Share this post


Link to post
Share on other sites
One thing to watch out for doing a pixel shader based palettized texture like this is that texture filtering won't work correctly. You'll either need to live with texture filtering turned off (as in Scet's example) or implement the filtering manually yourself in the shader. You will also have to write custom code to generate your mipmap chain as standard mipmapping won't work correclty either.

The reason that filtering and mipmapping don't work with palettized textures is that the lerp of two palette indices doesn't generally equate to the index of the lerp of the two colours, unless your palette happens to be a linear ramp.

Share this post


Link to post
Share on other sites
Hello. I found interesting bug in this code: pixel with value 255 is always mapped to 0. All other pixel values are OK. After playing some time with shader text I found the version which works correctly:

void ps( in v2p IN, out p2f OUT )
{
float4 TextureColor = tex2D( ColorTextureSampler, IN.TexCoords );
float f = TextureColor.r;

if ( f == 1.0 )
{
f = 0.999;
}

OUT.Color = tex1D( PaletteTextureSampler, f );
}

It looks like avoiding 1.0 value solved the problem. Maybe there is more elegant solution? Thank you.

Share this post


Link to post
Share on other sites

This topic is 3566 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this