Author: greg.ercolano
Date: 2009-09-06 19:25:51 -0700 (Sun, 06 Sep 2009)
New Revision: 6850
Log:
Solves STR#1739.

This allows icons to be defined for items in Fl_Browser.

In addition to the OP's patch:

    o Added doxygen docs

    o Fixed redraw handling of icons larger than the items

    o Some methods made const

    o Conformed indent to FLTK standards

See the STR for a test program that verifies the modifications.
Mods tested on linux,osx,windows.



Modified:
   branches/branch-1.3/FL/Fl_Browser.H
   branches/branch-1.3/src/Fl_Browser.cxx

Modified: branches/branch-1.3/FL/Fl_Browser.H
===================================================================
--- branches/branch-1.3/FL/Fl_Browser.H 2009-09-06 18:09:24 UTC (rev 6849)
+++ branches/branch-1.3/FL/Fl_Browser.H 2009-09-07 02:25:51 UTC (rev 6850)
@@ -36,6 +36,7 @@
 #define Fl_Browser_H
 
 #include "Fl_Browser_.H"
+#include "Fl_Image.H"
 
 struct FL_BLINE;
 
@@ -306,6 +307,11 @@
     else Fl_Browser_::display(find_line(line));
   }
 
+  // icon support
+  void icon(int line, Fl_Image* icon);
+  Fl_Image* icon(int line) const;
+  void remove_icon(int line);
+
   /** For back compatibility only. */
   void replace(int a, const char* b) { text(a, b); }
   void display(int line, int val=1);

Modified: branches/branch-1.3/src/Fl_Browser.cxx
===================================================================
--- branches/branch-1.3/src/Fl_Browser.cxx      2009-09-06 18:09:24 UTC (rev 
6849)
+++ branches/branch-1.3/src/Fl_Browser.cxx      2009-09-07 02:25:51 UTC (rev 
6850)
@@ -48,6 +48,7 @@
   FL_BLINE* prev;
   FL_BLINE* next;
   void* data;
+  Fl_Image* icon;
   short length;                // sizeof(txt)-1, may be longer than string
   char flags;          // selected, displayed
   char txt[1];         // start of allocated array
@@ -287,6 +288,7 @@
   t->flags = 0;
   strcpy(t->txt, newtext);
   t->data = d;
+  t->icon = 0;
   insert(line, t);
 }
 
@@ -321,6 +323,7 @@
     replacing(t, n);
     cache = n;
     n->data = t->data;
+    n->icon = t->icon;
     n->length = (short)l;
     n->flags = t->flags;
     n->prev = t->prev;
@@ -400,6 +403,9 @@
     }
   }
 
+  if (l->icon && (l->icon->h()+2)>hmax) {
+    hmax = l->icon->h() + 2;   // leave 2px above/below
+  }
   return hmax; // previous version returned hmax+2!
 }
 
@@ -412,7 +418,8 @@
        incr_height(), full_height()
 */
 int Fl_Browser::item_width(void *item) const {
-  char* str = ((FL_BLINE*)item)->txt;
+  FL_BLINE* l=(FL_BLINE*)item;
+  char* str = l->txt;
   const int* i = column_widths();
   int ww = 0;
 
@@ -457,6 +464,8 @@
   if (*str == format_char_ && str[1])
     str ++;
 
+  if (ww==0 && l->icon) ww = l->icon->w();
+
   fl_font(font, tsize);
   return ww + int(fl_width(str)) + 6;
 }
