/*
 * Interface code to listbox widgets
 *
 * Copyright  Martin Ayotte, 1993
 *
 */


static char Copyright[] = "Copyright Martin Ayotte, 1993";

#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include "windows.h"
#include "user.h"
#include "heap.h"
#include "win.h"
#include "msdos.h"
#include "wine.h"
#include "listbox.h"
#include "scroll.h"
#include "prototypes.h"
#include "stddebug.h"
/* #define DEBUG_LISTBOX */
/* #undef  DEBUG_LISTBOX */
#include "debug.h"

#define GMEM_ZEROINIT 0x0040


LPHEADLIST ListBoxGetWindowAndStorage(HWND hwnd, WND **wndPtr);
LPHEADLIST ListBoxGetStorageHeader(HWND hwnd);
void StdDrawListBox(HWND hwnd);
void OwnerDrawListBox(HWND hwnd);
int ListBoxFindMouse(HWND hwnd, int X, int Y);
int CreateListBoxStruct(HWND hwnd);
void ListBoxAskMeasure(WND *wndPtr, LPHEADLIST lphl, LPLISTSTRUCT lpls);
int ListBoxAddString(HWND hwnd, LPSTR newstr);
int ListBoxInsertString(HWND hwnd, UINT uIndex, LPSTR newstr);
int ListBoxGetText(HWND hwnd, UINT uIndex, LPSTR OutStr, BOOL bItemData);
int ListBoxSetItemData(HWND hwnd, UINT uIndex, DWORD ItemData);
int ListBoxDeleteString(HWND hwnd, UINT uIndex);
int ListBoxFindString(HWND hwnd, UINT nFirst, LPSTR MatchStr);
int ListBoxResetContent(HWND hwnd);
int ListBoxSetCurSel(HWND hwnd, WORD wIndex);
int ListBoxSetSel(HWND hwnd, WORD wIndex, WORD state);
int ListBoxGetSel(HWND hwnd, WORD wIndex);
int ListBoxDirectory(HWND hwnd, UINT attrib, LPSTR filespec);
int ListBoxGetItemRect(HWND hwnd, WORD wIndex, LPRECT rect);
int ListBoxSetItemHeight(HWND hwnd, WORD wIndex, long height);
int ListBoxDefaultItem(HWND hwnd, WND *wndPtr, 
	LPHEADLIST lphl, LPLISTSTRUCT lpls);
int ListBoxFindNextMatch(HWND hwnd, WORD wChar);

#define HasStrings(wndPtr) ( \
  ( ((wndPtr->dwStyle & LBS_OWNERDRAWFIXED) != LBS_OWNERDRAWFIXED) && \
    ((wndPtr->dwStyle & LBS_OWNERDRAWVARIABLE) != LBS_OWNERDRAWVARIABLE) ) || \
  ((wndPtr->dwStyle & LBS_HASSTRINGS) == LBS_HASSTRINGS) )

#define HasStrings(wndPtr) ( \
	( ((wndPtr->dwStyle & LBS_OWNERDRAWFIXED) != LBS_OWNERDRAWFIXED) && \
	  ((wndPtr->dwStyle & LBS_OWNERDRAWVARIABLE) != LBS_OWNERDRAWVARIABLE) ) || \
	  ((wndPtr->dwStyle & LBS_HASSTRINGS) == LBS_HASSTRINGS) )


/***********************************************************************
 *           ListBoxWndProc 
 */
