/*
 * Combo controls
 * 
 * Copyright 1993 Martin Ayotte
 * Copyright 1995 Bernd Schmidt
 * Copyright 1996 Albrecht Kleine  [some fixes]
 * 
 */

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/types.h>
#include <sys/stat.h>

#include "windows.h"
#include "sysmetrics.h"
#include "combo.h"
#include "stackframe.h"
#include "user.h"
#include "win.h"
#include "graphics.h"
#include "heap.h"
#include "listbox.h"
#include "dos_fs.h"
#include "drive.h"
#include "stddebug.h"
#include "debug.h"
#include "xmalloc.h"

 /*
  * Note: Combos are probably implemented in a different way by Windows.
  * Using a message spy for Windows, you can see some undocumented
  * messages being passed between ComboBox and ComboLBox.
  * I hope no programs rely on the implementation of combos.
  */

#define ID_EDIT  1
#define ID_CLB   2
#define CBLMM_EDGE   4    /* distance inside box which is same as moving mouse
			     outside box, to trigger scrolling of CBL */

static BOOL CBCheckSize(HWND hwnd);
static BOOL CBLCheckSize(HWND hwnd);

static HBITMAP hComboBit = 0;
static WORD CBitHeight, CBitWidth;

static int COMBO_Init()
{
  BITMAP16 bm;
  
  dprintf_combo(stddeb, "COMBO_Init\n");
  hComboBit = LoadBitmap16(0, MAKEINTRESOURCE(OBM_COMBO));
  GetObject16( hComboBit, sizeof(bm), &bm );
  CBitHeight = bm.bmHeight;
  CBitWidth = bm.bmWidth;
  return 0;
}

LPHEADCOMBO ComboGetStorageHeader(HWND hwnd)
{
  return (LPHEADCOMBO)GetWindowLong32A(hwnd,4);
}

LPHEADLIST ComboGetListHeader(HWND hwnd)
{
  return (LPHEADLIST)GetWindowLong32A(hwnd,0);
}

int CreateComboStruct(HWND hwnd, LONG style)
{
  LPHEADCOMBO lphc;

  lphc = (LPHEADCOMBO)xmalloc(sizeof(HEADCOMBO));
  SetWindowLong32A(hwnd,4,(LONG)lphc);
  lphc->hWndEdit = 0;
  lphc->hWndLBox = 0;
  lphc->dwState = 0;
  lphc->LastSel = -1;
  lphc->dwStyle = style; 
  lphc->DropDownVisible = FALSE;
  return TRUE;
}

void ComboUpdateWindow(HWND hwnd, LPHEADLIST lphl, LPHEADCOMBO lphc, BOOL repaint)
{
  WND *wndPtr = WIN_FindWndPtr(hwnd);

  if (wndPtr->dwStyle & WS_VSCROLL) 
    SetScrollRange(lphc->hWndLBox,SB_VERT,0,ListMaxFirstVisible(lphl),TRUE);
  if (repaint && lphl->bRedrawFlag) InvalidateRect32( hwnd, NULL, TRUE );
}

/***********************************************************************
 *           CBNCCreate
 */
static LRESULT CBNCCreate(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  CREATESTRUCT16 *createStruct;

  if (!hComboBit) COMBO_Init();

  createStruct = (CREATESTRUCT16 *)PTR_SEG_TO_LIN(lParam);
  createStruct->style |= WS_BORDER;
  SetWindowLong32A(hwnd, GWL_STYLE, createStruct->style);

  dprintf_combo(stddeb,"ComboBox WM_NCCREATE!\n");
  return DefWindowProc16(hwnd, WM_NCCREATE, wParam, lParam);

}

/***********************************************************************
 *           CBCreate
 */
