changeset 1077:34f1d6f5f1c3

Added function dw_box_pack_at_index() on Windows, Mac and OS/2. And an example usage in dwtest. Only tested on Windows... will be testing on OS/2 and Mac shortly... then implementing the GTK versions of the function after that.
author bsmith@81767d24-ef19-dc11-ae90-00e081727c95
date Tue, 28 Jun 2011 04:41:43 +0000
parents dbaf1b11c301
children 6eadfe0007b4
files dw.def dw.h dwtest.c dww.def mac/dw.m os2/dw.c win/dw.c
diffstat 7 files changed, 366 insertions(+), 3 deletions(-) [+]
line wrap: on
line diff
--- a/dw.def	Sun Jun 26 02:36:23 2011 +0000
+++ b/dw.def	Tue Jun 28 04:41:43 2011 +0000
@@ -28,6 +28,8 @@
   dw_groupbox_new                        @41
   dw_box_pack_start                      @42
   dw_box_pack_end                        @43
+  dw_box_pack_at_index                   @44
+  
   dw_mdi_new                             @46
 
   dw_window_new                          @50
--- a/dw.h	Sun Jun 26 02:36:23 2011 +0000
+++ b/dw.h	Tue Jun 28 04:41:43 2011 +0000
@@ -1427,6 +1427,7 @@
 /* Public function prototypes */
 void API dw_box_pack_start(HWND box, HWND item, int width, int height, int hsize, int vsize, int pad);
 void API dw_box_pack_end(HWND box, HWND item, int width, int height, int hsize, int vsize, int pad);
+void API dw_box_pack_at_index(HWND box, HWND item, int index, int width, int height, int hsize, int vsize, int pad);
 #if !defined(__OS2__) && !defined(__WIN32__) && !defined(__EMX__) && !defined(__MAC__)
 int API dw_int_init(DWResources *res, int newthread, int *argc, char **argv[]);
 #define dw_init(a, b, c) dw_int_init(&_resources, a, &b, &c)
--- a/dwtest.c	Sun Jun 26 02:36:23 2011 +0000
+++ b/dwtest.c	Tue Jun 28 04:41:43 2011 +0000
@@ -775,9 +775,6 @@
     cursortogglebutton = dw_button_new("Set Cursor pointer - CLOCK", 1003L);
     dw_box_pack_start(buttonbox, cursortogglebutton, 130, 30, TRUE, TRUE, 2);
 
-    colorchoosebutton = dw_button_new("Color Chooser Dialog", 1004L);
-    dw_box_pack_start(buttonbox, colorchoosebutton, 130, 30, TRUE, TRUE, 2);
-
     okbutton = dw_button_new("Turn Off Annoying Beep!", 1001L);
     dw_box_pack_start(buttonbox, okbutton, 130, 30, TRUE, TRUE, 2);
 
@@ -785,6 +782,9 @@
     dw_box_pack_start(buttonbox, cancelbutton, 130, 30, TRUE, TRUE, 2);
     dw_window_click_default( mainwindow, cancelbutton );
 
+    colorchoosebutton = dw_button_new("Color Chooser Dialog", 1004L);
+    dw_box_pack_at_index(buttonbox, colorchoosebutton, 1, 130, 30, TRUE, TRUE, 2);
+
     /* Set some nice fonts and colors */
     dw_window_set_color(lbbox, DW_CLR_DARKCYAN, DW_CLR_PALEGRAY);
     dw_window_set_color(buttonbox, DW_CLR_DARKCYAN, DW_CLR_PALEGRAY);
--- a/dww.def	Sun Jun 26 02:36:23 2011 +0000
+++ b/dww.def	Tue Jun 28 04:41:43 2011 +0000
@@ -25,6 +25,8 @@
   dw_groupbox_new                        @41
   dw_box_pack_start                      @42
   dw_box_pack_end                        @43
+  dw_box_pack_at_index                   @44
+  
   dw_mdi_new                             @46
 
   dw_window_new                          @50
