diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/fl_gleam.cxx | 136 |
1 files changed, 93 insertions, 43 deletions
diff --git a/src/fl_gleam.cxx b/src/fl_gleam.cxx index 087f4baf4..010b50a8a 100644 --- a/src/fl_gleam.cxx +++ b/src/fl_gleam.cxx @@ -1,9 +1,9 @@ // // "$Id$" // -// "Gleam" drawing routines for the Fast Light Tool Kit (FLTK). +// "Gleam" scheme box drawing routines for the Fast Light Tool Kit (FLTK). // -// Copyright 1998-2010 by Bill Spitzak and others. +// Copyright 1998-2018 by Bill Spitzak and others. // // This library is free software. Distribution and use rights are outlined in // the file "COPYING" which should have been included with this file. If this @@ -22,97 +22,148 @@ // // Modified 2012-2013 by Edmanuel Torres // This is a new version of the fl_gleam. The gradients are on the top -// an the bottom, the text area looks like in the classic FLTK way. +// and the bottom, the text area looks like in the classic FLTK way. // #include <FL/Fl.H> #include <FL/fl_draw.H> +/* + Implementation notes: + + All box types have 2 pixel wide borders, there is no distinction + of "thin" box types, hence Fl::box_dx() = Fl::box_dy() = 2, + Fl::box_dw() = Fl::box_dh() = 4 for all box types. + + All coordinates of function calls (x, y, w, h) describe the full + box size with borders, i.e. the original box coordinates. + The interior (background) of the box is drawn with reduced size. + This is adjusted only in function shade_rect_top_bottom(). + + Note: There is one pixel "leaking" out of the box border at each + corner which is currently not drawn in a full box redraw. +*/ + +// Standard box drawing code static void gleam_color(Fl_Color c) { Fl::set_box_color(c); } +/* Draw the shaded background of the box. + + This is called before the box frame (border) is drawn. + The interior of the box (shaded background) should be inset by two + pixels, hence width and height should be reduced by 4 (border size). + Since not all pixels of the border are drawn (border lines are shorter + by one or two pixels on each side) setting other offsets (+1, -2 instead + of +2, -4) would leak the box background color instead of the parent + widget's background color. + Note: the original implementation was maybe equivalent to using +1 and -2 + for offset and width, respectively instead of +2 and -4. It is not clear + whether this was intended or by accident. +*/ + static void shade_rect_top_bottom(int x, int y, int w, int h, Fl_Color fg1, Fl_Color fg2, float th) { - // Draws the shiny using maximum limits - int h_top = ((h/2) < (20) ? (h/2) : (20)); // min(h/2,20); - int h_bottom = ((h/6) < (15) ? (h/6) : (15)); // min(h/6,15); - int h_flat = h-(h_top+h_bottom); - int j = 0; - float step_size_top = h_top>1?(0.999f/(float)(h_top)):1; - float step_size_bottom = h_bottom>1?(0.999f/(float)(h_bottom)):1; - // This loop generates the gradient at the top of the widget - for (float k = 1; k >= 0; k -= step_size_top){ + // calculate background size w/o borders + x += 2; y += 2; w -= 4; h -= 4; + // draw the shiny background using maximum limits + int h_top = ((h/2) < (20) ? (h/2) : (20)); // min(h/2, 20); + int h_bottom = ((h/6) < (15) ? (h/6) : (15)); // min(h/6, 15); + int h_flat = h - h_top - h_bottom; + float step_size_top = h_top > 1 ? (0.999f/float(h_top)) : 1; + float step_size_bottom = h_bottom > 1 ? (0.999f/float(h_bottom)) : 1; + // draw the gradient at the top of the widget + float k = 1; + for (int i = 0; i < h_top; i++, k -= step_size_top) { gleam_color(fl_color_average(fl_color_average(fg1, fg2, th), fg1, k)); - fl_xyline(x, y+j, x+w); - j++; + fl_xyline(x, y+i, x+w-1); } + + // draw a "flat" rectangle in the middle area of the box gleam_color(fg1); - fl_rectf(x, y+h_top, w+1, h_flat); - // This loop generates the gradient at the bottom of the widget - for (float k = 1; k >= 0; k -= step_size_bottom){ - gleam_color(fl_color_average(fg1,fl_color_average(fg1, fg2, th), k)); - fl_xyline(x, y+j+h_flat-1, x+w); - j++; + fl_rectf(x, y + h_top, w, h_flat); + + // draw the gradient at the bottom of the widget + k = 1; + for (int i = 0; i < h_bottom; i++, k -= step_size_bottom) { + gleam_color(fl_color_average(fg1, fl_color_average(fg1, fg2, th), k)); + fl_xyline(x, y+h_top+h_flat+i, x+w-1); } } +// See shade_rect_top_bottom() static void shade_rect_top_bottom_up(int x, int y, int w, int h, Fl_Color bc, float th) { - shade_rect_top_bottom(x,y,w,h,bc,FL_WHITE,th); + shade_rect_top_bottom(x, y, w, h, bc, FL_WHITE, th); } +// See shade_rect_top_bottom() static void shade_rect_top_bottom_down(int x, int y, int w, int h, Fl_Color bc, float th) { - shade_rect_top_bottom(x,y,w,h,bc,FL_BLACK,th); + shade_rect_top_bottom(x, y, w, h, bc, FL_BLACK, th); } +// Draw box borders. Color arguments: +// - fg1: outer border line (left, right, top, bottom) +// - fg2: inner border line (left, right) +// - lc : inner border line (top, bottom) + static void frame_rect(int x, int y, int w, int h, Fl_Color fg1, Fl_Color fg2, Fl_Color lc) { + // outer border line: gleam_color(fg1); - fl_yxline(x, y+h-1, y+1); //Go from bottom to top left side - fl_yxline(x+w, y+h-1, y+1); //Go from bottom to top right side - fl_xyline(x+1, y, x+w-1); //Go across the top - fl_xyline(x+1, y+h, x+w-1); //Go across the bottom + fl_xyline(x+1, y, x+w-2); // top + fl_yxline(x+w-1, y+1, y+h-2); // right + fl_xyline(x+1, y+h-1, x+w-2); // bottom + fl_yxline(x, y+1, y+h-2); // left + + // inner border line (left, right): gleam_color(fg2); - fl_yxline(x+1, y+h-2, y+2); //Go from bottom to top left side - fl_yxline(x+w-1, y+h-2, y+2); //Go from bottom to top right side + fl_yxline(x+1, y+2, y+h-3); // left + fl_yxline(x+w-2, y+2, y+h-3); // right + + // inner border line (top, bottom): gleam_color(lc); - fl_xyline(x+2, y+1, x+w-3); //Go across the top - fl_xyline(x+2, y+h-1, x+w-3); //Go across the bottom + fl_xyline(x+2, y+1, x+w-3); // top + fl_xyline(x+2, y+h-2, x+w-3); // bottom } +// Draw box borders with different colors (up/down effect). + static void frame_rect_up(int x, int y, int w, int h, Fl_Color bc, Fl_Color lc, float th1, float th2) { - frame_rect(x,y,w,h,fl_color_average(fl_darker(bc), FL_BLACK, th1),fl_color_average(bc, FL_WHITE, th2),lc); + frame_rect(x, y, w, h, fl_color_average(fl_darker(bc), FL_BLACK, th1), fl_color_average(bc, FL_WHITE, th2), lc); } static void frame_rect_down(int x, int y, int w, int h, Fl_Color bc, Fl_Color lc, float th1, float th2) { - frame_rect(x,y,w,h,fl_color_average(bc, FL_WHITE, th1),fl_color_average(FL_BLACK, bc, th2),lc); + frame_rect(x,y,w,h,fl_color_average(bc, FL_WHITE, th1), fl_color_average(FL_BLACK, bc, th2), lc); } +// Draw the different box types. These are the actual box drawing functions. + static void up_frame(int x, int y, int w, int h, Fl_Color c) { - frame_rect_up(x, y, w-1, h-1, c, fl_color_average(c, FL_WHITE, .25f), .55f, .05f); + frame_rect_up(x, y, w, h, c, fl_color_average(c, FL_WHITE, .25f), .55f, .05f); } static void up_box(int x, int y, int w, int h, Fl_Color c) { - shade_rect_top_bottom_up(x+2, y+1, w-5, h-3, c, .15f); - frame_rect_up(x, y, w-1, h-1, c, fl_color_average(c, FL_WHITE, .05f), .15f, .05f); + shade_rect_top_bottom_up(x, y, w, h, c, .15f); + frame_rect_up(x, y, w, h, c, fl_color_average(c, FL_WHITE, .05f), .15f, .05f); } static void thin_up_box(int x, int y, int w, int h, Fl_Color c) { - shade_rect_top_bottom_up(x+2, y+1, w-5, h-3, c, .25f); - frame_rect_up(x, y, w-1, h-1, c, fl_color_average(c, FL_WHITE, .45f), .25f, .15f); + shade_rect_top_bottom_up(x, y, w, h, c, .25f); + frame_rect_up(x, y, w, h, c, fl_color_average(c, FL_WHITE, .45f), .25f, .15f); } static void down_frame(int x, int y, int w, int h, Fl_Color c) { - frame_rect_down(x, y, w-1, h-1, fl_darker(c), fl_darker(c), .25f, .95f); + frame_rect_down(x, y, w, h, fl_darker(c), fl_darker(c), .25f, .95f); } static void down_box(int x, int y, int w, int h, Fl_Color c) { - shade_rect_top_bottom_down(x+1, y+1, w-3, h-3, c, .65f); - frame_rect_down(x, y, w-1, h-1, c, fl_color_average(c, FL_BLACK, .05f), .05f, .95f); + shade_rect_top_bottom_down(x, y, w, h, c, .65f); + frame_rect_down(x, y, w, h, c, fl_color_average(c, FL_BLACK, .05f), .05f, .95f); } static void thin_down_box(int x, int y, int w, int h, Fl_Color c) { - shade_rect_top_bottom_down(x+1, y+1, w-3, h-3, c, .85f); - frame_rect_down(x, y, w-1, h-1, c, fl_color_average(c, FL_BLACK, .45f), .35f, 0.85f); + shade_rect_top_bottom_down(x, y, w, h, c, .85f); + frame_rect_down(x, y, w, h, c, fl_color_average(c, FL_BLACK, .45f), .35f, 0.85f); } extern void fl_internal_boxtype(Fl_Boxtype, Fl_Box_Draw_F*); @@ -133,4 +184,3 @@ Fl_Boxtype fl_define_FL_GLEAM_UP_BOX() { // // End of "$Id$". // - |