static LRESULT CBCreate(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADLIST   lphl;
  LPHEADCOMBO  lphc;
  LONG         style = 0;
  LONG         cstyle = GetWindowLong32A(hwnd,GWL_STYLE);
  RECT16       rect,lboxrect;
  WND*         wndPtr = WIN_FindWndPtr(hwnd);
  char className[] = "COMBOLBOX";  /* Hack so that class names are > 0x10000 */
  char editName[] = "EDIT";
  HWND hwndp=0;

  /* translate combo into listbox styles */
  cstyle |= WS_BORDER;
  if (cstyle & CBS_OWNERDRAWFIXED) style |= LBS_OWNERDRAWFIXED;
  if (cstyle & CBS_OWNERDRAWVARIABLE) style |= LBS_OWNERDRAWVARIABLE;
  if (cstyle & CBS_SORT) style |= LBS_SORT;
  if (cstyle & CBS_HASSTRINGS) style |= LBS_HASSTRINGS;
  style |= LBS_NOTIFY;
  CreateListBoxStruct(hwnd, ODT_COMBOBOX, style, GetParent(hwnd));
  CreateComboStruct(hwnd,cstyle);

  lphl = ComboGetListHeader(hwnd);
  lphc = ComboGetStorageHeader(hwnd);

  GetClientRect16(hwnd,&rect);
  lphc->LBoxTop = lphl->StdItemHeight;

  switch(cstyle & 3) 
  {
   case CBS_SIMPLE:            /* edit control, list always visible  */
     lboxrect=rect;    
     dprintf_combo(stddeb,"CBS_SIMPLE\n");
     style= WS_BORDER |  WS_CHILD | WS_VISIBLE | WS_VSCROLL;
     SetRectEmpty16(&lphc->RectButton);
     hwndp=hwnd;
     break;

   case CBS_DROPDOWNLIST:      /* static control, dropdown listbox   */
   case CBS_DROPDOWN:          /* edit control, dropdown listbox     */
     GetWindowRect16(hwnd,&lboxrect);
     style = WS_POPUP | WS_BORDER | WS_VSCROLL;
     /* FIXME: WinSight says these should be CHILD windows with the TOPMOST flag
      * set. Wine doesn't support TOPMOST, and simply setting the WS_CHILD
      * flag doesn't work. */
     lphc->RectButton = rect;
     lphc->RectButton.left = lphc->RectButton.right - 6 - CBitWidth;
     lphc->RectButton.bottom = lphc->RectButton.top + lphl->StdItemHeight;
     SetWindowPos(hwnd, 0, 0, 0, rect.right -rect.left + 2*SYSMETRICS_CXBORDER,
		 lphl->StdItemHeight + 2*SYSMETRICS_CYBORDER,
		 SWP_NOMOVE | SWP_NOZORDER | SWP_NOSENDCHANGING);
     dprintf_combo(stddeb,(cstyle & 3)==CBS_DROPDOWN ? "CBS_DROPDOWN\n": "CBS_DROPDOWNLIST\n");
     break;
     
   default: fprintf(stderr,"COMBOBOX error: bad class style!\n");
     return 0;
  }

  if ((cstyle & 3) != CBS_DROPDOWNLIST)
      lphc->hWndEdit = CreateWindow16( editName, NULL,
				  WS_CHILD | WS_CLIPCHILDREN | WS_VISIBLE | ES_LEFT,
				  0, 0, rect.right-6-CBitWidth,
				  lphl->StdItemHeight+2*SYSMETRICS_CYBORDER,
				  hwnd, (HMENU)ID_EDIT, WIN_GetWindowInstance(hwnd), NULL );
				  
  lboxrect.top+=lphc->LBoxTop;
  lphc->hWndLBox = CreateWindow16( className, NULL, style |
 				((cstyle & WS_HSCROLL)? WS_HSCROLL : 0) |
 				((cstyle & WS_VSCROLL)? WS_VSCROLL : 0),
				lboxrect.left, lboxrect.top,
				lboxrect.right - lboxrect.left, 
				lboxrect.bottom - lboxrect.top,
				hwndp,(HMENU)ID_CLB, WIN_GetWindowInstance(hwnd),
				(LPVOID)(HWND32)hwnd );

   wndPtr->dwStyle &= ~(WS_VSCROLL | WS_HSCROLL);

   dprintf_combo( stddeb, "Combo Creation hwnd=%04x  LBox=%04x  Edit=%04x\n",
                  hwnd, lphc->hWndLBox, lphc->hWndEdit);
   dprintf_combo( stddeb, "  lbox %d,%d-%d,%d     button %d,%d-%d,%d\n",
                  lboxrect.left, lboxrect.top, lboxrect.right, lboxrect.bottom,
                  lphc->RectButton.left, lphc->RectButton.top,
                  lphc->RectButton.right, lphc->RectButton.bottom );
   dprintf_combo( stddeb, "   client %d,%d-%d,%d     window %d,%d-%d,%d\n",
                  wndPtr->rectClient.left, wndPtr->rectClient.top,
                  wndPtr->rectClient.right, wndPtr->rectClient.bottom,
                  wndPtr->rectWindow.left, wndPtr->rectWindow.top,
                  wndPtr->rectWindow.right, wndPtr->rectWindow.bottom );
   return 0;
}

/***********************************************************************
 *           CBDestroy
 */
static LRESULT CBDestroy(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADCOMBO lphc = ComboGetStorageHeader(hwnd);

  if (lphc->hWndEdit) DestroyWindow( lphc->hWndEdit );
  if (lphc->hWndLBox) DestroyWindow( lphc->hWndLBox );
  return 0;
}

/***********************************************************************
 *           CBPaint
 */
static LRESULT CBPaint(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  LPHEADCOMBO lphc = ComboGetStorageHeader(hwnd);
  LPLISTSTRUCT lpls;
  PAINTSTRUCT16  ps;
  HBRUSH hBrush;
  HFONT  hOldFont;
  HDC16 hdc;
  RECT16 rect;
  
  hdc = BeginPaint16(hwnd, &ps);

  GetClientRect16(hwnd, &rect);
  CBCheckSize(hwnd);
  /* 1 for button border */
  rect.right = lphc->RectButton.left - 1;

  if (hComboBit != 0 && !IsRectEmpty16(&lphc->RectButton))
  {
    Rectangle(hdc,lphc->RectButton.left-1,lphc->RectButton.top-1,
	      lphc->RectButton.right+1,lphc->RectButton.bottom+1);
    GRAPH_DrawReliefRect(hdc, &lphc->RectButton, 2, 2, FALSE);
    GRAPH_DrawBitmap(hdc, hComboBit,
		     lphc->RectButton.left + 2,lphc->RectButton.top + 2,
		     0, 0, CBitWidth, CBitHeight );
  }
  if (!IsWindowVisible(hwnd) || !lphl->bRedrawFlag 
      || (lphc->dwStyle & 3) != CBS_DROPDOWNLIST) 
  {
    /* we don't want to draw an entry when there is an edit control */
    EndPaint16(hwnd, &ps);
    return 0;
  }

  hOldFont = SelectObject(hdc, lphl->hFont);

  hBrush = SendMessage32A( lphl->hParent, WM_CTLCOLORLISTBOX, hdc, hwnd );
  if (hBrush == 0) hBrush = GetStockObject(WHITE_BRUSH);

  lpls = ListBoxGetItem(lphl,lphl->ItemFocused);
  if (lpls != NULL) {  
    FillRect16(hdc, &rect, hBrush);
    ListBoxDrawItem (hwnd, lphl, hdc, lpls, &rect, ODA_DRAWENTIRE, 0);
    if (GetFocus() == hwnd)
    ListBoxDrawItem (hwnd,lphl, hdc, lpls, &rect, ODA_FOCUS, ODS_FOCUS);
  }
  else FillRect16(hdc, &rect, hBrush);
  SelectObject(hdc,hOldFont);
  EndPaint16(hwnd, &ps);
  return 0;
}

/***********************************************************************
 *           CBGetDlgCode
 */
static LRESULT CBGetDlgCode(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  return DLGC_WANTARROWS | DLGC_WANTCHARS;
}

/***********************************************************************
 *           CBLButtonDown
 */
static LRESULT CBLButtonDown(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADCOMBO lphc = ComboGetStorageHeader(hwnd);
  SendMessage16(hwnd,CB_SHOWDROPDOWN,!lphc->DropDownVisible,0);
  return 0;
}

/***********************************************************************
 *           CBKeyDown
 */
static LRESULT CBKeyDown(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  WORD       newFocused = lphl->ItemFocused;

  switch(wParam) {
  case VK_HOME:
    newFocused = 0;
    break;
  case VK_END:
    newFocused = lphl->ItemsCount - 1;
    break;
  case VK_UP:
    if (newFocused > 0) newFocused--;
    break;
  case VK_DOWN:
    newFocused++;
    break;
  default:
    return 0;
  }

  if (newFocused >= lphl->ItemsCount)
    newFocused = lphl->ItemsCount - 1;
  
  ListBoxSetCurSel(lphl, newFocused);
  SendMessage16(hwnd, WM_COMMAND,ID_CLB,MAKELONG(0,CBN_SELCHANGE));
  ListBoxSendNotification(lphl, CBN_SELCHANGE);

  lphl->ItemFocused = newFocused;
  ListBoxScrollToFocus(lphl);
/*  SetScrollPos(hwnd, SB_VERT, lphl->FirstVisible, TRUE);*/
  InvalidateRect32( hwnd, NULL, TRUE );

  return 0;
}

/***********************************************************************
 *           CBChar
 */
static LRESULT CBChar(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  WORD       newFocused;

  newFocused = ListBoxFindNextMatch(lphl, wParam);
  if (newFocused == (WORD)LB_ERR) return 0;

  if (newFocused >= lphl->ItemsCount)
    newFocused = lphl->ItemsCount - 1;
  
  ListBoxSetCurSel(lphl, newFocused);
  SendMessage16(hwnd, WM_COMMAND,ID_CLB,MAKELONG(0,CBN_SELCHANGE));
  ListBoxSendNotification(lphl, CBN_SELCHANGE);
  lphl->ItemFocused = newFocused;
  ListBoxScrollToFocus(lphl);
  
/*  SetScrollPos(hwnd, SB_VERT, lphl->FirstVisible, TRUE);*/
  InvalidateRect32( hwnd, NULL, TRUE );

  return 0;
}

/***********************************************************************
 *           CBKillFocus
 */
static LRESULT CBKillFocus(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  return 0;
}

/***********************************************************************
 *           CBSetFocus
 */
static LRESULT CBSetFocus(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  return 0;
}

/***********************************************************************
 *           CBResetContent
 */
static LRESULT CBResetContent(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  LPHEADCOMBO lphc = ComboGetStorageHeader(hwnd);

  ListBoxResetContent(lphl);
  ComboUpdateWindow(hwnd, lphl, lphc, TRUE);
  return 0;
}

/***********************************************************************
 *           CBDir
 */
static LRESULT CBDir(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  WORD wRet;
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  LPHEADCOMBO lphc = ComboGetStorageHeader(hwnd);

  wRet = ListBoxDirectory(lphl, wParam, (LPSTR)PTR_SEG_TO_LIN(lParam));
  ComboUpdateWindow(hwnd, lphl, lphc, TRUE);
  return wRet;
}

/***********************************************************************
 *           CBInsertString
 */
static LRESULT CBInsertString(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  WORD  wRet;
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  LPHEADCOMBO lphc = ComboGetStorageHeader(hwnd);

  if (lphl->HasStrings)
    wRet = ListBoxInsertString(lphl, wParam, (LPSTR)PTR_SEG_TO_LIN(lParam));
  else
    wRet = ListBoxInsertString(lphl, wParam, (LPSTR)lParam);
  ComboUpdateWindow(hwnd, lphl, lphc, TRUE);
  return wRet;
}

/***********************************************************************
 *           CBAddString
 */
static LRESULT CBAddString(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  WORD  wRet;
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  LPHEADCOMBO lphc = ComboGetStorageHeader(hwnd);

  if (lphl->HasStrings)
    wRet = ListBoxAddString(lphl, (LPSTR)PTR_SEG_TO_LIN(lParam));
  else
    wRet = ListBoxAddString(lphl, (LPSTR)lParam);

  ComboUpdateWindow(hwnd, lphl, lphc, TRUE);
  return wRet;
}

/***********************************************************************
 *           CBDeleteString
 */
static LRESULT CBDeleteString(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  LPHEADCOMBO lphc = ComboGetStorageHeader(hwnd);
  LONG lRet = ListBoxDeleteString(lphl,wParam);
  
  ComboUpdateWindow(hwnd, lphl, lphc, TRUE);
  return lRet;
}

/***********************************************************************
 *           CBSelectString
 */
static LRESULT CBSelectString(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  WORD  wRet;

  wRet = ListBoxFindString(lphl, wParam, (SEGPTR)lParam);

  /* XXX add functionality here */

  return 0;
}

/***********************************************************************
 *           CBFindString
 */
static LRESULT CBFindString(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  return ListBoxFindString(lphl, wParam, (SEGPTR)lParam);
}

/***********************************************************************
 *           CBGetCount
 */
static LRESULT CBGetCount(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  return lphl->ItemsCount;
}

/***********************************************************************
 *           CBSetCurSel
 */
static LRESULT CBSetCurSel(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  WORD  wRet;

  wRet = ListBoxSetCurSel(lphl, wParam);

  dprintf_combo(stddeb,"CBSetCurSel: hwnd %04x wp %x lp %lx wRet %d\n",
		hwnd,wParam,lParam,wRet);
/*  SetScrollPos(hwnd, SB_VERT, lphl->FirstVisible, TRUE);*/
  InvalidateRect32( hwnd, NULL, TRUE );

  return wRet;
}

/***********************************************************************
 *           CBGetCurSel
 */
static LRESULT CBGetCurSel(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  return lphl->ItemFocused;
}

/***********************************************************************
 *           CBGetItemHeight
 */
static LRESULT CBGetItemHeight(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  LPLISTSTRUCT lpls = ListBoxGetItem (lphl, wParam);

  if (lpls == NULL) return LB_ERR;
  return lpls->mis.itemHeight;
}

/***********************************************************************
 *           CBSetItemHeight
 */
static LRESULT CBSetItemHeight(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  return ListBoxSetItemHeight(lphl, wParam, lParam);
}

/***********************************************************************
 *           CBSetRedraw
 */
static LRESULT CBSetRedraw(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  lphl->bRedrawFlag = wParam;
  return 0;
}

/***********************************************************************
 *           CBSetFont
 */
static LRESULT CBSetFont(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADLIST  lphl = ComboGetListHeader(hwnd);
  LPHEADCOMBO lphc = ComboGetStorageHeader(hwnd);
  
  if (wParam == 0)
    lphl->hFont = GetStockObject(SYSTEM_FONT);
  else
    lphl->hFont = (HFONT)wParam;
  if (lphc->hWndEdit)
     SendMessage16(lphc->hWndEdit,WM_SETFONT,lphl->hFont,0); 
  return 0;
}

/***********************************************************************
 *           CBGetLBTextLen
 */
static LRESULT CBGetLBTextLen(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADLIST   lphl = ComboGetListHeader(hwnd);
  LPLISTSTRUCT lpls = ListBoxGetItem(lphl,wParam);

  if (lpls == NULL || !lphl->HasStrings) return LB_ERR;
  return strlen(lpls->itemText);
}

/***********************************************************************
 *           CBGetLBText
 */
static LRESULT CBGetLBText(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  return ListBoxGetText(lphl, wParam, (LPSTR)PTR_SEG_TO_LIN(lParam));
}

/***********************************************************************
 *           CBGetItemData
 */
static LRESULT CBGetItemData(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  return ListBoxGetItemData(lphl, wParam);
}

/***********************************************************************
 *           CBSetItemData
 */
static LRESULT CBSetItemData(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  return ListBoxSetItemData(lphl, wParam, lParam);
}

/***********************************************************************
 *           CBShowDropDown
 */
static LRESULT CBShowDropDown(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADCOMBO lphc = ComboGetStorageHeader(hwnd);
  RECT32 rect;
  
  if ((lphc->dwStyle & 3) == CBS_SIMPLE) return LB_ERR;
  
  wParam = !!wParam;
  if (wParam != lphc->DropDownVisible) {
    lphc->DropDownVisible = wParam;
    GetWindowRect32(hwnd,&rect);
    SetWindowPos(lphc->hWndLBox, 0, rect.left, rect.top+lphc->LBoxTop, 0, 0,
		 SWP_NOSIZE | (wParam ? SWP_SHOWWINDOW : SWP_HIDEWINDOW));
    if (!wParam) SetFocus(hwnd);
  }
  return 0;
}


/***********************************************************************
 *             CBCheckSize
 */
static BOOL CBCheckSize(HWND hwnd)
{
  LPHEADCOMBO  lphc = ComboGetStorageHeader(hwnd);
  LPHEADLIST   lphl = ComboGetListHeader(hwnd);
  LONG         cstyle = GetWindowLong32A(hwnd,GWL_STYLE);
  RECT16       cRect,wRect;

  if (lphc->hWndLBox == 0) return FALSE;

  GetClientRect16(hwnd,&cRect);
  GetWindowRect16(hwnd,&wRect);

  dprintf_combo(stddeb,
	 "CBCheckSize: hwnd %04x Rect %d,%d-%d,%d  wRect %d,%d-%d,%d\n", 
		hwnd,cRect.left,cRect.top,cRect.right,cRect.bottom,
		wRect.left,wRect.top,wRect.right,wRect.bottom);
  if ((cstyle & 3) == CBS_SIMPLE  ) return TRUE ;

  if ((cRect.bottom - cRect.top) > 
      (lphl->StdItemHeight + 2*SYSMETRICS_CYBORDER)) {
    SetWindowPos(hwnd, 0, 0, 0, 
		 cRect.right-cRect.left,
		 lphl->StdItemHeight+2*SYSMETRICS_CYBORDER, 
		 SWP_NOMOVE | SWP_NOZORDER | SWP_NOREDRAW | SWP_NOACTIVATE );
    GetClientRect16(hwnd,&cRect);
    GetWindowRect16(hwnd,&wRect);

    lphc->RectButton.right = cRect.right;
    lphc->RectButton.left = cRect.right - 2*SYSMETRICS_CXBORDER - 4 
                            - CBitWidth;
    lphc->RectButton.top = cRect.top;
    lphc->RectButton.bottom = cRect.bottom;
  }

  if (cRect.right < lphc->RectButton.left) {
    /* if the button is outside the window, move it in */
    if ((wRect.right - wRect.left - 2*SYSMETRICS_CXBORDER) == (cRect.right - cRect.left)) {
      lphc->RectButton.right = cRect.right;
      lphc->RectButton.left = cRect.right - 2*SYSMETRICS_CXBORDER - 4 
	                       - CBitWidth;
      lphc->RectButton.top = cRect.top;
      lphc->RectButton.bottom = cRect.bottom;
    }
    /* otherwise we need to make the client include the button */
    else
      SetWindowPos(hwnd, 0, 0, 0, lphc->RectButton.right,
		   lphl->StdItemHeight+2*SYSMETRICS_CYBORDER, 
		   SWP_NOMOVE | SWP_NOZORDER | SWP_NOREDRAW | SWP_NOACTIVATE );
  }

  CBLCheckSize(hwnd);
  return TRUE;
}

/***********************************************************************
 *           CBCommand        
 */
static LRESULT CBCommand(HWND hwnd, WPARAM wParam, LPARAM lParam)
{
  LPHEADCOMBO lphc = ComboGetStorageHeader(hwnd);
  LPHEADLIST lphl = ComboGetListHeader(hwnd);
  char       buffer[256];
  WORD       newFocused;
  WORD       id;
  if (lphc->hWndEdit)  /* interdependence only used for CBS_SIMPLE and CBS_DROPDOWN styles */
  {
   switch (wParam)
   {
    case ID_CLB:                                        /* update EDIT window */
                if (HIWORD(lParam)==CBN_SELCHANGE)
                 if (lphl->HasStrings)
                 { 
                  ListBoxGetText(lphl,lphl->ItemFocused, buffer);
                  dprintf_combo(stddeb,"CBCommand: update Edit: %s\n",buffer);
                  SetWindowText32A( lphc->hWndEdit, buffer );
                 }
                break;
    case ID_EDIT:                                      /* update LISTBOX window */
                 id=GetWindowWord(hwnd,GWW_ID);
                 switch (HIWORD(lParam))
                 {
                  case EN_UPDATE:GetWindowText32A(lphc->hWndEdit,buffer,255);
                                 if (*buffer)
                                 {
                                  newFocused=ListBoxFindString(lphl, -1, MAKE_SEGPTR(buffer));
                                  dprintf_combo(stddeb,"CBCommand: new selection #%d is= %s\n",
                                                newFocused,buffer);
                                  if (newFocused != (WORD)LB_ERR)
                                  {                             /* if found something */
                                   ListBoxSetCurSel(lphl, newFocused);
                                   ListBoxSendNotification(lphl, CBN_SELCHANGE);
                                   InvalidateRect32(hwnd, NULL, TRUE); 
                                  }
                                 }
                                 SendMessage16(GetParent(hwnd),WM_COMMAND,id,
                                         MAKELONG(hwnd, CBN_EDITUPDATE));
                                 break;
                  case EN_CHANGE:SendMessage16(GetParent(hwnd),WM_COMMAND,id,
                                         MAKELONG(hwnd, CBN_EDITCHANGE));
                                 break;
                  case EN_ERRSPACE:SendMessage16(GetParent(hwnd),WM_COMMAND,id,
                                         MAKELONG(hwnd, CBN_ERRSPACE));
                                 break;
                }
                break;        
   }
  } 
  return 0;
}


/***********************************************************************
 *           ComboWndProc
 */
LRESULT ComboBoxWndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
{
    switch(message) {	
     case WM_NCCREATE: return CBNCCreate(hwnd, wParam, lParam);
     case WM_CREATE: return CBCreate(hwnd, wParam, lParam);
     case WM_DESTROY: return CBDestroy(hwnd, wParam, lParam);
     case WM_GETDLGCODE: return CBGetDlgCode(hwnd, wParam, lParam);
     case WM_KEYDOWN: return CBKeyDown(hwnd, wParam, lParam);
     case WM_CHAR: return CBChar(hwnd, wParam, lParam);
     case WM_SETFONT: return CBSetFont(hwnd, wParam, lParam);
     case WM_SETREDRAW: return CBSetRedraw(hwnd, wParam, lParam);
     case WM_PAINT: return CBPaint(hwnd, wParam, lParam);
     case WM_LBUTTONDOWN: return CBLButtonDown(hwnd, wParam, lParam);
     case WM_SETFOCUS: return CBSetFocus(hwnd, wParam, lParam);
     case WM_KILLFOCUS: return CBKillFocus(hwnd, wParam, lParam);
     case WM_SIZE: return CBCheckSize(hwnd);
     case WM_COMMAND: return CBCommand(hwnd, wParam, lParam);
     case CB_RESETCONTENT: return CBResetContent(hwnd, wParam, lParam);
     case CB_DIR: return CBDir(hwnd, wParam, lParam);
     case CB_ADDSTRING: return CBAddString(hwnd, wParam, lParam);
     case CB_INSERTSTRING: return CBInsertString(hwnd, wParam, lParam);
     case CB_DELETESTRING: return CBDeleteString(hwnd, wParam, lParam);
     case CB_FINDSTRING: return CBFindString(hwnd, wParam, lParam);
     case CB_GETCOUNT: return CBGetCount(hwnd, wParam, lParam);
     case CB_GETCURSEL: return CBGetCurSel(hwnd, wParam, lParam);
     case CB_GETITEMDATA: return CBGetItemData(hwnd, wParam, lParam);
     case CB_GETITEMHEIGHT: return CBGetItemHeight(hwnd, wParam, lParam);
     case CB_GETLBTEXT: return CBGetLBText(hwnd, wParam, lParam);
     case CB_GETLBTEXTLEN: return CBGetLBTextLen(hwnd, wParam, lParam);
     case CB_SELECTSTRING: return CBSelectString(hwnd, wParam, lParam);
     case CB_SETITEMDATA: return CBSetItemData(hwnd, wParam, lParam);
     case CB_SETCURSEL: return CBSetCurSel(hwnd, wParam, lParam);
     case CB_SETITEMHEIGHT: return CBSetItemHeight(hwnd, wParam, lParam);
     case CB_SHOWDROPDOWN: return CBShowDropDown(hwnd, wParam, lParam);
    }
    return DefWindowProc16(hwnd, message, wParam, lParam);
}

/*--------------------------------------------------------------------*/
/* ComboLBox code starts here */

HWND CLBoxGetCombo(HWND hwnd)
{
  return (HWND)GetWindowLong32A(hwnd,0);
}

LPHEADLIST CLBoxGetListHeader(HWND hwnd)
{
  return ComboGetListHeader(CLBoxGetCombo(hwnd));
}

/***********************************************************************
 *           CBLCreate
 */
static LRESULT CBLCreate( HWND hwnd, WPARAM wParam, LPARAM lParam )
{
  CREATESTRUCT16 *createStruct = (CREATESTRUCT16 *)PTR_SEG_TO_LIN(lParam);
  SetWindowLong32A(hwnd,0,(LONG)createStruct->lpCreateParams);
  return 0;
}

/***********************************************************************
 *           CBLGetDlgCode
 */