LONG ListBoxWndProc( HWND hwnd, WORD message, WORD wParam, LONG lParam )
{    
	WND  *wndPtr;
	LPHEADLIST  lphl;
	HWND	hWndCtl;
	WORD	wRet;
	LONG	lRet;
	RECT	rect;
	int		y;
	CREATESTRUCT *createStruct;
	static RECT rectsel;
    switch(message) {
	case WM_CREATE:
		CreateListBoxStruct(hwnd);
		lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
		dprintf_listbox(stddeb,"ListBox WM_CREATE %p !\n", lphl);
		if (lphl == NULL) return 0;
		createStruct = (CREATESTRUCT *)lParam;
		if (HIWORD(createStruct->lpCreateParams) != 0)
			lphl->hWndLogicParent = (HWND)HIWORD(createStruct->lpCreateParams);
		else
			lphl->hWndLogicParent = GetParent(hwnd);
		lphl->hFont = GetStockObject(SYSTEM_FONT);
		lphl->ColumnsWidth = wndPtr->rectClient.right - wndPtr->rectClient.left;
		if (wndPtr->dwStyle & WS_VSCROLL) {
			SetScrollRange(hwnd, SB_VERT, 1, lphl->ItemsCount, TRUE);
			ShowScrollBar(hwnd, SB_VERT, FALSE);
			}
		if (wndPtr->dwStyle & WS_HSCROLL) {
			SetScrollRange(hwnd, SB_HORZ, 1, 1, TRUE);
			ShowScrollBar(hwnd, SB_HORZ, FALSE);
			}
		if ((wndPtr->dwStyle & LBS_OWNERDRAWFIXED) == LBS_OWNERDRAWFIXED) {
			}
		return 0;
	case WM_DESTROY:
		lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
		if (lphl == NULL) return 0;
		ListBoxResetContent(hwnd);
		free(lphl);
		*((LPHEADLIST *)&wndPtr->wExtra[1]) = 0;
		dprintf_listbox(stddeb,"ListBox WM_DESTROY %p !\n", lphl);
		return 0;

	case WM_VSCROLL:
		dprintf_listbox(stddeb,"ListBox WM_VSCROLL w=%04X l=%08lX !\n",
				wParam, lParam);
		lphl = ListBoxGetStorageHeader(hwnd);
		if (lphl == NULL) return 0;
		y = lphl->FirstVisible;
		switch(wParam) {
			case SB_LINEUP:
				if (lphl->FirstVisible > 1)	
					lphl->FirstVisible--;
				break;
			case SB_LINEDOWN:
				if (lphl->FirstVisible < lphl->ItemsCount)
					lphl->FirstVisible++;
				break;
			case SB_PAGEUP:
				if (lphl->FirstVisible > 1)  
					lphl->FirstVisible -= lphl->ItemsVisible;
				break;
			case SB_PAGEDOWN:
				if (lphl->FirstVisible < lphl->ItemsCount)  
					lphl->FirstVisible += lphl->ItemsVisible;
				break;
			case SB_THUMBTRACK:
				lphl->FirstVisible = LOWORD(lParam);
				break;
			}
		if (lphl->FirstVisible < 1)    lphl->FirstVisible = 1;
		if (lphl->FirstVisible > lphl->ItemsCount)
			lphl->FirstVisible = lphl->ItemsCount;
		if (y != lphl->FirstVisible) {
			SetScrollPos(hwnd, SB_VERT, lphl->FirstVisible, TRUE);
			InvalidateRect(hwnd, NULL, TRUE);
			UpdateWindow(hwnd);
			}
		return 0;
	
	case WM_HSCROLL:
		dprintf_listbox(stddeb,"ListBox WM_HSCROLL w=%04X l=%08lX !\n",
				wParam, lParam);
		lphl = ListBoxGetStorageHeader(hwnd);
		if (lphl == NULL) return 0;
		y = lphl->FirstVisible;
		switch(wParam) {
			case SB_LINEUP:
				if (lphl->FirstVisible > 1)
					lphl->FirstVisible -= lphl->ItemsPerColumn;
				break;
			case SB_LINEDOWN:
				if (lphl->FirstVisible < lphl->ItemsCount)
					lphl->FirstVisible += lphl->ItemsPerColumn;
				break;
			case SB_PAGEUP:
				if (lphl->FirstVisible > 1 && lphl->ItemsPerColumn != 0)  
					lphl->FirstVisible -= lphl->ItemsVisible /
					lphl->ItemsPerColumn * lphl->ItemsPerColumn;
				break;
			case SB_PAGEDOWN:
				if (lphl->FirstVisible < lphl->ItemsCount &&
							lphl->ItemsPerColumn != 0)  
					lphl->FirstVisible += lphl->ItemsVisible /
					lphl->ItemsPerColumn * lphl->ItemsPerColumn;
				break;
			case SB_THUMBTRACK:
				lphl->FirstVisible = lphl->ItemsPerColumn * 
								(LOWORD(lParam) - 1) + 1;
				break;
			}
		if (lphl->FirstVisible < 1)    lphl->FirstVisible = 1;
		if (lphl->FirstVisible > lphl->ItemsCount)
			lphl->FirstVisible = lphl->ItemsCount;
		if (lphl->ItemsPerColumn != 0) {
			lphl->FirstVisible = lphl->FirstVisible /
				lphl->ItemsPerColumn * lphl->ItemsPerColumn + 1;
			if (y != lphl->FirstVisible) {
				SetScrollPos(hwnd, SB_HORZ, lphl->FirstVisible / 
				lphl->ItemsPerColumn + 1, TRUE);
				InvalidateRect(hwnd, NULL, TRUE);
				UpdateWindow(hwnd);
				}
			}
		return 0;
	
	case WM_LBUTTONDOWN:
		SetFocus(hwnd);
		SetCapture(hwnd);
		lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
		if (lphl == NULL) return 0;
		lphl->PrevFocused = lphl->ItemFocused;
	        y = ListBoxFindMouse(hwnd, LOWORD(lParam), HIWORD(lParam));
		if (y==-1)
		    return 0;
		if ((wndPtr->dwStyle & LBS_MULTIPLESEL) == LBS_MULTIPLESEL) {
		    lphl->ItemFocused = y;
		    wRet = ListBoxGetSel(hwnd, y);
		    ListBoxSetSel(hwnd, y, !wRet);
		    }
		else {
		    ListBoxSetCurSel(hwnd, y);
		    if ((wndPtr->dwStyle && LBS_NOTIFY) != 0)
				SendMessage(lphl->hWndLogicParent, WM_COMMAND, 
	    	    wndPtr->wIDmenu, MAKELONG(hwnd, LBN_SELCHANGE));
		    }
		ListBoxGetItemRect(hwnd, y, &rectsel);
		InvalidateRect(hwnd, NULL, TRUE);
		UpdateWindow(hwnd);
		return 0;
	case WM_LBUTTONUP:
		ReleaseCapture();
		lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
		if (lphl == NULL) return 0;
		if (lphl->PrevFocused != lphl->ItemFocused)
			SendMessage(lphl->hWndLogicParent, WM_COMMAND, wndPtr->wIDmenu,
											MAKELONG(hwnd, LBN_SELCHANGE));
		return 0;
	case WM_RBUTTONUP:
	case WM_LBUTTONDBLCLK:
		lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
		if (lphl == NULL) return 0;
		SendMessage(lphl->hWndLogicParent, WM_COMMAND, wndPtr->wIDmenu,
										MAKELONG(hwnd, LBN_DBLCLK));
		return 0;
	case WM_MOUSEMOVE:
		lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
		if (lphl == NULL) return 0;
		if ((wParam & MK_LBUTTON) != 0) {
			y = HIWORD(lParam);
			if (y < 4) {
				if (lphl->FirstVisible > 1) {
					lphl->FirstVisible--;
					if (wndPtr->dwStyle & WS_VSCROLL)
					SetScrollPos(hwnd, SB_VERT, lphl->FirstVisible, TRUE);
					InvalidateRect(hwnd, NULL, TRUE);
					UpdateWindow(hwnd);
					break;
					}
				}
			GetClientRect(hwnd, &rect);
			if (y > (rect.bottom - 4)) {
				if (lphl->FirstVisible < lphl->ItemsCount) {
					lphl->FirstVisible++;
					if (wndPtr->dwStyle & WS_VSCROLL)
					SetScrollPos(hwnd, SB_VERT, lphl->FirstVisible, TRUE);
					InvalidateRect(hwnd, NULL, TRUE);
					UpdateWindow(hwnd);
					break;
					}
				}
			if ((y > 0) && (y < (rect.bottom - 4))) {
				if ((y < rectsel.top) || (y > rectsel.bottom)) {
					wRet = ListBoxFindMouse(hwnd, LOWORD(lParam), HIWORD(lParam));
					if ((wndPtr->dwStyle & LBS_MULTIPLESEL) == LBS_MULTIPLESEL) {
						lphl->ItemFocused = wRet;
						}
					else {
						ListBoxSetCurSel(hwnd, wRet);
					    if ((wndPtr->dwStyle && LBS_NOTIFY) != 0)
							SendMessage(lphl->hWndLogicParent, WM_COMMAND, 
				    	    wndPtr->wIDmenu, MAKELONG(hwnd, LBN_SELCHANGE));
						}
					ListBoxGetItemRect(hwnd, wRet, &rectsel);
					InvalidateRect(hwnd, NULL, TRUE);
					UpdateWindow(hwnd);
					}
				}
			}
		break;
	case WM_KEYDOWN:
		lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
		if (lphl == NULL) return 0;
		switch(wParam) {
			case VK_TAB:
				hWndCtl = GetNextDlgTabItem(lphl->hWndLogicParent,
					hwnd, !(GetKeyState(VK_SHIFT) < 0));
				SetFocus(hWndCtl);
#ifdef DEBUG_LISTBOX
				if ((GetKeyState(VK_SHIFT) < 0))
					dprintf_listbox(stddeb,"ListBox PreviousDlgTabItem %04X !\n", hWndCtl);
				else
					dprintf_listbox(stddeb,"ListBox NextDlgTabItem %04X !\n", hWndCtl);
#endif
				break;
			case VK_HOME:
				lphl->ItemFocused = 0;
				break;
			case VK_END:
				lphl->ItemFocused = lphl->ItemsCount - 1;
				break;
			case VK_LEFT:
				if ((wndPtr->dwStyle & LBS_MULTICOLUMN) == LBS_MULTICOLUMN) {
					lphl->ItemFocused -= lphl->ItemsPerColumn;
					}
				break;
			case VK_UP:
				lphl->ItemFocused--;
				break;
			case VK_RIGHT:
				if ((wndPtr->dwStyle & LBS_MULTICOLUMN) == LBS_MULTICOLUMN) {
					lphl->ItemFocused += lphl->ItemsPerColumn;
					}
				break;
			case VK_DOWN:
				lphl->ItemFocused++;
				break;
			case VK_PRIOR:
				lphl->ItemFocused -= lphl->ItemsVisible;
				break;
			case VK_NEXT:
				lphl->ItemFocused += lphl->ItemsVisible;
				break;
			case VK_SPACE:
				wRet = ListBoxGetSel(hwnd, lphl->ItemFocused);
				ListBoxSetSel(hwnd, lphl->ItemFocused, !wRet);
				break;
			default:
				ListBoxFindNextMatch(hwnd, wParam);
				return 0;
			}
		if (lphl->ItemFocused < 0) lphl->ItemFocused = 0;
		if (lphl->ItemFocused >= lphl->ItemsCount)
			lphl->ItemFocused = lphl->ItemsCount - 1;
		lphl->FirstVisible = lphl->ItemFocused / lphl->ItemsVisible * 
											lphl->ItemsVisible + 1;
		if (lphl->FirstVisible < 1) lphl->FirstVisible = 1;
		if ((wndPtr->dwStyle & LBS_MULTIPLESEL) != LBS_MULTIPLESEL) {
			ListBoxSetCurSel(hwnd, lphl->ItemFocused);
		    if ((wndPtr->dwStyle && LBS_NOTIFY) != 0)
				SendMessage(lphl->hWndLogicParent, WM_COMMAND, 
	    	    wndPtr->wIDmenu, MAKELONG(hwnd, LBN_SELCHANGE));
			}
		if (wndPtr->dwStyle & WS_VSCROLL)
			SetScrollPos(hwnd, SB_VERT, lphl->FirstVisible, TRUE);
		InvalidateRect(hwnd, NULL, TRUE);
		UpdateWindow(hwnd);
		break;
	case WM_SETFONT:
		lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
		if (lphl == NULL) return 0;
		if (wParam == 0)
			lphl->hFont = GetStockObject(SYSTEM_FONT);
		else
			lphl->hFont = wParam;
		if (wParam == 0) break;
		break;
	case WM_SETREDRAW:
#ifdef DEBUG_LISTBOX
		printf("ListBox WM_SETREDRAW hWnd=%04X w=%04X !\n", hwnd, wParam);
#endif
		lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
		if (lphl == NULL) return 0;
		lphl->bRedrawFlag = wParam;
		break;
	case WM_PAINT:
		wndPtr = WIN_FindWndPtr(hwnd);
		if ((wndPtr->dwStyle & LBS_OWNERDRAWFIXED) == LBS_OWNERDRAWFIXED) {
			OwnerDrawListBox(hwnd);
			break;
			}
		if ((wndPtr->dwStyle & LBS_OWNERDRAWVARIABLE) == LBS_OWNERDRAWVARIABLE) {
			OwnerDrawListBox(hwnd);
			break;
			}
		StdDrawListBox(hwnd);
		break;
	case WM_SETFOCUS:
		dprintf_listbox(stddeb,"ListBox WM_SETFOCUS !\n");
		lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
		break;
	case WM_KILLFOCUS:
		dprintf_listbox(stddeb,"ListBox WM_KILLFOCUS !\n");
		InvalidateRect(hwnd, NULL, TRUE);
		UpdateWindow(hwnd);
		break;

    case LB_RESETCONTENT:
		dprintf_listbox(stddeb,"ListBox LB_RESETCONTENT !\n");
		ListBoxResetContent(hwnd);
		return 0;
    case LB_DIR:
		dprintf_listbox(stddeb,"ListBox LB_DIR !\n");
		wRet = ListBoxDirectory(hwnd, wParam, (LPSTR)lParam);
		InvalidateRect(hwnd, NULL, TRUE);
		UpdateWindow(hwnd);
		return wRet;
	case LB_ADDSTRING:
		wRet = ListBoxAddString(hwnd, (LPSTR)lParam);
		return wRet;
	case LB_GETTEXT:
		wRet = ListBoxGetText(hwnd, wParam, (LPSTR)lParam, FALSE);
                return wRet;
	case LB_INSERTSTRING:
		wRet = ListBoxInsertString(hwnd, wParam, (LPSTR)lParam);
		return wRet;
	case LB_DELETESTRING:
		wRet = ListBoxDeleteString(hwnd, wParam);
		return wRet;
	case LB_FINDSTRING:
		wRet = ListBoxFindString(hwnd, wParam, (LPSTR)lParam);
		return wRet;
	case LB_GETCARETINDEX:
		return wRet;
	case LB_GETCOUNT:
		lphl = ListBoxGetStorageHeader(hwnd);
		return lphl->ItemsCount;
	case LB_GETCURSEL:
		lphl = ListBoxGetStorageHeader(hwnd);
		dprintf_listbox(stddeb,"ListBox LB_GETCURSEL %u !\n", 
				lphl->ItemFocused);
		return lphl->ItemFocused;
	case LB_GETHORIZONTALEXTENT:
		return wRet;
	case LB_GETITEMDATA:
		lRet = ListBoxGetText(hwnd, wParam, (LPSTR)lParam, HasStrings(wndPtr));
		return lRet;
	case LB_GETITEMHEIGHT:
                ListBoxGetItemRect(hwnd, wParam, &rect);
                return (rect.bottom - rect.top);
	case LB_GETITEMRECT:
                ListBoxGetItemRect(hwnd, wParam, (LPRECT)lParam);
                return 0;
	case LB_GETSEL:
		wRet = ListBoxGetSel(hwnd, wParam);
		return wRet;
	case LB_GETSELCOUNT:
		lphl = ListBoxGetStorageHeader(hwnd);
		if (lphl == NULL) return LB_ERR;
		return lphl->SelCount;
	case LB_GETSELITEMS:
		return wRet;
	case LB_GETTEXTLEN:
		return wRet;
	case LB_GETTOPINDEX:
		lphl = ListBoxGetStorageHeader(hwnd);
		if (lphl == NULL) return LB_ERR;
		return lphl->FirstVisible;
	case LB_SELECTSTRING:
		return wRet;
	case LB_SELITEMRANGE:
		return wRet;
	case LB_SETCARETINDEX:
		return wRet;
	case LB_SETCOLUMNWIDTH:
		lphl = ListBoxGetStorageHeader(hwnd);
		if (lphl == NULL) return LB_ERR;
		lphl->ColumnsWidth = wParam;
		break;
	case LB_SETHORIZONTALEXTENT:
		return wRet;
	case LB_SETITEMDATA:
		wRet = ListBoxSetItemData(hwnd, wParam, lParam);
		return wRet;
	case LB_SETTABSTOPS:
		lphl = ListBoxGetStorageHeader(hwnd);
		if (lphl == NULL) return LB_ERR;
		lphl->FirstVisible = wParam;
		return 0;
	case LB_SETCURSEL:
		dprintf_listbox(stddeb,"ListBox LB_SETCURSEL wParam=%x !\n", 
				wParam);
		wRet = ListBoxSetCurSel(hwnd, wParam);
		InvalidateRect(hwnd, NULL, TRUE);
		UpdateWindow(hwnd);
		return wRet;
	case LB_SETSEL:
		dprintf_listbox(stddeb,"ListBox LB_SETSEL wParam=%x lParam=%lX !\n", wParam, lParam);
		wRet = ListBoxSetSel(hwnd, LOWORD(lParam), wParam);
		InvalidateRect(hwnd, NULL, TRUE);
		UpdateWindow(hwnd);
		return wRet;
	case LB_SETTOPINDEX:
		dprintf_listbox(stddeb,"ListBox LB_SETTOPINDEX wParam=%x !\n",
				wParam);
		lphl = ListBoxGetStorageHeader(hwnd);
		lphl->FirstVisible = wParam;
		wndPtr = WIN_FindWndPtr(hwnd);
		if (wndPtr->dwStyle & WS_VSCROLL)
		    SetScrollPos(hwnd, SB_VERT, lphl->FirstVisible, TRUE);
		InvalidateRect(hwnd, NULL, TRUE);
		UpdateWindow(hwnd);
		break;
	case LB_SETITEMHEIGHT:
		dprintf_listbox(stddeb,"ListBox LB_SETITEMHEIGHT wParam=%x lParam=%lX !\n", wParam, lParam);
		wRet = ListBoxSetItemHeight(hwnd, wParam, lParam);
		return wRet;

	default:
		return DefWindowProc( hwnd, message, wParam, lParam );
    }
return 0;
}


