diff mde/gui/widget/layout.d @ 123:d3b2cefd46c9

minSizeChange() allows run-time changes to widgets' minimal size (except for shrinking in a GridLayoutWidget). FloatingAreaWidget: correct resize limiters AStringContent: allows space and ignores modifier keys
author Diggory Hardy <diggory.hardy@gmail.com>
date Sun, 04 Jan 2009 17:35:15 +0000
parents 5b37d0400732
children a2ef6b549101
line wrap: on
line diff
--- a/mde/gui/widget/layout.d	Fri Jan 02 18:10:14 2009 +0000
+++ b/mde/gui/widget/layout.d	Sun Jan 04 17:35:15 2009 +0000
@@ -100,7 +100,6 @@
     this (IWidgetManager mgr, IParentWidget parent, widgetID id, WidgetData data, IContent content) {
 	cList = cast(IContentList) content;
 	WDCCheck (data, 2, 1, cList);
-        logger.trace ("Got data: {} and {}", data.ints, data.strings);
         cols = 1;
         rows = cList.list.length;
         subWidgets.length = rows;
@@ -116,7 +115,8 @@
             }
         } else {
             rows = cols = 1;
-            subWidgets = [mgr.makeWidget (this, data.strings[0], new ErrorContent ("<empty list>"))];
+            subWidgets = [mgr.makeWidget (this, data.strings[0],
+                                          new ErrorContent ("<empty list>",null)) ];
         }
     }
     
@@ -142,6 +142,7 @@
  *
  * The grid has no border but has spacing between widgets.
  *************************************************************************************************/
+// Note: mw, mh inherited from AWidget are not used; use col.mw, row.mw instead.
 abstract class GridWidget : AParentWidget
 {
     //BEGIN Creation & saving
@@ -192,8 +193,6 @@
 	}
 	initWidths = null;  // free
 	
-	mw = col.mw;
-	mh = row.mw;
 	w = col.w;
 	h = row.w;
 	
@@ -215,6 +214,14 @@
         return row.firstSizable >= 0;
     }
     
+    // mw, mh not used
+    override wdim minWidth () {
+        return col.mw;
+    }
+    override wdim minHeight () {
+        return row.mw;
+    }
+
     override void setWidth (wdim nw, int dir) {
         w = col.resizeWidth (nw, dir);
         // Note: setPosition must be called after!
@@ -232,6 +239,26 @@
         foreach (i,widget; subWidgets)
             widget.setPosition (x + col.pos[i % cols], y + row.pos[i / cols]);
     }
+    
+    override void minSizeChange (IChildWidget widg, wdim nmw, wdim nmh) {
+        size_t c = 0;
+        while (c < subWidgets.length) {
+            if (subWidgets[c] is widg)
+                goto gotCell;
+            ++c;
+        }
+        debug logger.error ("minSizeChange: widget is not my child (code error)");
+        return;
+        
+        gotCell:
+        if (col.newMinWidth (c % cols, nmw) ||
+            row.newMinWidth (c / cols, nmh)) {
+            parent.minSizeChange (this, col.mw, row.mw);
+            w = col.w;
+            h = row.w;
+        }
+        mgr.requestRedraw;
+    }
     //END Size & position
     
     
@@ -545,6 +572,7 @@
             diff = adjustCellSizes (diff, minWidth.length-1, -1);
         else
             diff = adjustCellSizes (diff, (dir == -1 ? lastSizable : firstSizable), dir);
+        genPositions;
         
         debug if (nw != w) {
             logger.trace ("resizeWidth on {} to {} failed, new width: {}, diff {}, firstSizable {}, columns {}",cast(void*)this, nw,w, diff, firstSizable, minWidth.length);
@@ -596,6 +624,29 @@
             diff = -adjustCellSizes (diff, resizeD, -1);
             adjustCellSizes (diff, resizeU, 1);
         }
+        genPositions;
+    }
+    
+    /** Called when one of the cells in column col now has minimal width nmw.
+     *
+     * Enlarges column minimal width if necessary; tries to keep total width the same but returns
+     * true if it cannot. */
+    bool newMinWidth (myDiff col, wdim nmw) {
+        bool r = false;
+        if (minWidth[col] < nmw) {
+            minWidth[col] = nmw;
+            wdim d = nmw - width[col];
+            if (d > 0 || (d < 0 && !sizable[col])) {
+                d = -adjustCellSizes (d, col, -1);
+                if (d != adjustCellSizes (d, minWidth.length-1, -1))
+                    r = true;	// if unable to keep overall size the same
+                genPositions;
+            }
+            mw = spacing * cast(wdim)(minWidth.length - 1);
+            foreach (imw; minWidth)
+                mw += imw;
+        }
+        return r;
     }
     
     /* Generate position infomation for each column and set w. */
@@ -666,7 +717,6 @@
         }
         // else no adjustment needed (diff == 0)
         
-        genPositions;
         return diff;
     }
     
@@ -687,11 +737,11 @@
      * Treat as READ ONLY outside this class! */
     wdim[]  width;              // only adjusted within the class
     wdim[]  pos;                /// ditto
+    wdim    spacing;            // used by genPositions (which cannot access the layout class's data)
+    wdim    w,mw;               // current & minimal widths
 protected:
     myDiff  resizeD,            // resizeCols works down from this index (<0 if not resizing)
             resizeU;            // and up from this index
-    wdim    spacing;            // used by genPositions (which cannot access the layout class's data)
-    wdim    w,mw;               // current & minimal widths
     /* indicies of the first/last resizable column (negative if none are resizable). */
     myDiff  firstSizable = -1, lastSizable = -1;  // set by calcFLSbl
     // Callbacks used to actually adjust a column's width: