#ifndef _PALETTE_HPP_
#define _PALETTE_HPP_
/**
 * \file palette.h
 *
 * Defines the util::Palette class
 */

#include <config.h>
#include <string>
#include <util/gl.h>
#include <util/color.h>
#include <util/watchdog.h>

namespace util {
  /**
   * \class Palette palette.h <util/palette.h>
   * \brief A utility class for palettes.
   *
   * This class provides an interface for VLAB palette files
   * and their use for OpenGL.
   */
  class Palette : public FileObject {
  public:
    typedef util::Color<GLfloat> Color;

    /**
     * Construct the palette from a file
     *
     * \param filename File to read the palette from
     */
    Palette(std::string filename);

    /**
     * Construct an empty palette with only black colors.
     */
    Palette();

    /**
     * Reread the file describing the palette
     */
    void reread();

    /**
     * Get a color from the palette
     *
     * \param index Index of the color in the palette (between 0 and 255)
     * \param alpha Alpha value to use for this color (between 0 and 1)
     */
    Color getColor(unsigned int index, double alpha = 1) const;
    /**
     * Blend two colors in the palette together
     *
     * \param ind1 Index of the first color (between 0 and 255)
     * \param ind2 Index of the second color (between 0 and 255)
     * \param w Blending coefficient, from 0 to 1. The color is linearly 
     * interpolated from \p ind1 to \p ind2.
     * \parma alpha Alpha value to use for this color (between 0 and 1)
     */
    Color getColor(unsigned int ind1, unsigned int ind2, double w, double alpha = 1) const;
    /**
     * Get a color and make it the current OpenGL color
     * \param index Index of the color in the palette
     * \param alpha Alpha value fo use for this color
     */
    void  useColor(unsigned int index, double alpha = 1) const;
    /**
     * Blend two colors together and make the result the current OpenGL color
     * \param ind1 Index of the first color
     * \param ind2 Index of the second color
     * \param w Blending coefficient, from 0 to 1. The color is linearly 
     * interpolated from \p ind1 to \p ind2.
     * \param alpha Alpha value to use for this color.
     */
    void blend(unsigned int ind1, unsigned int ind2, double w, double alpha = 1) const;

    /**
     * Blend two colors together
     */
    static Color blend(const Color& c1, const Color& c2, double w);

    /**
     * Select a color from a range in a palette and make it the current OpenGL 
     * color.
     * \param start Index of the first color of the range
     * \param end Index of the last color of the range
     * \param w Position within the range, if the value correspond to a color 
     * in between two defined colors, they will be linearly interpolated.
     * \param alpha Alpha value to use for this color.
     */
    void select(unsigned int start, unsigned int end, double w, double alpha = 1) const;

    /**
     * Select a color from a range in a palette and returns it.
     * \param start Index of the first color of the range
     * \param end Index of the last color of the range
     * \param w Position within the range, if the value correspond to a color 
     * in between two defined colors, they will be linearly interpolated.
     * \param alpha Alpha value to use for this color.
     */
    Color selectColor(unsigned int start, unsigned int end, double w, double alpha = 1) const;


  private:
    Color colors[256];
  };
}

#endif