LPHEADLIST ListBoxGetWindowAndStorage(HWND hwnd, WND **wndPtr)
{
    WND  *Ptr;
    LPHEADLIST lphl;
    *(wndPtr) = Ptr = WIN_FindWndPtr(hwnd);
    lphl = *((LPHEADLIST *)&Ptr->wExtra[1]);
    return lphl;
}


LPHEADLIST ListBoxGetStorageHeader(HWND hwnd)
{
    WND  *wndPtr;
    LPHEADLIST lphl;
    wndPtr = WIN_FindWndPtr(hwnd);
    lphl = *((LPHEADLIST *)&wndPtr->wExtra[1]);
    return lphl;
}


void StdDrawListBox(HWND hwnd)
{
	WND 	*wndPtr;
	LPHEADLIST  lphl;
	LPLISTSTRUCT lpls;
	PAINTSTRUCT ps;
	HBRUSH 	hBrush;
	int 	OldBkMode;
	DWORD 	dwOldTextColor;
	HDC 	hdc;
	RECT 	rect;
	int     i, h, h2, maxwidth, ipc;
	h = 0;
	hdc = BeginPaint( hwnd, &ps );
	if (!IsWindowVisible(hwnd)) {
		EndPaint( hwnd, &ps );
		return;
		}
	lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
	if (lphl == NULL) goto EndOfPaint;
	if (!lphl->bRedrawFlag) goto EndOfPaint;
	SelectObject(hdc, lphl->hFont);
	hBrush = SendMessage(lphl->hWndLogicParent, WM_CTLCOLOR, (WORD)hdc,
		    MAKELONG(hwnd, CTLCOLOR_LISTBOX));
	if (hBrush == (HBRUSH)NULL)  hBrush = GetStockObject(WHITE_BRUSH);
	GetClientRect(hwnd, &rect);
/*
	if (wndPtr->dwStyle & WS_VSCROLL) rect.right -= 16;
	if (wndPtr->dwStyle & WS_HSCROLL) rect.bottom -= 16;
*/
	FillRect(hdc, &rect, hBrush);
	maxwidth = rect.right;
	rect.right = lphl->ColumnsWidth;
	if (lphl->ItemsCount == 0) goto EndOfPaint;
	lpls = lphl->lpFirst;
	if (lpls == NULL) goto EndOfPaint;
	lphl->ItemsVisible = 0;
	lphl->ItemsPerColumn = ipc = 0;
	for(i = 1; i <= lphl->ItemsCount; i++) {
	    if (i >= lphl->FirstVisible) {
	        if (lpls == NULL) break;
		if ((h + lpls->dis.rcItem.bottom - lpls->dis.rcItem.top) > rect.bottom) {
		    if ((wndPtr->dwStyle & LBS_MULTICOLUMN) == LBS_MULTICOLUMN) {
			lphl->ItemsPerColumn = max(lphl->ItemsPerColumn, ipc);
			ipc = 0;
			h = 0;
			rect.left += lphl->ColumnsWidth;
			rect.right += lphl->ColumnsWidth;
			if (rect.left > maxwidth) break;
			}
		    else 
			break;
		    }
		h2 = lpls->dis.rcItem.bottom - lpls->dis.rcItem.top;
		lpls->dis.rcItem.top = h;
		lpls->dis.rcItem.bottom = h + h2;
		lpls->dis.rcItem.left = rect.left;
		lpls->dis.rcItem.right = rect.right;
		OldBkMode = SetBkMode(hdc, TRANSPARENT);
		if (lpls->dis.itemState != 0) {
			dwOldTextColor = SetTextColor(hdc, 0x00FFFFFFL);
		    FillRect(hdc, &lpls->dis.rcItem, GetStockObject(BLACK_BRUSH));
		    }
		TextOut(hdc, rect.left + 5, h + 2, (char *)lpls->itemText, 
			strlen((char *)lpls->itemText));
		if (lpls->dis.itemState != 0) {
			SetTextColor(hdc, dwOldTextColor);
		    }
		SetBkMode(hdc, OldBkMode);
		if ((lphl->ItemFocused == i - 1) && GetFocus() == hwnd) {
		    DrawFocusRect(hdc, &lpls->dis.rcItem);
		    }
		h += h2;
		lphl->ItemsVisible++;
		ipc++;
		}
	    if (lpls->lpNext == NULL) goto EndOfPaint;
	    lpls = (LPLISTSTRUCT)lpls->lpNext;
	}
EndOfPaint:
    EndPaint( hwnd, &ps );
    if ((lphl->ItemsCount > lphl->ItemsVisible) &
	(wndPtr->dwStyle & WS_VSCROLL)) {
/*
        InvalidateRect(wndPtr->hWndVScroll, NULL, TRUE);
        UpdateWindow(wndPtr->hWndVScroll);
*/
 	}
}



void OwnerDrawListBox(HWND hwnd)
{
	WND 	*wndPtr,*ParentWndPtr;
	LPHEADLIST  lphl;
	LPLISTSTRUCT lpls;
	PAINTSTRUCT ps;
	HBRUSH 	hBrush;
	HWND	hWndParent;
	DWORD   itemData;
	HDC 	hdc;
	RECT 	rect;
	int     i, h, h2, maxwidth;
	h = 0;
	hdc = BeginPaint(hwnd, &ps);
	if (!IsWindowVisible(hwnd)) {
		EndPaint( hwnd, &ps );
		return;
		}
	lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
	if (lphl == NULL) goto EndOfPaint;
	if (!lphl->bRedrawFlag) goto EndOfPaint;
	hBrush = SendMessage(lphl->hWndLogicParent, WM_CTLCOLOR, (WORD)hdc,
		    MAKELONG(hwnd, CTLCOLOR_LISTBOX));
	if (hBrush == (HBRUSH)NULL)  hBrush = GetStockObject(WHITE_BRUSH);
	GetClientRect(hwnd, &rect);
	if (wndPtr->dwStyle & WS_VSCROLL) rect.right -= 16;
	if (wndPtr->dwStyle & WS_HSCROLL) rect.bottom -= 16;
	FillRect(hdc, &rect, hBrush);
	maxwidth = rect.right;
	rect.right = lphl->ColumnsWidth;
	if (lphl->ItemsCount == 0) goto EndOfPaint;
	lpls = lphl->lpFirst;
	if (lpls == NULL) goto EndOfPaint;
	lphl->ItemsVisible = 0;
	for (i = 1; i <= lphl->ItemsCount; i++) {
	    if (i >= lphl->FirstVisible) {
		lpls->dis.hDC = hdc;
		lpls->dis.hwndItem = hwnd;
		lpls->dis.CtlType = ODT_LISTBOX;
		lpls->dis.itemID = i - 1;
		if ((!lpls->dis.CtlID) && (lphl->hWndLogicParent)) {
			ParentWndPtr = WIN_FindWndPtr(lphl->hWndLogicParent);
			lpls->dis.CtlID = ParentWndPtr->wIDmenu;
			}
		h2 = lpls->dis.rcItem.bottom - lpls->dis.rcItem.top;
		lpls->dis.rcItem.top = h;
		lpls->dis.rcItem.bottom = h + h2;
		lpls->dis.rcItem.left = rect.left;
		lpls->dis.rcItem.right = rect.right;
		lpls->dis.itemAction = ODA_DRAWENTIRE;
/*		if (lpls->dis.itemState != 0) {
		    lpls->dis.itemAction |= ODA_SELECT;
		    }
		if (lphl->ItemFocused == i - 1) {
		    lpls->dis.itemAction |= ODA_FOCUS;
		    }*/
		dprintf_listbox(stddeb,"LBOX WM_DRAWITEM #%d left=%d top=%d right=%d bottom=%d !\n", 
			i-1, lpls->dis.rcItem.left, lpls->dis.rcItem.top, 
			lpls->dis.rcItem.right, lpls->dis.rcItem.bottom);
		dprintf_listbox(stddeb,"LBOX WM_DRAWITEM Parent=%X &dis=%lX CtlID=%u !\n", 
			hWndParent, (LONG)&lpls->dis, lpls->dis.CtlID);
		dprintf_listbox(stddeb,"LBOX WM_DRAWITEM %08lX!\n",lpls->dis.itemData);
		if (HasStrings(wndPtr))
		  dprintf_listbox(stddeb,"  '%s'\n",lpls->itemText);
		if (HasStrings(wndPtr)) {
			itemData = lpls->dis.itemData;
			lpls->dis.itemData = (DWORD)lpls->itemText;
			}
		SendMessage(lphl->hWndLogicParent, WM_DRAWITEM, 
							i-1, (LPARAM)&lpls->dis);
		if (HasStrings(wndPtr))
			lpls->dis.itemData = itemData;

/*		if (lpls->dis.itemState != 0) {
  		    InvertRect(hdc, &lpls->dis.rcItem);  
		    }  */
		h += h2;
		lphl->ItemsVisible++;
		/* if (h > rect.bottom) goto EndOfPaint;*/
		}
	    if (lpls->lpNext == NULL) goto EndOfPaint;
	    lpls = (LPLISTSTRUCT)lpls->lpNext;
	}
EndOfPaint:
    EndPaint( hwnd, &ps );
    if ((lphl->ItemsCount > lphl->ItemsVisible) &
		(wndPtr->dwStyle & WS_VSCROLL)) {
/*
        InvalidateRect(wndPtr->hWndVScroll, NULL, TRUE);
        UpdateWindow(wndPtr->hWndVScroll);
*/
        }

}