static LRESULT CBLGetDlgCode( HWND hwnd, WPARAM wParam, LPARAM lParam )
{
  return DLGC_WANTARROWS | DLGC_WANTCHARS;
}

/***********************************************************************
 *           CBLKeyDown
 */
static LRESULT CBLKeyDown( HWND hwnd, WPARAM wParam, LPARAM lParam ) 
{
  LPHEADLIST lphl = CLBoxGetListHeader(hwnd);
  WORD newFocused = lphl->ItemFocused;

  switch(wParam) {
  case VK_HOME:
    newFocused = 0;
    break;
  case VK_END:
    newFocused = lphl->ItemsCount - 1;
    break;
  case VK_UP:
    if (newFocused > 0) newFocused--;
    break;
  case VK_DOWN:
    newFocused++;
    break;
  case VK_PRIOR:
    if (newFocused > lphl->ItemsVisible) {
      newFocused -= lphl->ItemsVisible;
    } else {
      newFocused = 0;
    }
    break;
  case VK_NEXT:
    newFocused += lphl->ItemsVisible;
    break;
  default:
    return 0;
  }

  if (newFocused >= lphl->ItemsCount)
    newFocused = lphl->ItemsCount - 1;
  
  ListBoxSetCurSel(lphl, newFocused);
  ListBoxSendNotification(lphl, CBN_SELCHANGE);
  SendMessage16(GetParent(hwnd), WM_COMMAND,ID_CLB,MAKELONG(0,CBN_SELCHANGE));
  lphl->ItemFocused = newFocused;
  ListBoxScrollToFocus(lphl);
  SetScrollPos(hwnd, SB_VERT, lphl->FirstVisible, TRUE);
  InvalidateRect32( hwnd, NULL, TRUE );
  return 0;
}

/***********************************************************************
 *           CBLChar
 */
static LRESULT CBLChar( HWND hwnd, WPARAM wParam, LPARAM lParam )
{
  return 0;
}

/***********************************************************************
 *           CBLPaint
 */
static LRESULT CBLPaint( HWND hwnd, WPARAM wParam, LPARAM lParam )
{
  LPHEADLIST   lphl = CLBoxGetListHeader(hwnd);
  LPLISTSTRUCT lpls;
  PAINTSTRUCT16  ps;
  HBRUSH       hBrush;
  HFONT        hOldFont;
  WND * wndPtr = WIN_FindWndPtr(hwnd);
  HWND  combohwnd = CLBoxGetCombo(hwnd);
  HDC16 hdc;
  RECT16 rect;
  int   i, top, height;

  top = 0;
  hdc = BeginPaint16( hwnd, &ps );

  if (!IsWindowVisible(hwnd) || !lphl->bRedrawFlag) {
    EndPaint16(hwnd, &ps);
    return 0;
  }

  hOldFont = SelectObject(hdc, lphl->hFont);
  /* listboxes should be white */
  hBrush = GetStockObject(WHITE_BRUSH);

  GetClientRect16(hwnd, &rect);
  FillRect16(hdc, &rect, hBrush);
  CBLCheckSize(hwnd);

  lpls = lphl->lpFirst;

  lphl->ItemsVisible = 0;
  for(i = 0; i < lphl->ItemsCount; i++) {
    if (lpls == NULL) break;

    if (i >= lphl->FirstVisible) {
      height = lpls->mis.itemHeight;
      /* must have enough room to draw entire item */
      if (top > (rect.bottom-height+1)) break;

      lpls->itemRect.top    = top;
      lpls->itemRect.bottom = top + height;
      lpls->itemRect.left   = rect.left;
      lpls->itemRect.right  = rect.right;

      dprintf_listbox(stddeb,"drawing item: %d %d %d %d %d\n",
                      rect.left,top,rect.right,top+height,lpls->itemState);
      if (lphl->OwnerDrawn) {
	ListBoxDrawItem (combohwnd, lphl, hdc, lpls, &lpls->itemRect, ODA_DRAWENTIRE, 0);
	if (lpls->itemState)
	  ListBoxDrawItem (combohwnd, lphl, hdc, lpls, &lpls->itemRect, ODA_SELECT, ODS_SELECTED);
      } else {
	ListBoxDrawItem (combohwnd, lphl, hdc, lpls, &lpls->itemRect, ODA_DRAWENTIRE, 
			 lpls->itemState);
      }
      if ((lphl->ItemFocused == i) && GetFocus() == hwnd)
	ListBoxDrawItem (combohwnd, lphl, hdc, lpls, &lpls->itemRect, ODA_FOCUS, ODS_FOCUS);

      top += height;
      lphl->ItemsVisible++;
    }

    lpls = lpls->lpNext;
  }

  if (wndPtr->dwStyle & WS_VSCROLL) 
      SetScrollRange(hwnd, SB_VERT, 0, ListMaxFirstVisible(lphl), TRUE);

  SelectObject(hdc,hOldFont);
  EndPaint16( hwnd, &ps );
  return 0;

}

/***********************************************************************
 *           CBLKillFocus
 */
static LRESULT CBLKillFocus( HWND hwnd, WPARAM wParam, LPARAM lParam )
{
/*  SendMessage16(CLBoxGetCombo(hwnd),CB_SHOWDROPDOWN,0,0);*/
  return 0;
}

/***********************************************************************
 *           CBLActivate
 */
static LRESULT CBLActivate( HWND hwnd, WPARAM wParam, LPARAM lParam )
{
  if (wParam == WA_INACTIVE)
    SendMessage16(CLBoxGetCombo(hwnd),CB_SHOWDROPDOWN,0,0);
  return 0;
}

/***********************************************************************
 *           CBLLButtonDown
 */