--- a/mac/dw.m	Sun Jun 26 02:36:23 2011 +0000
+++ b/mac/dw.m	Tue Jun 28 04:41:43 2011 +0000
@@ -3155,6 +3155,124 @@
 }
 
 /*
+ * Pack windows (widgets) into a box at an arbitrary location.
+ * Parameters:
+ *       box: Window handle of the box to be packed into.
+ *       item: Window handle of the item to be back.
+ *       index: 0 based index of packed items. 
+ *       width: Width in pixels of the item or -1 to be self determined.
+ *       height: Height in pixels of the item or -1 to be self determined.
+ *       hsize: TRUE if the window (widget) should expand horizontally to fill space given.
+ *       vsize: TRUE if the window (widget) should expand vertically to fill space given.
+ *       pad: Number of pixels of padding around the item.
+ */
+void API dw_box_pack_at_index(HWND box, HWND item, int index, int width, int height, int hsize, int vsize, int pad)
+{
+    int _locked_by_me = FALSE;
+    DW_MUTEX_LOCK;
+    id object = box;
+    DWBox *view = box;
+    DWBox *this = item;
+    Box *thisbox;
+    int z, x = 0;
+    Item *tmpitem, *thisitem;
+
+    /* Query the objects */
+    if([ object isKindOfClass:[ NSWindow class ] ])
+    {
+        NSWindow *window = box;
+        view = [window contentView];
+    }
+    else if([ object isMemberOfClass:[ DWScrollBox class ] ])
+    {
+        DWScrollBox *scrollbox = box;
+        view = [scrollbox box];
+    }
+
+    thisbox = [view box];
+    thisitem = thisbox->items;
+    object = item;
+
+    /* Query the objects */
+    if([ object isKindOfClass:[ DWContainer class ] ])
+    {
+        DWContainer *cont = item;
+        this = item = [cont scrollview];
+    }
+    else if([ object isKindOfClass:[ DWTree class ] ])
+    {
+        DWTree *tree = item;
+        this = item = [tree scrollview];
+    }
+
+    /* Do some sanity bounds checking */
+    if(index < 0)
+       index = 0;
+    if(index > thisbox->count)
+       index = thisbox->count;
+        
+    /* Duplicate the existing data */
+    tmpitem = malloc(sizeof(Item)*(thisbox->count+1));
+
+    for(z=0;z<thisbox->count;z++)
+    {
+       if(z == index)
+           x++;
+       tmpitem[z+1] = thisitem[z];
+       x++;
+    }
+
+    /* Sanity checks */
+    if(vsize && !height)
+       height = 1;
+    if(hsize && !width)
+       width = 1;
+
+    /* Fill in the item data appropriately */
+    if([object isKindOfClass:[DWBox class]] || [object isMemberOfClass:[DWGroupBox class]])
+       tmpitem[index].type = TYPEBOX;
+    else
+       tmpitem[index].type = TYPEITEM;
+
+    tmpitem[index].hwnd = item;
+    tmpitem[index].origwidth = tmpitem[index].width = width;
+    tmpitem[index].origheight = tmpitem[index].height = height;
+    tmpitem[index].pad = pad;
+    if(hsize)
+       tmpitem[index].hsize = SIZEEXPAND;
+    else
+       tmpitem[index].hsize = SIZESTATIC;
+
+    if(vsize)
+       tmpitem[index].vsize = SIZEEXPAND;
+    else
+       tmpitem[index].vsize = SIZESTATIC;
+
+    thisbox->items = tmpitem;
+
+    /* Update the item count */
+    thisbox->count++;
+
+    /* Add the item to the box */
+    [view addSubview:this];
+    /* If we are packing a button... */
+    if([this isMemberOfClass:[DWButton class]])
+    {
+        DWButton *button = (DWButton *)this;
+
+        /* Save the parent box so radio
+         * buttons can use it later.
+         */
+        [button setParent:view];
+    }
+
+    /* Free the old data */
+    if(thisbox->count)
+       free(thisitem);
+    DW_MUTEX_UNLOCK;
+}
+
+/*
  * Pack windows (widgets) into a box from the end (or bottom).
  * Parameters:
  *       box: Window handle of the box to be packed into.
--- a/os2/dw.c	Sun Jun 26 02:36:23 2011 +0000
+++ b/os2/dw.c	Tue Jun 28 04:41:43 2011 +0000
@@ -5973,6 +5973,121 @@
 }
 
 /*
+ * Pack windows (widgets) into a box at an arbitrary location.
+ * Parameters:
+ *       box: Window handle of the box to be packed into.
+ *       item: Window handle of the item to be back.
+ *       index: 0 based index of packed items. 
+ *       width: Width in pixels of the item or -1 to be self determined.
+ *       height: Height in pixels of the item or -1 to be self determined.
+ *       hsize: TRUE if the window (widget) should expand horizontally to fill space given.
+ *       vsize: TRUE if the window (widget) should expand vertically to fill space given.
+ *       pad: Number of pixels of padding around the item.
+ */
+void API dw_box_pack_at_index(HWND box, HWND item, int index, int width, int height, int hsize, int vsize, int pad)
+{
+   char *funcname = "dw_box_pack_at_index()";
+   Box *thisbox;
+   
+      /*
+       * If you try and pack an item into itself VERY bad things can happen; like at least an
+       * infinite loop on GTK! Lets be safe!
+       */
+   if(box == item)
+   {
+      dw_messagebox(funcname, DW_MB_OK|DW_MB_ERROR, "Danger! Danger! Will Robinson; box and item are the same!");
+      return;
+   }
+
+   if(WinWindowFromID(box, FID_CLIENT))
+   {
+      HWND intbox = (HWND)dw_window_get_data(box, "_dw_box");
+      if(intbox)
+      {
+         box = intbox;
+      }
+      else
+      {
+         box = WinWindowFromID(box, FID_CLIENT);
+         hsize = vsize = TRUE;
+      }
+   }
+   
+   thisbox = WinQueryWindowPtr(box, QWP_USER);
+
+   if(thisbox)
+   {
+      int z, x = 0;
+      Item *tmpitem, *thisitem = thisbox->items;
+      char tmpbuf[100];
+      HWND frame = (HWND)dw_window_get_data(item, "_dw_combo_box");
+
+      /* Do some sanity bounds checking */
+      if(index < 0)
+        index = 0;
+      if(index > thisbox->count)
+        index = thisbox->count;
+        
+      tmpitem = malloc(sizeof(Item)*(thisbox->count+1));
+
+      for(z=0;z<thisbox->count;z++)
+      {
+         if(z == index)
+            x++;
+         tmpitem[x] = thisitem[z];
+         x++;
+      }
+
+
+      WinQueryClassName(item, 99, tmpbuf);
+
+      if(vsize && !height)
+         height = 1;
+      if(hsize && !width)
+         width = 1;
+
+      if(strncmp(tmpbuf, "#1", 3)==0)
+         tmpitem[index].type = TYPEBOX;
+      else
+      {
+         if ( width == 0 && hsize == FALSE )
+            dw_messagebox(functionname, DW_MB_OK|DW_MB_ERROR, "Width and expand Horizonal both unset for box: %x item: %x",box,item);
+         if ( height == 0 && vsize == FALSE )
+            dw_messagebox(functionname, DW_MB_OK|DW_MB_ERROR, "Height and expand Vertical both unset for box: %x item: %x",box,item);
+
+         tmpitem[index].type = TYPEITEM;
+      }
+
+      tmpitem[index].hwnd = item;
+      tmpitem[index].origwidth = tmpitem[index].width = width;
+      tmpitem[index].origheight = tmpitem[index].height = height;
+      tmpitem[index].pad = pad;
+      if(hsize)
+         tmpitem[index].hsize = SIZEEXPAND;
+      else
+         tmpitem[index].hsize = SIZESTATIC;
+
+      if(vsize)
+         tmpitem[index].vsize = SIZEEXPAND;
+      else
+         tmpitem[index].vsize = SIZESTATIC;
+
+      thisbox->items = tmpitem;
+
+      if(thisbox->count)
+         free(thisitem);
+
+      thisbox->count++;
+
+      WinQueryClassName(item, 99, tmpbuf);
+      /* Don't set the ownership if it's an entryfield or spinbutton */
+      if(strncmp(tmpbuf, "#6", 3)!=0 && strncmp(tmpbuf, "#32", 4)!=0 && strncmp(tmpbuf, "#2", 3)!=0)
+         WinSetOwner(item, box);
+      WinSetParent(frame ? frame : item, box, FALSE);
+   }
+}
+
+/*
  * Pack windows (widgets) into a box from the end (or bottom).
  * Parameters:
  *       box: Window handle of the box to be packed into.
--- a/win/dw.c	Sun Jun 26 02:36:23 2011 +0000
+++ b/win/dw.c	Tue Jun 28 04:41:43 2011 +0000
@@ -5930,6 +5930,131 @@
 }
 
 /*
+ * Pack windows (widgets) into a box at an arbitrary location.
+ * Parameters:
+ *       box: Window handle of the box to be packed into.
+ *       item: Window handle of the item to be back.
+ *       index: 0 based index of packed items. 
+ *       width: Width in pixels of the item or -1 to be self determined.
+ *       height: Height in pixels of the item or -1 to be self determined.
+ *       hsize: TRUE if the window (widget) should expand horizontally to fill space given.
+ *       vsize: TRUE if the window (widget) should expand vertically to fill space given.
+ *       pad: Number of pixels of padding around the item.
+ */
+void API dw_box_pack_at_index(HWND box, HWND item, int index, int width, int height, int hsize, int vsize, int pad)
+{
+   Box *thisbox = NULL;
+   char tmpbuf[100];
+
+      /*
+       * If you try and pack an item into itself VERY bad things can happen; like at least an
+       * infinite loop on GTK! Lets be safe!
+       */
+   if(box == item)
+   {
+      dw_messagebox("dw_box_pack_start()", DW_MB_OK|DW_MB_ERROR, "Danger! Danger! Will Robinson; box and item are the same!");
+      return;
+   }
+
+   GetClassName(box, tmpbuf, 99);
+
+   /* If we are in a scrolled box... extract the interal box */
+   if(strnicmp(tmpbuf, ScrollClassName, strlen(ScrollClassName)+1)==0)
+   {
+        ColorInfo *cinfo = (ColorInfo *)GetWindowLongPtr(box, GWLP_USERDATA);
+        if(cinfo)
+        {
+            box = cinfo->buddy;
+            thisbox = (Box *)GetWindowLongPtr(box, GWLP_USERDATA);
+        }
+   }
+   else //if(strnicmp(tmpbuf, FRAMECLASSNAME, strlen(FRAMECLASSNAME)+1)==0)
+       thisbox = (Box *)GetWindowLongPtr(box, GWLP_USERDATA);
+   if(thisbox)
+   {
+      int z, x = 0;
+      Item *tmpitem, *thisitem = thisbox->items;
+      
+      /* Do some sanity bounds checking */
+      if(index < 0)
+        index = 0;
+      if(index > thisbox->count)
+        index = thisbox->count;
+
+      tmpitem = malloc(sizeof(Item)*(thisbox->count+1));
+
+      for(z=0;z<thisbox->count;z++)
+      {
+         if(z == index)
+            x++;
+         tmpitem[x] = thisitem[z];
+         x++;
+      }
+
+      GetClassName(item, tmpbuf, 99);
+
+      if(vsize && !height)
+         height = 1;
+      if(hsize && !width)
+         width = 1;
+
+      if(strnicmp(tmpbuf, FRAMECLASSNAME, strlen(FRAMECLASSNAME)+1)==0)
+         tmpitem[index].type = TYPEBOX;
+      else if(strnicmp(tmpbuf, "SysMonthCal32", 13)==0)
+      {
+         RECT rc;
+         MonthCal_GetMinReqRect(item, &rc);
+         width = 1 + rc.right - rc.left;
+         height = 1 + rc.bottom - rc.top;
+         tmpitem[index].type = TYPEITEM;
+      }
+      else
+      {
+         if ( width == 0 && hsize == FALSE )
+            dw_messagebox("dw_box_pack_start()", DW_MB_OK|DW_MB_ERROR, "Width and expand Horizonal both unset for box: %x item: %x",box,item);
+         if ( height == 0 && vsize == FALSE )
+            dw_messagebox("dw_box_pack_start()", DW_MB_OK|DW_MB_ERROR, "Height and expand Vertical both unset for box: %x item: %x",box,item);
+
+         tmpitem[index].type = TYPEITEM;
+      }
+
+      tmpitem[index].hwnd = item;
+      tmpitem[index].origwidth = tmpitem[index].width = width;
+      tmpitem[index].origheight = tmpitem[index].height = height;
+      tmpitem[index].pad = pad;
+      if(hsize)
+         tmpitem[index].hsize = SIZEEXPAND;
+      else
+         tmpitem[index].hsize = SIZESTATIC;
+
+      if(vsize)
+         tmpitem[index].vsize = SIZEEXPAND;
+      else
+         tmpitem[index].vsize = SIZESTATIC;
+
+      thisbox->items = tmpitem;
+
+      if(thisbox->count)
+         free(thisitem);
+
+      thisbox->count++;
+
+      SetParent(item, box);
+      if(strncmp(tmpbuf, UPDOWN_CLASS, strlen(UPDOWN_CLASS)+1)==0)
+      {
+         ColorInfo *cinfo = (ColorInfo *)GetWindowLongPtr(item, GWLP_USERDATA);
+
+         if(cinfo)
+         {
+            SetParent(cinfo->buddy, box);
+            ShowWindow(cinfo->buddy, SW_SHOW);
+            SendMessage(item, UDM_SETBUDDY, (WPARAM)cinfo->buddy, 0);
+         }
+      }
+   }
+}
+
+/*
  * Pack windows (widgets) into a box from the start (or top).
  * Parameters:
  *       box: Window handle of the box to be packed into.