int ListBoxFindMouse(HWND hwnd, int X, int Y)
{
    WND 		*wndPtr;
    LPHEADLIST 		lphl;
    LPLISTSTRUCT	lpls;
    RECT 		rect;
    int                 i, h, h2, w, w2;
    lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
    if (lphl == NULL) return LB_ERR;
    if (lphl->ItemsCount == 0) return LB_ERR;
    lpls = lphl->lpFirst;
    if (lpls == NULL) return LB_ERR;
    GetClientRect(hwnd, &rect);
    if (wndPtr->dwStyle & WS_VSCROLL) rect.right -= 16;
    if (wndPtr->dwStyle & WS_HSCROLL) rect.bottom -= 16;
    h = w2 = 0;
    w = lphl->ColumnsWidth;
    for(i = 1; i <= lphl->ItemsCount; i++) {
	if (i >= lphl->FirstVisible) {
	    h2 = h;
	    h += lpls->dis.rcItem.bottom - lpls->dis.rcItem.top;
	    if ((Y > h2) && (Y < h) &&
		(X > w2) && (X < w)) return(i - 1);
	    if (h > rect.bottom) {
		if ((wndPtr->dwStyle & LBS_MULTICOLUMN) != LBS_MULTICOLUMN) return LB_ERR;
		h = 0;
		w2 = w;
		w += lphl->ColumnsWidth;
		if (w2 > rect.right) return LB_ERR;
		}
	    }
	if (lpls->lpNext == NULL) return LB_ERR;
	lpls = (LPLISTSTRUCT)lpls->lpNext;
	}
    return(LB_ERR);
}



int CreateListBoxStruct(HWND hwnd)
{
	WND  *wndPtr;
	LPHEADLIST lphl;
	wndPtr = WIN_FindWndPtr(hwnd);
	lphl = (LPHEADLIST)malloc(sizeof(HEADLIST));
	lphl->lpFirst = NULL;
	*((LPHEADLIST *)&wndPtr->wExtra[1]) = lphl;     /* HEAD of List */
	lphl->ItemsCount = 0;
	lphl->ItemsVisible = 0;
	lphl->FirstVisible = 1;
	lphl->ColumnsVisible = 1;
	lphl->ItemsPerColumn = 0;
	lphl->StdItemHeight = 15;
	lphl->ItemFocused = 0;
	lphl->PrevFocused = 0;
	lphl->SelCount = 0;
	lphl->DrawCtlType = ODT_LISTBOX;
	lphl->bRedrawFlag = TRUE;
	return TRUE;
}


void ListBoxAskMeasure(WND *wndPtr, LPHEADLIST lphl, LPLISTSTRUCT lpls)  
{
	MEASUREITEMSTRUCT 	*lpmeasure;
	HANDLE hTemp = USER_HEAP_ALLOC(GMEM_MOVEABLE, sizeof(MEASUREITEMSTRUCT));
	lpmeasure = (MEASUREITEMSTRUCT *) USER_HEAP_ADDR(hTemp);
	if (lpmeasure == NULL) {
		fprintf(stderr,"ListBoxAskMeasure() // Bad allocation of Measure struct !\n");
		return;
		}
	lpmeasure->CtlType = ODT_LISTBOX;
	lpmeasure->CtlID = wndPtr->wIDmenu;
	lpmeasure->itemID = lpls->dis.itemID;
	lpmeasure->itemWidth = wndPtr->rectWindow.right - wndPtr->rectWindow.left;
	lpmeasure->itemHeight = 0;
	if (HasStrings(wndPtr))
		lpmeasure->itemData = (DWORD)lpls->itemText;
	else
		lpmeasure->itemData = lpls->dis.itemData;
	SendMessage(lphl->hWndLogicParent, WM_MEASUREITEM, 0, (DWORD)lpmeasure);
	lpls->dis.rcItem.right = lpls->dis.rcItem.left + lpmeasure->itemWidth;
	lpls->dis.rcItem.bottom = lpls->dis.rcItem.top + lpmeasure->itemHeight;
	USER_HEAP_FREE(hTemp);			
}


int ListBoxAddString(HWND hwnd, LPSTR newstr)
{
    WND  	*wndPtr;
    LPHEADLIST 	lphl;
    LPLISTSTRUCT lpls, lplsnew;
    HANDLE 	hItem;
    HANDLE 	hStr;
    LPSTR 	str;
    lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
    if (lphl == NULL) return LB_ERR;
    hItem = USER_HEAP_ALLOC(GMEM_MOVEABLE, sizeof(LISTSTRUCT));
    lplsnew = (LPLISTSTRUCT) USER_HEAP_ADDR(hItem);
    if (lplsnew == NULL) {
		dprintf_listbox(stddeb,"ListBoxAddString() // Bad allocation of new item !\n");
		return LB_ERRSPACE;
		}
    lpls = lphl->lpFirst;
    if (lpls != NULL) {
	while(lpls->lpNext != NULL) {
	    lpls = (LPLISTSTRUCT)lpls->lpNext;
	    }
	lpls->lpNext = lplsnew;
 	}
    else
	lphl->lpFirst = lplsnew;
    lphl->ItemsCount++;
    dprintf_listbox(stddeb,"Items Count = %u\n", lphl->ItemsCount);
    hStr = 0;

	ListBoxDefaultItem(hwnd, wndPtr, lphl, lplsnew);
	if (HasStrings(wndPtr)) {
		hStr = USER_HEAP_ALLOC(GMEM_MOVEABLE, strlen(newstr) + 1);
		str = (LPSTR)USER_HEAP_ADDR(hStr);
		if (str == NULL) return LB_ERRSPACE;
		strcpy(str, newstr);
		newstr = str;
		lplsnew->itemText = str;
		dprintf_listbox(stddeb,"ListBoxAddString // LBS_HASSTRINGS after strcpy '%s'\n", str);
		}
    else {
		lplsnew->itemText = NULL;
		lplsnew->dis.itemData = (DWORD)newstr;
		}
	lplsnew->hMem = hItem;
	lplsnew->lpNext = NULL;
	lplsnew->dis.itemID = lphl->ItemsCount;
	lplsnew->hData = hStr;
	if (((wndPtr->dwStyle & LBS_OWNERDRAWVARIABLE) == LBS_OWNERDRAWVARIABLE) ||
		((wndPtr->dwStyle & LBS_OWNERDRAWFIXED) == LBS_OWNERDRAWFIXED))
		ListBoxAskMeasure(wndPtr, lphl, lplsnew);
	if (wndPtr->dwStyle & WS_VSCROLL)
		SetScrollRange(hwnd, SB_VERT, 1, lphl->ItemsCount, 
			(lphl->FirstVisible != 1 && lphl->bRedrawFlag));
	if ((wndPtr->dwStyle & WS_HSCROLL) && lphl->ItemsPerColumn != 0)
		SetScrollRange(hwnd, SB_HORZ, 1, 
			lphl->ItemsVisible / lphl->ItemsPerColumn + 1, 
			(lphl->FirstVisible != 1 && lphl->bRedrawFlag));
	if (lphl->FirstVisible >= (lphl->ItemsCount - lphl->ItemsVisible)) {
		InvalidateRect(hwnd, NULL, TRUE);
		UpdateWindow(hwnd);
		}
	if ((lphl->ItemsCount - lphl->FirstVisible) == lphl->ItemsVisible) {
		if (wndPtr->dwStyle & WS_VSCROLL)
			ShowScrollBar(hwnd, SB_VERT, TRUE);
		if (wndPtr->dwStyle & WS_HSCROLL)
			ShowScrollBar(hwnd, SB_HORZ, TRUE);
		}
    return (lphl->ItemsCount - 1);
}