static LRESULT CBLLButtonDown( HWND hwnd, WPARAM wParam, LPARAM lParam )
{
  LPHEADLIST lphl = CLBoxGetListHeader(hwnd);
  int        y;
  RECT16     rectsel;

  SetFocus(hwnd);
  SetCapture(hwnd);

  lphl->PrevFocused = lphl->ItemFocused;

  y = ListBoxFindMouse(lphl, LOWORD(lParam), HIWORD(lParam));
  if (y == -1)
    return 0;

  ListBoxSetCurSel(lphl, y);
  ListBoxGetItemRect(lphl, y, &rectsel);

  InvalidateRect32( hwnd, NULL, TRUE );
  return 0;
}

/***********************************************************************
 *           CBLLButtonUp
 */
static LRESULT CBLLButtonUp( HWND hwnd, WPARAM wParam, LPARAM lParam )
{
  LPHEADLIST lphl = CLBoxGetListHeader(hwnd);

  if (GetCapture() == hwnd) ReleaseCapture();

  if(!lphl)
     {
      fprintf(stdnimp,"CBLLButtonUp: CLBoxGetListHeader returned NULL!\n");
     }
  else if (lphl->PrevFocused != lphl->ItemFocused) 
          {
      		SendMessage16(CLBoxGetCombo(hwnd),CB_SETCURSEL,lphl->ItemFocused,0);
      		SendMessage16(GetParent(hwnd), WM_COMMAND,ID_CLB,MAKELONG(0,CBN_SELCHANGE));
      		ListBoxSendNotification(lphl, CBN_SELCHANGE);
     	  }

  SendMessage16(CLBoxGetCombo(hwnd),CB_SHOWDROPDOWN,0,0);

  return 0;
}

/***********************************************************************
 *           CBLMouseMove
 */
static LRESULT CBLMouseMove( HWND hwnd, WPARAM wParam, LPARAM lParam )
{
  LPHEADLIST lphl = CLBoxGetListHeader(hwnd);
  short y;
  WORD wRet;
  RECT16 rect, rectsel;

  y = SHIWORD(lParam);
  wRet = ListBoxFindMouse(lphl, LOWORD(lParam), HIWORD(lParam));
  ListBoxGetItemRect(lphl, wRet, &rectsel);
  GetClientRect16(hwnd, &rect);

  dprintf_combo(stddeb,"CBLMouseMove: hwnd %04x wp %x lp %lx  y %d  if %d wret %d %d,%d-%d,%d\n",
hwnd,wParam,lParam,y,lphl->ItemFocused,wRet,rectsel.left,rectsel.top,rectsel.right,rectsel.bottom);
  
  if ((wParam & MK_LBUTTON) != 0) {
    if (y < CBLMM_EDGE) {
      if (lphl->FirstVisible > 0) {
	lphl->FirstVisible--;
	SetScrollPos(hwnd, SB_VERT, lphl->FirstVisible, TRUE);
	ListBoxSetCurSel(lphl, wRet);
	InvalidateRect32( hwnd, NULL, TRUE );
	return 0;
      }
    }
    else if (y >= (rect.bottom-CBLMM_EDGE)) {
      if (lphl->FirstVisible < ListMaxFirstVisible(lphl)) {
	lphl->FirstVisible++;
	SetScrollPos(hwnd, SB_VERT, lphl->FirstVisible, TRUE);
	ListBoxSetCurSel(lphl, wRet);
	InvalidateRect32( hwnd, NULL, TRUE );
	return 0;
      }
    }
    else {
      if ((short) wRet == lphl->ItemFocused) return 0;
      ListBoxSetCurSel(lphl, wRet);
      InvalidateRect32( hwnd, NULL, TRUE );
    }
  }

  return 0;
}

/***********************************************************************
 *           CBLVScroll
 */
static LRESULT CBLVScroll( HWND hwnd, WPARAM wParam, LPARAM lParam )
{
  LPHEADLIST lphl = CLBoxGetListHeader(hwnd);
  int  y;

  y = lphl->FirstVisible;

  switch(wParam) {
  case SB_LINEUP:
    if (lphl->FirstVisible > 0)
      lphl->FirstVisible--;
    break;

  case SB_LINEDOWN:
    lphl->FirstVisible++;
    break;

  case SB_PAGEUP:
    if (lphl->FirstVisible > lphl->ItemsVisible) {
      lphl->FirstVisible -= lphl->ItemsVisible;
    } else {
      lphl->FirstVisible = 0;
    }
    break;

  case SB_PAGEDOWN:
    lphl->FirstVisible += lphl->ItemsVisible;
    break;

  case SB_THUMBTRACK:
    lphl->FirstVisible = LOWORD(lParam);
    break;
  }

  if (lphl->FirstVisible > ListMaxFirstVisible(lphl))
    lphl->FirstVisible = ListMaxFirstVisible(lphl);

  if (y != lphl->FirstVisible) {
    SetScrollPos(hwnd, SB_VERT, lphl->FirstVisible, TRUE);
    InvalidateRect32( hwnd, NULL, TRUE );
  }

  return 0;
}


/***********************************************************************
 *             CBLCheckSize
 */
