tags:

views:

51

answers:

4
#include <Fl/Enumerations.H>
class Color
{
    public:
        static Color amber () {return fl_rgb_color (255, 204, 0);}
        static Color lighter_gray () {return fl_rgb_color (40, 40, 40); }
        static Color light_gray () {return fl_rgb_color (179, 179, 179);}
        static Color gray () {return fl_rgb_color (100, 100, 100);}
        static Color light_blue () {return fl_rgb_color (107, 107, 255);}
        static Color white () {return FL_WHITE;}
        static Color off_white() { return fl_rgb_color(225, 225, 225); }
        static Color cream() { return fl_rgb_color(204, 236, 255); }
        static Color black () {return FL_BLACK;}
        static Color red () {return FL_RED;}
        static Color green () {return FL_GREEN;}
        static Color dark_green () {return fl_rgb_color (0, 169, 45);}
        static Color blue () {return FL_BLUE;}
        static Color background () {return FL_BACKGROUND_COLOR;}

        Color (const Fl_Color& c = Color::black ()) : fl_color_ (c) {}
        operator Fl_Color () const {return fl_color_;}
        void make_current () const;

    private:
        Fl_Color fl_color_;
};

and this is an excerpt of the important parts from Fl/Enumerations.h

enum Fl_Color { // standard colors
  // These are used as default colors in widgets and altered as necessary
  FL_FOREGROUND_COLOR   = 0,
  FL_BACKGROUND2_COLOR  = 7,
  FL_INACTIVE_COLOR = 8,
  FL_SELECTION_COLOR    = 15,

  // boxtypes generally limit themselves to these colors so
  // the whole ramp is not allocated:
  FL_GRAY0   = 32, // 'A'
  FL_DARK3   = 39, // 'H'
  FL_DARK2   = 45,   // 'N'
  FL_DARK1   = 47, // 'P'
  FL_BACKGROUND_COLOR   = 49, // 'R' default background color
  FL_LIGHT1  = 50, // 'S'
  FL_LIGHT2  = 52, // 'U'
  FL_LIGHT3  = 54, // 'W'

  // FLTK provides a 5x8x5 color cube that is used with colormap visuals
  FL_BLACK   = 56,
  FL_RED     = 88,
  FL_GREEN   = 63,
  FL_YELLOW  = 95,
  FL_BLUE    = 216,
  FL_MAGENTA     = 248,
  FL_CYAN    = 223,
  FL_DARK_RED    = 72,

  FL_DARK_GREEN  = 60,
  FL_DARK_YELLOW    = 76,
  FL_DARK_BLUE   = 136,
  FL_DARK_MAGENTA   = 152,
  FL_DARK_CYAN   = 140,

  FL_WHITE   = 255
};

#define FL_FREE_COLOR    (Fl_Color)16
#define FL_NUM_FREE_COLOR   16
#define FL_GRAY_RAMP     (Fl_Color)32
#define FL_NUM_GRAY  24
#define FL_GRAY   FL_BACKGROUND_COLOR
#define FL_COLOR_CUBE    (Fl_Color)56
#define FL_NUM_RED   5
#define FL_NUM_GREEN     8
#define FL_NUM_BLUE  5

FL_EXPORT Fl_Color fl_inactive(Fl_Color c);
FL_EXPORT Fl_Color fl_contrast(Fl_Color fg, Fl_Color bg);
FL_EXPORT Fl_Color fl_color_average(Fl_Color c1, Fl_Color c2, float weight);
inline Fl_Color fl_lighter(Fl_Color c) { return fl_color_average(c, FL_WHITE, .67f); }
inline Fl_Color fl_darker(Fl_Color c) { return fl_color_average(c, FL_BLACK, .67f); }
inline Fl_Color fl_rgb_color(uchar r, uchar g, uchar b) {

  if (!r && !g && !b) return FL_BLACK;
  else return (Fl_Color)(((((r << 8) | g) << 8) | b) << 8);
}
inline Fl_Color fl_rgb_color(uchar g) {
  if (!g) return FL_BLACK;
  else return (Fl_Color)(((((g << 8) | g) << 8) | g) << 8);
}
inline Fl_Color fl_gray_ramp(int i) {return (Fl_Color)(i+FL_GRAY_RAMP);}
inline Fl_Color fl_color_cube(int r, int g, int b) {
  return (Fl_Color)((b*FL_NUM_RED + r) * FL_NUM_GREEN + g + FL_COLOR_CUBE);}

I have been unable to wrap my mind about what is going on in the following class with regard to the static class definitions returning FL_COLOR enumerations. I can't see how Fl_Color could have any knowledge of the Color class and how the compiler could have any idea of how to convert an Fl_Color into a Color. I do realize that Color has an implicit conversion to Fl_Color, but I didn't think that conversion went both ways. How does this work? Does the compiler just call the constructor and pass in the return value as the first parameter?

A: 

implicitly runs the Color constructor on the F1_color before returning

A: 

The constructor for Color takes an Fl_Color parameter so the compiler will use it implicitly to convert Fl_Color to Color when necessary. This is normal behaviour for C++ constructors that take a single parameter and are not marked with the explicit keyword.

Carlos A. Ibarra
+3  A: 

The static methods returning a Color all return the result of a call to fl_rgb_color.

fl_rgb_color returns a Fl_Color and Color has a single parameter constructor which is not marked explicit and takes a reference to a const Fl_Color so this is a valid implict conversion.

The return value of fl_rgb_color is a temporary but because Color takes the Fl_Color parameter by a const reference it is legal to bind the temporary to the constructor parameter. Its lifetime lasts until the construction of the Color object (itself also a temporary for a return value) completes.

Charles Bailey
A: 

Fl_Color is implicitly convertible to Color, because Color has non-explicit constructor that takes Fl_Color as a parameter.

avakar