int ListBoxInsertString(HWND hwnd, UINT uIndex, LPSTR newstr)
{
	WND  	*wndPtr;
	LPHEADLIST 	lphl;
	LPLISTSTRUCT lpls, lplsnew;
    HANDLE 	hItem;
    HANDLE 	hStr;
	LPSTR	str;
	UINT	Count;
	dprintf_listbox(stddeb,"ListBoxInsertString(%04X, %d, %p);\n", 
		    hwnd, uIndex, newstr);
	if (uIndex == (UINT)-1) return ListBoxAddString(hwnd, newstr);
	lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
	if (lphl == NULL) return LB_ERR;
	/* The following line will cause problems if the content of the */
	/* listbox is sorted by the listbox itself */
	if (uIndex == lphl->ItemsCount) return ListBoxAddString(hwnd, newstr);
	if (uIndex >= lphl->ItemsCount) return LB_ERR;
	lpls = lphl->lpFirst;
	if (lpls == NULL) return LB_ERR;
	if (uIndex > lphl->ItemsCount) return LB_ERR;
	for(Count = 1; Count < uIndex; Count++) {
		if (lpls->lpNext == NULL) return LB_ERR;
		lpls = (LPLISTSTRUCT)lpls->lpNext;
		}
	hItem = USER_HEAP_ALLOC(GMEM_MOVEABLE, sizeof(LISTSTRUCT));
	lplsnew = (LPLISTSTRUCT) USER_HEAP_ADDR(hItem);
    if (lplsnew == NULL) {
		printf("ListBoxInsertString() // Bad allocation of new item !\n");
		return LB_ERRSPACE;
		}
	ListBoxDefaultItem(hwnd, wndPtr, lphl, lplsnew);
	lplsnew->hMem = hItem;
	if (uIndex == 0) {
		lplsnew->lpNext = lphl->lpFirst;
		lphl->lpFirst = lplsnew;
		}
	else {
		lplsnew->lpNext = lpls->lpNext;
		lpls->lpNext = lplsnew;
		}
	lphl->ItemsCount++;
	hStr = 0;

	if (HasStrings(wndPtr)) {
		hStr = USER_HEAP_ALLOC(GMEM_MOVEABLE, strlen(newstr) + 1);
		str = (LPSTR)USER_HEAP_ADDR(hStr);
		if (str == NULL) return LB_ERRSPACE;
		strcpy(str, newstr);
		newstr = str;
		lplsnew->itemText = str;
		dprintf_listbox(stddeb,"ListBoxInsertString // LBS_HASSTRINGS after strcpy '%s'\n", str);
		}
	else {
		lplsnew->itemText = NULL;
		lplsnew->dis.itemData = (DWORD)newstr;
		}
	lplsnew->dis.itemID = lphl->ItemsCount;
	lplsnew->hData = hStr;
	if (((wndPtr->dwStyle & LBS_OWNERDRAWVARIABLE) == LBS_OWNERDRAWVARIABLE) ||
		((wndPtr->dwStyle & LBS_OWNERDRAWFIXED) == LBS_OWNERDRAWFIXED))
		ListBoxAskMeasure(wndPtr, lphl, lplsnew);
	if (wndPtr->dwStyle & WS_VSCROLL)
		SetScrollRange(hwnd, SB_VERT, 1, lphl->ItemsCount, 
						    (lphl->FirstVisible != 1));
	if ((wndPtr->dwStyle & WS_HSCROLL) && lphl->ItemsPerColumn != 0)
		SetScrollRange(hwnd, SB_HORZ, 1, lphl->ItemsVisible / 
			lphl->ItemsPerColumn + 1, (lphl->FirstVisible != 1));
	if (((lphl->ItemsCount - lphl->FirstVisible) == lphl->ItemsVisible) && 
		(lphl->ItemsVisible != 0)) {
		if (wndPtr->dwStyle & WS_VSCROLL) ShowScrollBar(hwnd, SB_VERT, TRUE);
		if (wndPtr->dwStyle & WS_HSCROLL) ShowScrollBar(hwnd, SB_HORZ, TRUE);
		}
	if ((lphl->FirstVisible <= uIndex) &&
		((lphl->FirstVisible + lphl->ItemsVisible) >= uIndex)) {
		InvalidateRect(hwnd, NULL, TRUE);
		UpdateWindow(hwnd);
		}
        dprintf_listbox(stddeb,"ListBoxInsertString // count=%d\n", lphl->ItemsCount);
/*	return lphl->ItemsCount; */
	return uIndex;
}


int ListBoxGetText(HWND hwnd, UINT uIndex, LPSTR OutStr, BOOL bItemData)
{
    WND  	*wndPtr;
    LPHEADLIST 	lphl;
    LPLISTSTRUCT lpls;
    UINT	Count;
    if (!bItemData)   	*OutStr=0;
    lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
    if (lphl == NULL) return LB_ERR;
    if (uIndex >= lphl->ItemsCount) return LB_ERR;
    lpls = lphl->lpFirst;
    if (lpls == NULL) return LB_ERR;
    if (uIndex > lphl->ItemsCount) return LB_ERR;
    for(Count = 0; Count < uIndex; Count++) {
	if (lpls->lpNext == NULL) return LB_ERR;
	lpls = (LPLISTSTRUCT)lpls->lpNext;
    }
    if (bItemData)
	return lpls->dis.itemData;
    if (!(HasStrings(wndPtr)) )
      {
	*((long *)OutStr) = lpls->dis.itemData;
	return 4;
      }
	
    strcpy(OutStr, lpls->itemText);
    return strlen(OutStr);
}

int ListBoxSetItemData(HWND hwnd, UINT uIndex, DWORD ItemData)
{
    WND         *wndPtr;
    LPHEADLIST  lphl;
    LPLISTSTRUCT lpls;
    UINT        Count;
    lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
    if (lphl == NULL) return LB_ERR;
    if (uIndex >= lphl->ItemsCount) return LB_ERR;
    lpls = lphl->lpFirst;
    if (lpls == NULL) return LB_ERR;
    if (uIndex > lphl->ItemsCount) return LB_ERR;
    for(Count = 0; Count < uIndex; Count++) {
        if (lpls->lpNext == NULL) return LB_ERR;
        lpls = (LPLISTSTRUCT)lpls->lpNext;
    }
    lpls->dis.itemData = ItemData;
    return 1;
}


int ListBoxDeleteString(HWND hwnd, UINT uIndex)
{
    WND  	*wndPtr;
    LPHEADLIST 	lphl;
    LPLISTSTRUCT lpls, lpls2;
    UINT	Count;
    lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
    if (lphl == NULL) return LB_ERR;
    if (uIndex >= lphl->ItemsCount) return LB_ERR;
    lpls = lphl->lpFirst;
    if (lpls == NULL) return LB_ERR;
    if (uIndex > lphl->ItemsCount) return LB_ERR;
    for(Count = 1; Count < uIndex; Count++) {
	if (lpls->lpNext == NULL) return LB_ERR;
	lpls2 = lpls;
	lpls = (LPLISTSTRUCT)lpls->lpNext;
    }
    lpls2->lpNext = (LPLISTSTRUCT)lpls->lpNext;
    lphl->ItemsCount--;
    if (lpls->hData != 0) USER_HEAP_FREE(lpls->hData);
    if (lpls->hMem != 0) USER_HEAP_FREE(lpls->hMem);
    if (wndPtr->dwStyle & WS_VSCROLL)
	SetScrollRange(hwnd, SB_VERT, 1, lphl->ItemsCount, TRUE);
    if ((wndPtr->dwStyle & WS_HSCROLL) && lphl->ItemsPerColumn != 0)
	SetScrollRange(hwnd, SB_HORZ, 1, lphl->ItemsVisible / 
	    lphl->ItemsPerColumn + 1, TRUE);
    if (lphl->ItemsCount < lphl->ItemsVisible) {
	if (wndPtr->dwStyle & WS_VSCROLL)
	    ShowScrollBar(hwnd, SB_VERT, FALSE);
	if (wndPtr->dwStyle & WS_HSCROLL)
	    ShowScrollBar(hwnd, SB_HORZ, FALSE);
	}
    if ((lphl->FirstVisible <= uIndex) &&
        ((lphl->FirstVisible + lphl->ItemsVisible) >= uIndex)) {
        InvalidateRect(hwnd, NULL, TRUE);
        UpdateWindow(hwnd);
        }
    return lphl->ItemsCount;
}


