Dark side of the moon - Stealth Strategy Game Love - Online Procedural Adventiure Game Quel Solaar - Verse Rendering Engine Loq Airou 3D DSD modeling tool Co On - Verse Asset Scene Graph and Management Tool Nil Salentinn - Color Correction and editing tool Un wraped - A fully automatic UV unwraper Adri Om - Data visualization system Confuce - Procedural Character animator BubblEd - A simple toy that lets you build 3D models with spheres Verse - Realtime networking protocol for 3D graphic Technology files - Dowload tools and source code About - Eskil Steenberg and this site News and updates
Home | Enough | Betray | Seduce | Persuade | Clut | Reserch | Download

Introduction.

Today, various techniques are used to modify colors in digital images. These techniques are used to calibrate images between different mediums such as film stock, digital files and various display equipment such as projectors monitors and displays, or acquisition equipment such as CCDs, Telecine machines and film scanners. By applying corrections, the images can retain their look between the different mediums. But they also make it possible to simulate a specific input or process, such as a specific film stock or film process. Going even further one can create new "looks" where the colorist can design a custom artistic feel by modifying the colors of an image.

All colors are defined in a color space. Usually they are 3 dimentional but they don't have to be. There are multiple color spaces such as XYZ, LAB, HSV but the most common one is RGB. RGB is comprised of three colors: Red, Green And Blue.


Any color correction can be expressed as a Color LookUp Table or CLUT (some times written as "Color LUT"). This a 3D dimensional table where all colors are represented in color space. For each color in the color lookup table there is a destination color value that corresponds to what the particular color becomes when it is corrected using the CLUT. These tables are by nature 3-dimensional (Red Green and Blue) and therefore special file formats are used to store them. Hald CLUTs however have been converted to a 2D space and since tables store colors the CLUT can be be saved as a image, in any non destructive image format.


+ Concept:

A Hald CLUT is an image that has a specific color pattern on it. In this pattern all colors in the color space are represented. An application that uses the HALD CLUT image to color correct an image, takes a source image color and looks it up in the color pattern of the HALD CLUT, and the color it finds in that place is the corrected color that should replace the source color in the destination image. If the color doesn't exist in the CLUT, one can look up several colors and interpolate between them.

This simple procedure has some very elegant properties:

  • You can store any color correction.
  • Supported by multiple applications.
  • By use of interpolation to save size and precision.
  • Hardware supported.
  • You can have multiple sizes of CLUTs.
  • Uses file formats that are well known and documented.

  • An identity Hald CLUT - Click for full size
    + Creating Hald Cluts:

    In order to Create a CLUT you can either generate it using a custom program, or you can take an identity CLUT and color correct it in order to generate color a correction CLUT. An identity CLUT is a CLUT that doesn't affect the image it is applied to.

    The great thing about Hald CLUTs is that you can use any color correcting application to create them. For example if you start up an application like Photoshop and use it to color correct an image, you can take the same color correction settings and correct an identity CLUT. The correction then gets embedded on to that CLUT. The CLUT can then be used to correct any image.


    Original image

    Identity Hald CLUT

    Corrected Image

    Same correction applied to CLUT

    Original image corrected using corrected CLUT, Identical to corrected image

    Other image corrected using the same CLUT
    + Manipulating CLUTS:

    Since CLUTs are simple images you can use any image manipulation application to process them. For instance you can blend between two different CLUTs in order to create a color correction that averages two different looks.


    Identity Hald CLUT

    Image corrected using identity CLUT is unchanged

    Monocrome CLUT

    Monocrome CLUT applied to image

    CLUT created by averaging Monocrome and Identity CLUT

    CLUT applied to image creates a desaturated effect

    If you have several CLUTs that you would like to apply, you can merge CLUTs simply by correcting a CLUT with another CLUT. The new CLUT will then contain both corrections and any image corrected using this CLUT will get the same treatment as if corrected by the two original CLUTs.

    + Programming CLUTs:

    It is also very easy to program your own color corrections to create custom functions. Often it is very useful to programm a custom effect and then tweak the correction in a color correction application to get the special look you are after. Included in the files are varius example of programs that create custom color corrections. This sample code can easily be modified to create you own looks.

    + File Formats:

    Any Image format or bit depth can be used to store a CLUT. However, a Hald CLUT should never be stored using a destructive/lossy image format such as JPEG, since it can create artifacts. These artifacts may be very severe since the JPEG algorithm is not designed to compress CLUTs. However there are other efective ways to compress a Hald CLUT: Using a 4096 by 4096 identity CLUT, it will take up roughly 50 MB in a raw file format such as Targa. Compressed using ZIP, it will come down to 36 MB, but RAR compression will render a file size of only 124Kb. With the PNG file format you can also get drastic compression down to 131Kb. We strongly recommend the PNG file format if size is a factor. Other file formats that may be useful are RGBe and OpenEXR for High Dynamic Range (HDR) use.

    + Image Levels:

    A color lookup table can have different density. Most often you don't need to represent every possible color in a color space but instead you can interpolate the color without any visible artifacts. Therefore the Hald CLUT supports multiple different sizes. The larger the image the higher the precision, and the more memory is used. A CLUT can therfore be computed in a number of levels from 2 and up. Any implementation that supports Hald CLUTs must be able to handle at least up to level 16. To compute the size of a CLUT of a specific level, one takes the level to the power of three. All Hald CLUTs must always be square. In order to find out what level a CLUT has been encoded to, you simply take the size of the image and compute the cubic root. In order to compute how many colors for each component can be stored in the CLUT, you take the level to the power of two. Using level 4 (64 * 64 size) or 8 (512 * 512 size) is recommended using 8 bit per channel or lower images. Level 16 is recommended for advanced 8 corrections as well as 10, 12 and 16 bit images.

    + Encoding:

    The encoding is very simple. The encoding encodes to a continuous buffer as if the buffer was 3 dimensional, where width is red, height is green and depth is blue. The first pixel is in the upper left, closer corner starting at black and the last pixel is in the lower right deep corner. (this means that in terms of scanlines of a tv or monitor, the image is right, where as in a coordinate system, or OpenGL Texture it is upside down)

    Here is a typical example of an implementation on an identity CLUT generator.


    cube_size = level * level;
    image_size = level * level * level;
    data = p = malloc((sizeof *data) * image_size * image_size * 3);
    for(blue = 0; blue < cube_size; blue++)
    {
         for(green = 0; green < cube_size; green++)
         {
             for(red = 0; red < cube_size; red++)
             {
                 *p++ = (float)red / (float)(cube_size - 1);
                 *p++ = (float)green / (float)(cube_size - 1);
                 *p++ = (float)blue / (float)(cube_size - 1);
             }
         }
    }
    + Hardware Correction:

    Modern graphics hardware is very capable of computing this color correction in hardware. The CLUT is then encoded into a 3D texture that is applied to a image in a shader program. Using OpenGLs Shading Language the pixel shader would look like this:

    /* Fragment shader for color correction */
    uniform sampler2D image;
    uniform sampler3D clut;

    void main()
    {
         vec4 color;
             /* reading out a pixel */
         color = texture2D(image, gl_TexCoord[0].st);
             /* corecting the color using CLUT */
         color = texture3D(clut, color.rgb);
         gl_FragColor = color;
    }

    Make sure the the 3D texture is set to LINEAR interpolation. The image to be corrected should, if possible, use NEAREST interpolation since the algorithm will otherwise correct averages between pixels that may result in border artifacts. Note: some graphics cards claims to support 3D textures in order to be OpenGL 1.2 (or later) compatible, but does not in fact have 3D texturing in hardware. These cards will run sades using 3D textures in software resulting in a dramatic reduction in performance. The textures need to be set to to border clamp. And note remember that a clamped edge will not properly extrapolate the correction for HDR pixels out of range for the CLUT. Also remember to turn the CLUT upside down.

    + Download:

    I have some sample Hald CLUTs and some sample applications for creating identity CLUTs, and correcting images with them. The archive also contains source code and a gallery of Hald CLUTs. Find the files here.