static BOOL CBLCheckSize(HWND hwnd)
{
  LPHEADCOMBO  lphc = ComboGetStorageHeader(hwnd);
  LPHEADLIST   lphl = ComboGetListHeader(hwnd);
  LPLISTSTRUCT lpls;
  HWND         hWndLBox;
  RECT16 cRect,wRect,lRect,lwRect;
  int totheight,dw;
  char className[80];

  GetClassName32A(hwnd,className,80);
  fflush(stddeb);
  if (strncmp(className,"COMBOBOX",8)) return FALSE;
  if ((hWndLBox = lphc->hWndLBox) == 0) return FALSE;
  dprintf_combo(stddeb,"CBLCheckSize headers hw %04x  lb %04x  name %s\n",
		hwnd,hWndLBox,className);

  GetClientRect16(hwnd,&cRect);
  GetWindowRect16(hwnd,&wRect);
  GetClientRect16(hWndLBox,&lRect);
  GetWindowRect16(hWndLBox,&lwRect);

  dprintf_combo(stddeb,"CBLCheckSize: init cRect %d,%d-%d,%d  wRect %d,%d-%d,%d\n",
		cRect.left,cRect.top,cRect.right,cRect.bottom,
		wRect.left,wRect.top,wRect.right,wRect.bottom);
  dprintf_combo(stddeb,"                   lRect %d,%d-%d,%d  lwRect %d,%d-%d,%d\n",
	      lRect.left,lRect.top,lRect.right,lRect.bottom,
	      lwRect.left,lwRect.top,lwRect.right,lwRect.bottom);
  fflush(stddeb);
  
  totheight = 0;
  for (lpls=lphl->lpFirst; lpls != NULL; lpls=lpls->lpNext)
    totheight += lpls->mis.itemHeight;

  dw = cRect.right-cRect.left+2*SYSMETRICS_CXBORDER+SYSMETRICS_CXVSCROLL;
  dw -= lwRect.right-lwRect.left;
  dw -= SYSMETRICS_CXVSCROLL;

  /* TODO: This isn't really what windows does */
  if ((lRect.bottom-lRect.top < 3*lphl->StdItemHeight) || dw) {
    dprintf_combo(stddeb,"    Changing; totHeight %d  StdItemHght %d  dw %d\n",
		  totheight,lphl->StdItemHeight,dw);
    SetWindowPos(hWndLBox, 0, lRect.left, lRect.top, 
		 lwRect.right-lwRect.left+dw, totheight+2*SYSMETRICS_CYBORDER, 
		 SWP_NOMOVE | SWP_NOZORDER | SWP_NOREDRAW | SWP_NOACTIVATE );
  }
  return TRUE;
}


/***********************************************************************
 *           ComboLBoxWndProc
 */
LRESULT ComboLBoxWndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
{
    switch(message) {	
     case WM_CREATE: return CBLCreate(hwnd, wParam, lParam);
     case WM_GETDLGCODE: return CBLGetDlgCode(hwnd, wParam, lParam);
     case WM_KEYDOWN: return CBLKeyDown(hwnd, wParam, lParam);
     case WM_CHAR: return CBLChar(hwnd, wParam, lParam);
     case WM_PAINT: return CBLPaint(hwnd, wParam, lParam);
     case WM_KILLFOCUS: return CBLKillFocus(hwnd, wParam, lParam);
     case WM_ACTIVATE: return CBLActivate(hwnd, wParam, lParam);
     case WM_LBUTTONDOWN: return CBLLButtonDown(hwnd, wParam, lParam);
     case WM_LBUTTONUP: return CBLLButtonUp(hwnd, wParam, lParam);
     case WM_MOUSEMOVE: return CBLMouseMove(hwnd, wParam, lParam);
     case WM_VSCROLL: return CBLVScroll(hwnd, wParam, lParam);
     case WM_SIZE: return CBLCheckSize(hwnd);
    }
    return DefWindowProc16(hwnd, message, wParam, lParam);
}

/************************************************************************
 * 			       	DlgDirSelectComboBox	[USER.194]
 */
BOOL DlgDirSelectComboBox(HWND hDlg, LPSTR lpStr, INT nIDLBox)
{
	fprintf(stdnimp,"DlgDirSelectComboBox(%04x, '%s', %d) \n",
				hDlg, lpStr, nIDLBox);
	return TRUE;
}

static INT32 COMBO_DlgDirList( HWND32 hDlg, LPARAM path, INT32 idCBox,
                               INT32 idStatic, UINT32 wType, BOOL32 unicode )
{
    LRESULT res = 0;

    if (idCBox)
    {
        SendDlgItemMessage32A( hDlg, idCBox, CB_RESETCONTENT, 0, 0 );
        if (unicode)
            res = SendDlgItemMessage32W( hDlg, idCBox, CB_DIR, wType, path );
        else
            res = SendDlgItemMessage32A( hDlg, idCBox, CB_DIR, wType, path );
    }
    if (idStatic)
    {
        char temp[512] = "A:\\";
        int drive = DRIVE_GetCurrentDrive();
        temp[0] += drive;
        lstrcpyn32A( temp + 3, DRIVE_GetDosCwd(drive), sizeof(temp)-3 );
        AnsiLower( temp );
        SetDlgItemText32A( hDlg, idStatic, temp );
    } 
    return (res >= 0);
}


/***********************************************************************
 *           DlgDirListComboBox16   (USER.195)
 */
INT16 DlgDirListComboBox16( HWND16 hDlg, LPCSTR path, INT16 idCBox,
                            INT16 idStatic, UINT16 wType )
{
    dprintf_combo( stddeb,"DlgDirListComboBox16(%04x,'%s',%d,%d,%04x)\n",
                   hDlg, path, idCBox, idStatic, wType );
    return COMBO_DlgDirList( hDlg, (LPARAM)path, idCBox,
                             idStatic, wType, FALSE );
}


/***********************************************************************
 *           DlgDirListComboBox32A   (USER32.143)
 */
INT32 DlgDirListComboBox32A( HWND32 hDlg, LPCSTR path, INT32 idCBox,
                             INT32 idStatic, UINT32 wType )
{
    dprintf_combo( stddeb,"DlgDirListComboBox32A(%08x,'%s',%d,%d,%08X)\n",
                   hDlg, path, idCBox, idStatic, wType );
    return COMBO_DlgDirList( hDlg, (LPARAM)path, idCBox,
                             idStatic, wType, FALSE );
}


/***********************************************************************
 *           DlgDirListComboBox32W   (USER32.144)
 */
INT32 DlgDirListComboBox32W( HWND32 hDlg, LPCWSTR path, INT32 idCBox,
                             INT32 idStatic, UINT32 wType )
{
    dprintf_combo( stddeb,"DlgDirListComboBox32W(%08x,%p,%d,%d,%08X)\n",
                   hDlg, path, idCBox, idStatic, wType );
    return COMBO_DlgDirList( hDlg, (LPARAM)path, idCBox,
                             idStatic, wType, TRUE );
}