int ListBoxFindString(HWND hwnd, UINT nFirst, LPSTR MatchStr)
{
    WND          *wndPtr;
    LPHEADLIST 	lphl;
    LPLISTSTRUCT lpls;
    UINT	Count;
    lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
    if (lphl == NULL) return LB_ERR;
    if (nFirst > lphl->ItemsCount) return LB_ERR;
    lpls = lphl->lpFirst;
    if (lpls == NULL) return LB_ERR;
    Count = 0;
    while(lpls != NULL) {
      if (HasStrings(wndPtr))
	{
	  if (strcmp(lpls->itemText, MatchStr) == 0) return Count;
	}
      else
	{
	  if (lpls->dis.itemData == (DWORD)MatchStr) return Count;
	}
      lpls = (LPLISTSTRUCT)lpls->lpNext;
      Count++;
    }
    return LB_ERR;
}


int ListBoxResetContent(HWND hwnd)
{
    WND  *wndPtr;
    LPHEADLIST 	lphl;
    LPLISTSTRUCT lpls, lpls2;
    UINT	i;
    lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
    if (lphl == NULL) return LB_ERR;
    lpls = lphl->lpFirst;
    if (lpls == NULL) return LB_ERR;
    for(i = 0; i <= lphl->ItemsCount; i++) {
	lpls2 = lpls;
	lpls = (LPLISTSTRUCT)lpls->lpNext;
	if (i != 0) {
	    dprintf_listbox(stddeb,"ResetContent #%u\n", i);
	    if (lpls2->hData != 0 && lpls2->hData != lpls2->hMem)
		USER_HEAP_FREE(lpls2->hData);
	    if (lpls2->hMem != 0) USER_HEAP_FREE(lpls2->hMem);
	    }  
	if (lpls == NULL)  break;
    }
    lphl->lpFirst = NULL;
    lphl->FirstVisible = 1;
    lphl->ItemsCount = 0;
	lphl->ItemFocused = -1;
	lphl->PrevFocused = -1;
    if ((wndPtr->dwStyle && LBS_NOTIFY) != 0)
	SendMessage(lphl->hWndLogicParent, WM_COMMAND, 
    	    wndPtr->wIDmenu, MAKELONG(hwnd, LBN_SELCHANGE));
    if (wndPtr->dwStyle & WS_VSCROLL)
	SetScrollRange(hwnd, SB_VERT, 1, lphl->ItemsCount, TRUE);
    if ((wndPtr->dwStyle & WS_HSCROLL) && lphl->ItemsPerColumn != 0)
	SetScrollRange(hwnd, SB_HORZ, 1, lphl->ItemsVisible / 
	    lphl->ItemsPerColumn + 1, TRUE);
    if (wndPtr->dwStyle & WS_VSCROLL)
	ShowScrollBar(hwnd, SB_VERT, FALSE);
    if (wndPtr->dwStyle & WS_HSCROLL)
	ShowScrollBar(hwnd, SB_HORZ, FALSE);
    InvalidateRect(hwnd, NULL, TRUE);
    UpdateWindow(hwnd);
    return TRUE;
}


int ListBoxSetCurSel(HWND hwnd, WORD wIndex)
{
    WND  *wndPtr;
    LPHEADLIST 	lphl;
    LPLISTSTRUCT lpls, lpls2;
    UINT	i;
    lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
    if (lphl == NULL) return LB_ERR;
    lphl->ItemFocused = LB_ERR; 
    if (wIndex >= lphl->ItemsCount) return LB_ERR;
    lpls = lphl->lpFirst;
    if (lpls == NULL) return LB_ERR;
    for(i = 0; i < lphl->ItemsCount; i++) {
	lpls2 = lpls;
	lpls = (LPLISTSTRUCT)lpls->lpNext;
	if (i == wIndex)
	    lpls2->dis.itemState = 1;
	else 
	    if (lpls2->dis.itemState != 0)
	        lpls2->dis.itemState = 0;
	if (lpls == NULL)  break;
    }
    lphl->ItemFocused = wIndex;
    if ((wndPtr->dwStyle && LBS_NOTIFY) != 0)
	SendMessage(lphl->hWndLogicParent, WM_COMMAND, 
    	    wndPtr->wIDmenu, MAKELONG(hwnd, LBN_SELCHANGE));
    return LB_ERR;
}



int ListBoxSetSel(HWND hwnd, WORD wIndex, WORD state)
{
    LPHEADLIST 	lphl;
    LPLISTSTRUCT lpls, lpls2;
    UINT	i;
    lphl = ListBoxGetStorageHeader(hwnd);
    if (lphl == NULL) return LB_ERR;
    if (wIndex >= lphl->ItemsCount) return LB_ERR;
    lpls = lphl->lpFirst;
    if (lpls == NULL) return LB_ERR;
    for(i = 0; i < lphl->ItemsCount; i++) {
	lpls2 = lpls;
	lpls = (LPLISTSTRUCT)lpls->lpNext;
	if ((i == wIndex) || (wIndex == (WORD)-1)) {
	    lpls2->dis.itemState = state;
	    break;
	    }  
	if (lpls == NULL)  break;
    }
    return LB_ERR;
}


int ListBoxGetSel(HWND hwnd, WORD wIndex)
{
    LPHEADLIST 	lphl;
    LPLISTSTRUCT lpls, lpls2;
    UINT	i;
    lphl = ListBoxGetStorageHeader(hwnd);
    if (lphl == NULL) return LB_ERR;
    if (wIndex >= lphl->ItemsCount) return LB_ERR;
    lpls = lphl->lpFirst;
    if (lpls == NULL) return LB_ERR;
    for(i = 0; i < lphl->ItemsCount; i++) {
	lpls2 = lpls;
	lpls = (LPLISTSTRUCT)lpls->lpNext;
	if (i == wIndex) {
	    return lpls2->dis.itemState;
	    }  
	if (lpls == NULL)  break;
    }
    return LB_ERR;
}


int ListBoxDirectory(HWND hwnd, UINT attrib, LPSTR filespec)
{
	struct dosdirent *dp;
	int	x, wRet;
	BOOL    OldFlag;
	char 	temp[256];
    LPHEADLIST 	lphl;
	dprintf_listbox(stddeb,"ListBoxDirectory: %s, %4x\n",filespec,attrib);
    lphl = ListBoxGetStorageHeader(hwnd);
    if (lphl == NULL) return LB_ERR;
	if ((dp = (struct dosdirent *)DOS_opendir(filespec)) ==NULL) return 0;
	OldFlag = lphl->bRedrawFlag;
	lphl->bRedrawFlag = FALSE;
	while ((dp = (struct dosdirent *)DOS_readdir(dp))) {
		if (!dp->inuse) break;
		dprintf_listbox(stddeb,"ListBoxDirectory %p '%s' !\n", dp->filename, dp->filename);
		if (dp->attribute & FA_DIREC) {
			if (attrib & DDL_DIRECTORY) {
				sprintf(temp, "[%s]", dp->filename);
				if ( (wRet = ListBoxAddString(hwnd, temp)) == LB_ERR) break;
				}
			} 
		else {
			if (attrib & DDL_EXCLUSIVE) {
				if (attrib & (DDL_READWRITE | DDL_READONLY | DDL_HIDDEN | 
					    DDL_SYSTEM) )
					if ( (wRet = ListBoxAddString(hwnd, dp->filename)) 
					    == LB_ERR) break;
				} 
			else {
				if ( (wRet = ListBoxAddString(hwnd, dp->filename)) 
					== LB_ERR) break;
				}
			}
		}
	DOS_closedir(dp);

	if (attrib & DDL_DRIVES) {
		for (x=0;x!=MAX_DOS_DRIVES;x++) {
			if (DOS_ValidDrive(x)) {
				sprintf(temp, "[-%c-]", 'a'+x);
				if ( (wRet = ListBoxAddString(hwnd, temp)) == LB_ERR) break;
				}		
			}
		}
	lphl->bRedrawFlag = OldFlag;
	if (OldFlag) {
		InvalidateRect(hwnd, NULL, TRUE);
		UpdateWindow(hwnd);
		}
	dprintf_listbox(stddeb,"End of ListBoxDirectory !\n");
	return wRet;
}


