/**
 * @file LocalFeatureColorWeijer.cpp
 * @brief implementation of the color features mentioned in van de Weijer, J. & Schmid, C. Applying Color Names to Image Description (2007)
 * @author Björn Fröhlich, Alexander Freytag
 * @date 01/28/2010
 */
#ifndef LOCALFEATURECOLORWEIJERINCLUDE
#define LOCALFEATURECOLORWEIJERINCLUDE

// nice-core includes
#include <core/basics/Config.h>
// 
#include <core/image/ImageT.h>
#include <core/image/MultiChannelImageT.h>
#include <core/imagedisplay/ImageDisplay.h>
// 
#include <core/vector/VectorT.h>
#include <core/vector/MatrixT.h>

// nice-vislearning includes
#include "LocalFeature.h"



namespace OBJREC {

/** interface to ColorSande implementation */
class LocalFeatureColorWeijer : public LocalFeature
{

  protected:
    //! enum for 11 main colors
    enum NAMEBLECOLORS
    {
      BLACK = 0,
      BLUE,
      BROWN,
      GREY,
      GREEN,
      ORANGE,
      PINK,
      PURPLE,
      RED,
      WHITE,
      YELLOW,
      LASTCOLOR
    };

    //! lookup table
    double hist[32][32][32][11];

    //! destination of the precomputed lookuptable
    std::string tfile;
    
  public:


    ///////////////////// ///////////////////// /////////////////////
    //                   CONSTRUCTORS / DESTRUCTORS
    ///////////////////// ///////////////////// /////////////////////   
    
    /** 
     * @brief default constructor 
     * @author Alexander Freytag
     * @date 06-02-2014 ( dd-mm-yyyy )
     */
    LocalFeatureColorWeijer ( );
    
    /** 
     * @brief recommended constructor, calls initFromConfig
     * @author Alexander Freytag
     * @date 06-02-2014 ( dd-mm-yyyy )
     */
    LocalFeatureColorWeijer ( const NICE::Config * _conf );

    /** 
     * @brief simple destructor
     */
    virtual ~LocalFeatureColorWeijer();
    
    /** 
     * @brief Jobs previously performed in the config-version of the constructor, read settings etc.
     * @author Alexander Freytag
     * @date 06-02-2014 ( dd-mm-yyyy )
     */    
    virtual void initFromConfig ( const NICE::Config * _conf, const std::string & _confSection = "LocalFeatureColorWeijer");

    ///////////////////// ///////////////////// /////////////////////
    //                      FEATURE STUFF
    ///////////////////// ///////////////////// //////////////////    
    
    /**
     * get the size of the descriptor
     * @return size of descriptor
     */
    int getDescSize () const;

    /**
     * get the colorWeijer features
     * @param img grayvalue input image
     * @param features features (output)
     * @param positions position of the features
     * @return
     */
    int getDescriptors ( const NICE::Image & img, NICE::VVector & positions, NICE::VVector & features ) const;

    /**
     * get the colorWeijer features
     * @param img color input image
     * @param features features (output)
     * @param positions given positions of the features
     * @return
     */
    int getDescriptors ( const NICE::ColorImage & img, NICE::VVector & positions, NICE::VVector & features ) const;

    /**
     * visualize the features
     * @param mark
     * @param positions
     * @param color
     */
    void visualizeFeatures ( NICE::Image & mark, const NICE::VVector & positions, size_t color ) const;

    /**
     * visualize the features
     * @param mark
     * @param positions
     * @param color
     */
    void visualizeFeatures ( NICE::ColorImage & mark, const NICE::VVector & features, const NICE::VVector & position ) const;

    /**
     * visualize the features
     * @param cimg
     */
    void visualizeFeatures ( const NICE::ColorImage & cimg ) const;

    /**
     * visualize the features
     * @param cimg
     * @param out
     */
    void visualizeFeatures ( const NICE::ColorImage & cimg, NICE::ColorImage & out ) const;

    /**
     * @brief load parameters (look up table for color correspondences) from external file (~3MB)
     */
    void restoreLUT();

    /**
     * finds a colorname in a given string
     * @param fn input string
     * @return number of the color
     */
    int findColor ( std::string &fn );

    /**
     * transform each pixel of an image
     * @param img input image
     * @param feats feature vector for each pixel
     */
    void getFeats ( const NICE::ColorImage &img, NICE::MultiChannelImageT<double> &feats );
    

    /**
     * transform each pixel of an image
     * @param img input image
     * @param feats feature value for each pixel
     * @param color which color name
     */
    void getFeats ( const NICE::ColorImage &img, NICE::ImageT<double> &feats, int color);

    ///////////////////// INTERFACE PERSISTENT /////////////////////
    // interface specific methods for store and restore
    ///////////////////// INTERFACE PERSISTENT /////////////////////   
    
    /** 
     * @brief Load object from external file (stream)
     * @author Alexander Freytag
     * @date 06-02-2014 ( dd-mmyyyy)
     */     
    virtual void restore ( std::istream & is, int format = 0 );
    
    /** 
     * @brief Save object to external file (stream)
     * @author Alexander Freytag
     * @date 06-02-2014 ( dd-mmyyyy)
     */       
    virtual void store( std::ostream & os, int format = 0 ) const;
    
    /** 
     * @brief Clear  object
     * @author Alexander Freytag
     * @date 06-02-2014 ( dd-mmyyyy)
     */    
    virtual void clear ();       
};


} // namespace

#endif