@@ -492,9 +501,11 @@
   \param[in] X,Y,W,H position and size.
 */
 void Fl_Browser::item_draw(void* item, int X, int Y, int W, int H) const {
-  char* str = ((FL_BLINE*)item)->txt;
+  FL_BLINE* l = (FL_BLINE*)item;
+  char* str = l->txt;
   const int* i = column_widths();
 
+  bool first = true;   // for icon
   while (W > 6) {      // do each tab-separated field
     int w1 = W;        // width for this field
     char* e = 0; // pointer to end of field or null if none
@@ -502,6 +513,15 @@
       e = strchr(str, column_char());
       if (e) {*e = 0; w1 = *i++;}
     }
+    // Icon drawing code
+    if (first) {
+      first = false;
+      if (l->icon) {
+       l->icon->draw(X+2,Y+1); // leave 2px left, 1px above
+       int iconw = l->icon->w()+2;
+       X += iconw; W -= iconw; w1 -= iconw;
+      }
+    }
     int tsize = textsize();
     Fl_Font font = textfont();
     Fl_Color lcol = textcolor();
@@ -521,7 +541,7 @@
       case 'c': talign = FL_ALIGN_CENTER; break;
       case 'r': talign = FL_ALIGN_RIGHT; break;
       case 'B': 
-       if (!(((FL_BLINE*)item)->flags & SELECTED)) {
+       if (!(l->flags & SELECTED)) {
          fl_color((Fl_Color)strtol(str, &str, 10));
          fl_rectf(X, Y, w1, H);
        } else strtol(str, &str, 10);
@@ -557,7 +577,7 @@
     }
   BREAK:
     fl_font(font, tsize);
-    if (((FL_BLINE*)item)->flags & SELECTED)
+    if (l->flags & SELECTED)
       lcol = fl_contrast(lcol, selection_color());
     if (!active_r()) lcol = fl_inactive(lcol);
     fl_color(lcol);
@@ -835,6 +855,64 @@
   swap(ai,bi);
 }
 
+/**
+  Set the image icon for \p line to the value \p icon.
+  Caller is responsible for keeping the icon allocated.
+  The \p line is automatically redrawn.
+  \param[in] line The line to be modified. If out of range, nothing is done.
+  \param[in] icon The image icon to be assigned to the \p line.
+                  If NULL, any previous icon is removed.
+*/
+void Fl_Browser::icon(int line, Fl_Image* icon) {
+  if (icon==0) {
+      remove_icon(line);
+  } else if (line>0 && line<=lines) {
+    // Update full_height_
+    FL_BLINE* l = find_line(line);
+    int dh = icon->h() - item_height(l) + 2;   // leave 2px above/below
+    l->icon = icon;                            // define icon AFTER 
item_height() check
+    if (dh>0) {
+      full_height_ += dh;
+      redraw();                                        // icon larger than 
item? must redraw widget
+    } else {
+      redraw_line(l);                          // icon same or smaller? can 
redraw just this line
+    }
+  }
+}
+
+/**
+  Returns the icon currently defined for \p line.
+  If no icon is defined, NULL is returned.
+  \param[in] line The line whose icon is returned.
+  \returns The icon defined, or NULL if none.
+*/
+Fl_Image* Fl_Browser::icon(int line) const {
+  FL_BLINE* l = find_line(line);
+  return(l ? l->icon : NULL);
+}
+
+/**
+  Removes the icon for \p line.
+  It's ok to remove an icon if none has been defined.
+  \param[in] line The line whose icon is to be removed.
+*/
+void Fl_Browser::remove_icon(int line) { 
+  if (line>0 && line<=lines) {
+    FL_BLINE* bl = find_line(line);
+    if (!bl->icon) return;
+    int dh = bl->icon->h()+2;  // leave 2px above/below
+    bl->icon=0; 
+    // update_full_height_
+    dh -= item_height(bl);
+    if (dh>0) {
+      full_height_ -= dh; 
+      redraw();                        // if icon was larger, must redraw 
window
+    } else {
+      redraw_line(bl);                 // if icon same size or smaller, can 
just redraw line
+    }
+  }
+}
+
 //
 // End of "$Id$".
 //

_______________________________________________
fltk-commit mailing list
[email protected]
http://lists.easysw.com/mailman/listinfo/fltk-commit

Reply via email to