int ListBoxGetItemRect(HWND hwnd, WORD wIndex, LPRECT lprect)
{
    LPHEADLIST 	lphl;
    LPLISTSTRUCT lpls, lpls2;
    UINT	i;
    lphl = ListBoxGetStorageHeader(hwnd);
    if (lphl == NULL) return LB_ERR;
    if (wIndex > lphl->ItemsCount) return LB_ERR;
    lpls = lphl->lpFirst;
    if (lpls == NULL) return LB_ERR;
    for(i = 0; i < lphl->ItemsCount; i++) {
	lpls2 = lpls;
	lpls = (LPLISTSTRUCT)lpls->lpNext;
	if (i == wIndex) {
	    *(lprect) = lpls2->dis.rcItem;
	    break;
	    }  
	if (lpls == NULL)  break;
    }
    return LB_ERR;
}



int ListBoxSetItemHeight(HWND hwnd, WORD wIndex, long height)
{
    LPHEADLIST 	lphl;
    LPLISTSTRUCT lpls, lpls2;
    UINT	i;
    lphl = ListBoxGetStorageHeader(hwnd);
    if (lphl == NULL) return LB_ERR;
    if (wIndex > lphl->ItemsCount) return LB_ERR;
    lpls = lphl->lpFirst;
    if (lpls == NULL) return LB_ERR;
    for(i = 0; i < lphl->ItemsCount; i++) {
	lpls2 = lpls;
	lpls = (LPLISTSTRUCT)lpls->lpNext;
	if (i == wIndex) {
	    lpls2->dis.rcItem.bottom = lpls2->dis.rcItem.top + (short)height;
	    InvalidateRect(hwnd, NULL, TRUE);
	    UpdateWindow(hwnd);
	    break;
	    }  
	if (lpls == NULL)  break;
    }
    return LB_ERR;
}





int ListBoxDefaultItem(HWND hwnd, WND *wndPtr, 
	LPHEADLIST lphl, LPLISTSTRUCT lpls)
{
    RECT	rect;
	if (wndPtr == NULL || lphl == NULL || lpls == NULL) {
		fprintf(stderr,"ListBoxDefaultItem() // Bad Pointers !\n");
		return FALSE;
		}
    GetClientRect(hwnd, &rect);
    SetRect(&lpls->dis.rcItem, 0, 0, rect.right, lphl->StdItemHeight);
    lpls->dis.CtlType = lphl->DrawCtlType;
    lpls->dis.CtlID = wndPtr->wIDmenu;
    lpls->dis.itemID = 0;
    lpls->dis.itemAction = 0;
    lpls->dis.itemState = 0;
    lpls->dis.hwndItem = hwnd;
    lpls->dis.hDC = 0;
    lpls->dis.itemData = 0;
	return TRUE;
}



int ListBoxFindNextMatch(HWND hwnd, WORD wChar)
{
    WND  	*wndPtr;
    LPHEADLIST 	lphl;
    LPLISTSTRUCT lpls;
    UINT	Count;
    lphl = ListBoxGetWindowAndStorage(hwnd, &wndPtr);
    if (lphl == NULL) return LB_ERR;
    lpls = lphl->lpFirst;
    if (lpls == NULL) return LB_ERR;
    if (wChar < ' ') return LB_ERR;
    if (((wndPtr->dwStyle & LBS_OWNERDRAWFIXED) == LBS_OWNERDRAWFIXED) ||
	    ((wndPtr->dwStyle & LBS_OWNERDRAWVARIABLE) == LBS_OWNERDRAWVARIABLE)) {
	if ((wndPtr->dwStyle & LBS_HASSTRINGS) != LBS_HASSTRINGS) { 
	    return LB_ERR;
	    }
	}
    Count = 0;
    while(lpls != NULL) {
        if (Count > lphl->ItemFocused) {
	    if (*(lpls->itemText) == (char)wChar) {
		lphl->FirstVisible = Count - lphl->ItemsVisible / 2;
		if (lphl->FirstVisible < 1) lphl->FirstVisible = 1;
		if ((wndPtr->dwStyle & LBS_MULTIPLESEL) == LBS_MULTIPLESEL) {
		    lphl->ItemFocused = Count;
		    }
		else {
		    ListBoxSetCurSel(hwnd, Count);
		    }
		SetScrollPos(hwnd, SB_VERT, lphl->FirstVisible, TRUE);
	        InvalidateRect(hwnd, NULL, TRUE);
	        UpdateWindow(hwnd);
	        return Count;
	        }
	    }
	lpls = (LPLISTSTRUCT)lpls->lpNext;
	Count++;
	}
    Count = 0;
    lpls = lphl->lpFirst;
    while(lpls != NULL) {
	if (*(lpls->itemText) == (char)wChar) {
	    if (Count == lphl->ItemFocused)    return LB_ERR;
	    lphl->FirstVisible = Count - lphl->ItemsVisible / 2;
	    if (lphl->FirstVisible < 1) lphl->FirstVisible = 1;
	    if ((wndPtr->dwStyle & LBS_MULTIPLESEL) == LBS_MULTIPLESEL) {
		lphl->ItemFocused = Count;
		}
	    else {
		ListBoxSetCurSel(hwnd, Count);
		}
	    SetScrollPos(hwnd, SB_VERT, lphl->FirstVisible, TRUE);
	    InvalidateRect(hwnd, NULL, TRUE);
	    UpdateWindow(hwnd);
	    return Count;
	    }
	lpls = (LPLISTSTRUCT)lpls->lpNext;
	Count++;
        }
    return LB_ERR;
}


/************************************************************************
 * 					DlgDirSelect			[USER.99]
 */
BOOL DlgDirSelect(HWND hDlg, LPSTR lpStr, int nIDLBox)
{
	fprintf(stdnimp,"DlgDirSelect(%04X, '%s', %d) \n", hDlg, lpStr, nIDLBox);
	return FALSE;
}


/************************************************************************
 * 					DlgDirList				[USER.100]
 */
int DlgDirList(HWND hDlg, LPSTR lpPathSpec, 
	int nIDLBox, int nIDStat, WORD wType)
{
	HWND	hWnd;
	int ret;
	dprintf_listbox(stddeb,"DlgDirList(%04X, '%s', %d, %d, %04X) \n",
			hDlg, lpPathSpec, nIDLBox, nIDStat, wType);
	if (nIDLBox)
	  hWnd = GetDlgItem(hDlg, nIDLBox);
	else
	  hWnd = 0;
	if (hWnd)
	  ListBoxResetContent(hWnd);
	if (hWnd)
	  ret=ListBoxDirectory(hWnd, wType, lpPathSpec);
	else
	  ret=0;
	if (nIDStat)
	  {
	    int drive;
	    drive = DOS_GetDefaultDrive();
	    SendDlgItemMessage(hDlg, nIDStat, WM_SETTEXT, 0, 
			       (LONG) DOS_GetCurrentDir(drive) );
	  } 
	return ret;
}



