dominant_color.h
Go to the documentation of this file.
00001 
00060 #ifndef DOMINANT_COLOR_H_
00061 #define DOMINANT_COLOR_H_
00062 
00063 #include <stdint.h>
00064 #include <math.h>
00065 #include <algorithm>
00066 #include <vector>
00067 
00068 namespace cob_3d_mapping
00069 {
00079   template<typename T>
00080     inline T
00081     min3 (const T& a, const T& b, const T& c)
00082     {
00083       return (a < b ? std::min < T > (a, c) : std::min < T > (b, c));
00084     }
00085 
00095   template<typename T>
00096     inline T
00097     max3 (const T& a, const T& b, const T& c)
00098     {
00099       return (a > b ? std::max < T > (a, c) : std::max < T > (b, c));
00100     }
00101 
00105   class DominantColor
00106   {
00107   public:
00108     DominantColor () :
00109         sum_colors_ (0), sum_r_ (0), sum_g_ (0), sum_b_ (0), hue_histogram_ (HIST_SIZE, 0)
00110     {
00111     }
00112 
00113     ~DominantColor ()
00114     {
00115     }
00116 
00125     void
00126     addColor (uint8_t r, uint8_t g, uint8_t b, int weight = 1);
00127 
00135     void
00136     getColor (uint8_t& r, uint8_t& g, uint8_t& b) const;
00137 
00145     int
00146     incrBin (int h);
00147 
00153     int
00154     getMaxBin () const;
00155 
00166     void
00167     rgb2hsv (uint8_t r, uint8_t g, uint8_t b, int& h, int& s, int& v) const;
00168 
00179     void
00180     hsv2rgb (int h, int s, int v, uint8_t& r, uint8_t& g, uint8_t& b) const;
00181 
00185     void
00186     reset ();
00187 
00188   private:
00192     enum
00193     {
00194       HIST_SIZE = 180 
00195     };
00196     int sum_colors_; 
00197     //int sum_sat_;
00198     //int sum_val_;
00199     int sum_r_, sum_g_, sum_b_; 
00200     std::vector<int> hue_histogram_; 
00201     //std::vector<int> sat_values_;
00202 
00203     static const float inv_bin_size = 1.0f / 360.0f * HIST_SIZE;
00204     //static const float bin_size = 360.0f / HIST_SIZE;
00205     //static const float bin_center = ((360.0f / HIST_SIZE) - 1.0f) * 0.5f;
00206   };
00207 }
00208 #endif /* DOMINANT_COLOR_H_ */
00209 
00210 /*template<typename T>
00211  inline T min3(const T& a, const T& b, const T& c) { return ( a < b ? std::min<T>(a,c) : std::min<T>(b,c) ); }
00212  template<typename T>
00213  inline T max3(const T& a, const T& b, const T& c) { return ( a > b ? std::max<T>(a,c) : std::max<T>(b,c) ); }
00214 
00215  class DominantColor
00216  {
00217  private:
00218  enum { HIST_SIZE = 180 }; // uint8_t limits hue to 0..255
00219 
00220  public:
00221  DominantColor() : sum_colors_(0), sum_sat_(0), sum_val_(0), hue_histogram_(HIST_SIZE,0), sat_values_(HIST_SIZE,0)
00222  { }
00223 
00224  ~DominantColor() { }
00225 
00226  void addColor(uint8_t r, uint8_t g, uint8_t b)
00227  {
00228  int h,s,v;
00229  rgb2hsv(r,g,b,h,s,v);
00230  int pos = incrBin(h);
00231  sat_values_[pos] += s;
00232  sum_sat_ += s;
00233  sum_val_ += v;
00234  ++sum_colors_;
00235  }
00236 
00237  inline void getColor(uint8_t& r, uint8_t& g, uint8_t& b) const
00238  {
00239  if(!sum_colors_) { r=0; g=0; b=0; return; }
00240  int pos = getMaxBin();
00241  hsv2rgb( round(pos*bin_size+bin_center), sat_values_[pos]/hue_histogram_[pos], sum_val_/sum_colors_, r,g,b );
00242  }
00243 
00244  inline int incrBin(int h)
00245  { int bin = h*inv_bin_size; hue_histogram_[bin] += 1; return bin; }
00246 
00247  inline int getMaxBin() const
00248  {
00249  int max_bin=0, max_size=0;
00250  for(int i=0;i<HIST_SIZE;++i)
00251  {
00252  if (hue_histogram_[i] >= max_size)
00253  {
00254  max_size = hue_histogram_[i];
00255  max_bin = i;
00256  }
00257  }
00258  //std::cout<<"max_(bin/size): "<<max_bin<<"/"<<max_size<<std::endl;
00259  return max_bin;
00260  }
00261 
00262  inline void rgb2hsv(uint8_t r, uint8_t g, uint8_t b, int& h, int& s, int& v) const
00263  {
00264  int rgb_min = min3(r,g,b);
00265  int rgb_max = max3(r,g,b);
00266  int delta = rgb_max - rgb_min;
00267  v = rgb_max;
00268  if (v == 0) { s = h = 0; return; }
00269  s = round(float(delta) / float(v) * 100.0f);
00270  v /= 2.55f;
00271  float h_tmp;
00272  if (s == 0) { h = 0; return; }
00273  if      ((int)r == rgb_max)   h_tmp =     (float(g - b)) / (float(delta));
00274  else if ((int)g == rgb_max)   h_tmp = 2.0f + (float(b - r)) / (float(delta));
00275  else                          h_tmp = 4.0f + (float(r - g)) / (float(delta));
00276 
00277  h = h_tmp * 60.0f;
00278  if(h<0) h+=360;
00279  }
00280 
00281  inline void hsv2rgb(int h, int s, int v, uint8_t& r, uint8_t& g, uint8_t& b) const
00282  {
00283  if (s == 0) { r = g = b = v*2.55f; return; }
00284 
00285  float hh = h / 60.0f; // sector 0..5
00286  int i = floor(hh);
00287  float f = hh - i;
00288  v = round(v*2.55f);
00289  int p = v * (100 - s) * 0.01f;
00290  int q = v * (100 - s * f) * 0.01f;
00291  int t = v * (100 - s * (1.0f - f)) * 0.01f;
00292 
00293  switch(i)
00294  {
00295  case 0:
00296  { r = v; g = t; b = p; break; }
00297  case 1:
00298  { r = q; g = v; b = p; break; }
00299  case 2:
00300  { r = p; g = v; b = t; break; }
00301  case 3:
00302  { r = p; g = q; b = v; break; }
00303  case 4:
00304  { r = t; g = p; b = v; break; }
00305  default:// case 5:
00306  { r = v; g = p; b = q; break; }
00307  }
00308  }
00309 
00310  private:
00311  int sum_colors_;
00312  int sum_sat_;
00313  int sum_val_;
00314  std::vector<int> hue_histogram_;
00315  std::vector<int> sat_values_;
00316 
00317  static const float inv_bin_size = 1.0f / 360.0f * HIST_SIZE;
00318  static const float bin_size = 360.0f / HIST_SIZE;
00319  static const float bin_center = ((360.0f / HIST_SIZE) - 1.0f) * 0.5f;
00320  };*/


cob_3d_mapping_common
Author(s): Georg Arbeiter
autogenerated on Wed Aug 26 2015 11:02:19