Initial commit. Ported some code from wine.

Not much working yet.

svn path=/trunk/; revision=579
This commit is contained in:
Boudewijn Dekker
1999-07-04 16:01:27 +00:00
parent 84d1d53870
commit 2a01ea22a9
66 changed files with 20077 additions and 189 deletions

View File

@@ -0,0 +1,37 @@
#ifndef __WINE_CARET_H
#define __WINE_CARET_H
#define DCX_USESTYLE 0x00010000
typedef struct
{
HWND hwnd;
UINT hidden;
WINBOOL on;
INT x;
INT y;
INT width;
INT height;
HBRUSH hBrush;
UINT timeout;
UINT timerid;
} CARET;
typedef enum
{
CARET_OFF = 0,
CARET_ON,
CARET_TOGGLE,
} DISPLAY_CARET;
HWND CARET_GetHwnd(void);
void CARET_GetRect(LPRECT lprc); /* windows/caret.c */
void CARET_DisplayCaret( DISPLAY_CARET status );
//VOID CALLBACK CARET_Callback( HWND hwnd, UINT msg, UINT id, DWORD ctime);
void CARET_SetTimer(void);
void CARET_ResetTimer(void);
void CARET_KillTimer(void);
#endif

View File

@@ -7,9 +7,9 @@
#ifndef __WINE_CLASS_H
#define __WINE_CLASS_H
#include <windows.h>
#include <user32/winproc.h>
struct tagDCE;
#include <user32/dce.h>
#define MAX_CLASSNAME 255
@@ -17,32 +17,30 @@ struct tagDCE;
#define CLASS_MAGIC ('C' | ('L' << 8) | ('A' << 16) | ('S' << 24))
typedef struct tagCLASS
{
struct tagCLASS *next; /* Next class */
struct tagCLASS *next; /* Next class */
UINT magic; /* Magic number */
UINT cWindows; /* Count of existing windows */
UINT style; /* Class style */
WNDPROC winproc; /* Window procedure */
INT cbClsExtra; /* Class extra bytes */
INT cbWndExtra; /* Window extra bytes */
char menuNameA[MAX_CLASSNAME];
WCHAR menuNameW[MAX_CLASSNAME]; /* Default menu name (Unicode) */
struct tagDCE *dce; /* Class DCE (if CS_CLASSDC) */
void * menuName; /* Menu name */
struct tagDCE *dce; /* Class DCE (if CS_CLASSDC) */
HINSTANCE hInstance; /* Module that created the task */
HICON hIcon; /* Default icon */
HICON hIconSm; /* Default small icon */
HCURSOR hCursor; /* Default cursor */
HBRUSH hbrBackground; /* Default background */
ATOM atomName; /* Name of the class */
char classNameA[MAX_CLASSNAME]; /* Class name (ASCII string) */
WCHAR classNameW[MAX_CLASSNAME]; /* Class name (Unicode) */
LONG wExtra[1]; /* Class extra bytes */
ATOM atomName; /* Name of the class */
void * className; /* Class name (Unicode) */
WINBOOL bUnicode; /* Unicode or Ascii window */
LONG wExtra[1]; /* Class extra bytes */
} CLASS;
void CLASS_DumpClass( CLASS *class );
void CLASS_WalkClasses(void);
void CLASS_FreeModuleClasses( HMODULE hModule );
CLASS *CLASS_FindClassByAtom( ATOM atom, HINSTANCE hinstance );
CLASS *CLASS_FindClassByAtom( ATOM classAtom, HINSTANCE hInstance );
WINBOOL CLASS_FreeClass(CLASS *classPtr);
#endif /* __WINE_CLASS_H */

View File

@@ -0,0 +1,58 @@
/*
* USER DCE definitions
*
* Copyright 1993 Alexandre Julliard
*/
#ifndef __WINE_DCE_H
#define __WINE_DCE_H
#include <windows.h>
struct tagWND;
/* additional DCX flags
*/
#define DCX_NORESETATTR 0x00000004
#define DCX_EXCLUDEUPDATE 0x00000100
#define DCX_INTERSECTUPDATE 0x00000200
//#define DCX_LOCKWINDOWUPDATE 0x00000400
#define DCX_NORECOMPUTE 0x00100000
//#define DCX_VALIDATE 0x00200000
#define DCX_DCEEMPTY 0x00000800
#define DCX_DCEBUSY 0x00001000
#define DCX_DCEDIRTY 0x00002000
#define DCX_WINDOWPAINT 0x00020000
#define DCX_KEEPCLIPRGN 0x00040000
#define DCX_NOCLIPCHILDREN 0x00080000
typedef enum
{
DCE_CACHE_DC, /* This is a cached DC (allocated by USER) */
DCE_CLASS_DC, /* This is a class DC (style CS_CLASSDC) */
DCE_WINDOW_DC /* This is a window DC (style CS_OWNDC) */
} DCE_TYPE;
typedef struct tagDCE
{
struct tagDCE *next;
HDC hDC;
HWND hwndCurrent;
HWND hwndDC;
HRGN hClipRgn;
DCE_TYPE type;
DWORD DCXflags;
} DCE;
void DCE_Init(void);
DCE* DCE_AllocDCE( HWND hWnd, DCE_TYPE type );
DCE* DCE_FreeDCE( DCE *dce );
void DCE_FreeWindowDCE( struct tagWND* );
INT DCE_ExcludeRgn( HDC, struct tagWND*, HRGN );
HRGN DCE_GetVisRgn( HWND, WORD );
WINBOOL DCE_InvalidateDCE( struct tagWND *, const RECT* );
#endif /* __WINE_DCE_H */

View File

@@ -0,0 +1,5 @@
#ifndef DEBUG_H
#define DEBUG_H
#include <stdio.h>
#define DPRINT printf
#endif

View File

@@ -0,0 +1,11 @@
int lstrcpynWtoA( LPSTR ptr1, LPWSTR ptr2, int n );
int lstrcpynAtoW( LPWSTR ptr1, LPSTR ptr2, int n );
int lstrcpyWtoA( LPSTR ptr1, LPWSTR ptr2 );
int lstrcpyAtoW( LPWSTR ptr1, LPSTR ptr2 );
int lpstrncpyA( LPSTR ptr1,LPSTR ptr2, int nMaxCount);
int lpstrncpyW( LPWSTR ptr1,LPWSTR ptr2, int nMaxCount);
LPVOID HEAP_strdupAtoW(HANDLE hHeap,DWORD dwFlags, LPCSTR lpszAsciiString );
LPVOID HEAP_strdupWtoA(HANDLE hHeap,DWORD dwFlags, LPCWSTR lpszUnicodeString );
LPSTR HEAP_strdupA(LPSTR ptr);
LPWSTR HEAP_strdupW(LPWSTR ptr);

View File

@@ -9,21 +9,58 @@
#include <windows.h>
#define HOOK_WINA 0x01
#define HOOK_WINW 0x02
#define HOOK_WIN32A 0x01
#define HOOK_WIN32W 0x02
#define HOOK_INUSE 0x80
#define HQUEUE HANDLE
/* hook type mask */
#define HOOK_MAPTYPE (HOOK_WIN32A | HOOK_WIN32W)
HOOKPROC HOOK_GetProc( HHOOK hhook );
#define HOOK_MAGIC ((int)'H' | (int)'K' << 8) /* 'HK' */
/***** Window hooks *****/
/* Hook values */
#define WH_MIN (-1)
#define WH_MAX 12
#define WH_MINHOOK WH_MIN
#define WH_MAXHOOK WH_MAX
#define WH_NB_HOOKS (WH_MAXHOOK-WH_MINHOOK+1)
/* Hook data (pointed to by a HHOOK) */
typedef struct
{
HANDLE next; /* 00 Next hook in chain */
HOOKPROC proc; /* 02 Hook procedure */
INT id; /* 06 Hook id (WH_xxx) */
HQUEUE ownerQueue; /* 08 Owner queue (0 for system hook) */
HMODULE ownerModule; /* 0a Owner module */
WORD flags; /* 0c flags */
} HOOKDATA;
HANDLE HOOK_SetHook( INT id, LPVOID proc, INT type,
HINSTANCE hInst, DWORD dwThreadId );
WINBOOL HOOK_RemoveHook( HANDLE hook );
WINBOOL HOOK_IsHooked( INT id );
LRESULT HOOK_CallHooksA( INT id, INT code, WPARAM wParam,
LPARAM lParam );
LRESULT HOOK_CallHooksW( INT id, INT code, WPARAM wParam,
LPARAM lParam );
LRESULT HOOK_CallHook( HHOOK hook, INT fromtype, INT code,
WPARAM wParam, LPARAM lParam );
HANDLE HOOK_GetNextHook( HHOOK hook );
void HOOK_FreeModuleHooks( HMODULE hModule );
void HOOK_FreeQueueHooks( HQUEUE hQueue );
void HOOK_ResetQueueHooks( HQUEUE hQueue );

View File

@@ -0,0 +1,182 @@
/*
* Menu definitions
*/
#ifndef __WINE_MENU_H
#define __WINE_MENU_H
#include <user32/win.h>
#include <user32/queue.h>
#include <user32/nc.h>
#define PUT_WORD(ptr,w) (*(WORD *)(ptr) = (w))
#define GET_WORD(ptr) (*(WORD *)(ptr))
#define PUT_DWORD(ptr,dw) (*(DWORD *)(ptr) = (dw))
#define GET_DWORD(ptr) (*(DWORD *)(ptr))
#define WM_NEXTMENU 0x0213
#define MF_INSERT 0x0000
#define MF_CHANGE 0x0080
#define MF_APPEND 0x0100
#define MF_DELETE 0x0200
#define MF_REMOVE 0x1000
#define MF_END 0x0080
/* internal popup menu window messages */
#define MM_SETMENUHANDLE (WM_USER + 0)
#define MM_GETMENUHANDLE (WM_USER + 1)
extern WND* pTopPopupWnd;
extern UINT uSubPWndLevel;
/* Menu item structure */
typedef struct {
/* ----------- MENUITEMINFO Stuff ----------- */
UINT fType; /* Item type. */
UINT fState; /* Item state. */
UINT wID; /* Item id. */
HMENU hSubMenu; /* Pop-up menu. */
HBITMAP hCheckBit; /* Bitmap when checked. */
HBITMAP hUnCheckBit; /* Bitmap when unchecked. */
LPWSTR text; /* Item text or bitmap handle. */
DWORD dwItemData; /* Application defined. */
/* ----------- Wine stuff ----------- */
RECT rect; /* Item area (relative to menu window) */
UINT xTab; /* X position of text after Tab */
} MENUITEM;
/* Popup menu structure */
typedef struct {
WORD wFlags; /* Menu flags (MF_POPUP, MF_SYSMENU) */
WORD wMagic; /* Magic number */
HQUEUE hTaskQ; /* Task queue for this menu */
WORD Width; /* Width of the whole menu */
WORD Height; /* Height of the whole menu */
WORD nItems; /* Number of items in the menu */
HWND hWnd; /* Window containing the menu */
MENUITEM *items; /* Array of menu items */
UINT FocusedItem; /* Currently focused item */
WORD defitem; /* default item position. */
DWORD dwContextHelpId; /* Context help id */
} POPUPMENU, *LPPOPUPMENU;
/* internal flags for menu tracking */
#define TF_ENDMENU 0x0001
#define TF_SUSPENDPOPUP 0x0002
#define TF_SKIPREMOVE 0x0004
typedef struct
{
UINT trackFlags;
HMENU hCurrentMenu; /* current submenu (can be equal to hTopMenu)*/
HMENU hTopMenu; /* initial menu */
HWND hOwnerWnd; /* where notifications are sent */
POINT pt;
} MTRACKER;
#define MENU_MAGIC 0x554d /* 'MU' */
#define IS_A_MENU(pmenu) ((pmenu) && (pmenu)->wMagic == MENU_MAGIC)
#define ITEM_PREV -1
#define ITEM_NEXT 1
/* Internal MENU_TrackMenu() flags */
#define TPM_INTERNAL 0xF0000000
#define TPM_ENTERIDLEEX 0x80000000 /* set owner window for WM_ENTERIDLE */
#define TPM_BUTTONDOWN 0x40000000 /* menu was clicked before tracking */
/* popup menu shade thickness */
#define POPUP_XSHADE 4
#define POPUP_YSHADE 4
/* Space between 2 menu bar items */
#define MENU_BAR_ITEMS_SPACE 12
/* Minimum width of a tab character */
#define MENU_TAB_SPACE 8
/* Height of a separator item */
#define SEPARATOR_HEIGHT 5
/* (other menu->FocusedItem values give the position of the focused item) */
#define NO_SELECTED_ITEM 0xffff
#define MENU_ITEM_TYPE(flags) \
((flags) & (MF_STRING | MF_BITMAP | MF_OWNERDRAW | MF_SEPARATOR))
#define IS_STRING_ITEM(flags) (MENU_ITEM_TYPE ((flags)) == MF_STRING)
#define IS_SYSTEM_MENU(menu) \
(!((menu)->wFlags & MF_POPUP) && (menu)->wFlags & MF_SYSMENU)
#define IS_SYSTEM_POPUP(menu) \
((menu)->wFlags & MF_POPUP && (menu)->wFlags & MF_SYSMENU)
#define TYPE_MASK (MFT_STRING | MFT_BITMAP | MFT_OWNERDRAW | MFT_SEPARATOR | \
MFT_MENUBARBREAK | MFT_MENUBREAK | MFT_RADIOCHECK | \
MFT_RIGHTORDER | MFT_RIGHTJUSTIFY | \
MF_POPUP | MF_SYSMENU | MF_HELP)
#define STATE_MASK (~TYPE_MASK)
extern HMENU MENU_DefSysPopup;
WINBOOL MENU_Init(void);
HMENU MENU_GetSysMenu(HWND hWndOwner, HMENU hSysPopup);
UINT MENU_GetMenuBarHeight( HWND hwnd, UINT menubarWidth,
INT orgX, INT orgY );
BOOL MENU_PatchResidentPopup( HQUEUE, WND* );
void MENU_TrackMouseMenuBar( WND *wnd, INT ht, POINT pt );
void MENU_TrackKbdMenuBar( WND *wnd, UINT wParam, INT vkey );
UINT MENU_DrawMenuBar( HDC hDC, LPRECT lprect,
HWND hwnd, WINBOOL suppress_draw );
WINBOOL MENU_TrackMenu( HMENU hmenu, UINT wFlags, INT x, INT y,
HWND hwnd, const RECT *lprect );
WINBOOL MENU_ButtonUp( MTRACKER* pmt, HMENU hPtMenu );
WINBOOL MENU_MouseMove( MTRACKER* pmt, HMENU hPtMenu );
LRESULT MENU_DoNextMenu( MTRACKER* pmt, UINT vk );
void MENU_KeyLeft( MTRACKER* pmt );
void MENU_KeyRight( MTRACKER* pmt );
WINBOOL MENU_InitTracking(HWND hWnd, HMENU hMenu);
void MENU_TrackMouseMenuBar( WND* wndPtr, INT ht, POINT pt );
WINBOOL MENU_ShowPopup( HWND hwndOwner, HMENU hmenu, UINT id,
INT x, INT y, INT xanchor, INT yanchor );
void MENU_DrawPopupMenu( HWND hwnd, HDC hdc, HMENU hmenu );
UINT MENU_DrawMenuBar( HDC hDC, LPRECT lprect, HWND hwnd,
WINBOOL suppress_draw);
MENUITEM *MENU_FindItem( HMENU *hmenu, UINT *nPos, UINT wFlags );
void MENU_MenuBarCalcSize( HDC hdc, LPRECT lprect,
LPPOPUPMENU lppop, HWND hwndOwner );
void MENU_CalcItemSize( HDC hdc, MENUITEM *lpitem, HWND hwndOwner,
INT orgX, INT orgY, WINBOOL menuBar );
void MENU_HideSubPopups( HWND hwndOwner, HMENU hmenu,
WINBOOL sendMenuSelect );
void MENU_SelectItem( HWND hwndOwner, HMENU hmenu, UINT wIndex,
WINBOOL sendMenuSelect );
MENUITEM *MENU_InsertItem( HMENU hMenu, UINT pos, UINT flags );
WINBOOL MENU_SetItemData( MENUITEM *item, UINT flags, UINT id,
LPCWSTR str );
void MENU_FreeItemData( MENUITEM* item );
HMENU MENU_CopySysPopup(void);
// addition to win32
HPEN STDCALL GetSysColorPen(INT);
#endif /* __WINE_MENU_H */

View File

@@ -38,10 +38,8 @@ WINBOOL MSG_PeekMessage( LPMSG msg, HWND hwnd, WORD first, WORD last,
void MSG_CallWndProcHook( LPMSG pmsg, WINBOOL bUnicode );
LRESULT MSG_SendMessage( HQUEUE hDestQueue, HWND hwnd, UINT msg,
WPARAM wParam, LPARAM lParam, WORD flags );
LRESULT MSG_SendMessage( HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam,
WINBOOL bUnicode );
void joySendMessages(void);
#endif /* __WINE_MESSAGE_H */

View File

@@ -0,0 +1,64 @@
#ifndef __WINE_MSG_H
#define __WINE_MSG_H
#define WM_SYSTIMER 0x0118
#define WH_HARDWARE 8
#include <user32/win.h>
#include <user32/queue.h>
#include <user32/sysmetr.h>
//#include <user32/debug.h>
typedef struct
{
HWND hWnd;
UINT wMessage;
WPARAM wParam;
LPARAM lParam;
} HARDWAREHOOKSTRUCT, *LPHARDWAREHOOKSTRUCT;
#define MAX_QUEUE_SIZE 256
extern WINBOOL MouseButtonsStates[3];
extern WINBOOL AsyncMouseButtonsStates[3];
extern BYTE InputKeyStateTable[256];
extern BYTE QueueKeyStateTable[256];
extern BYTE AsyncKeyStateTable[256];
#define WM_NCMOUSEFIRST WM_NCMOUSEMOVE
#define WM_NCMOUSELAST WM_NCMBUTTONDBLCLK
typedef enum { SYSQ_MSG_ABANDON, SYSQ_MSG_SKIP,
SYSQ_MSG_ACCEPT, SYSQ_MSG_CONTINUE } SYSQ_STATUS;
extern MESSAGEQUEUE *pCursorQueue; /* queue.c */
extern MESSAGEQUEUE *pActiveQueue;
/* message.c */
WINBOOL MSG_InternalGetMessage( MSG *msg, HWND hwnd,
HWND hwndOwner, WPARAM code,
WORD flags, WINBOOL sendIdle );
WINBOOL MSG_PeekMessage( LPMSG msg, HWND hwnd, WORD first, WORD last,
WORD flags, WINBOOL peek );
void MSG_CallWndProcHook( LPMSG pmsg, WINBOOL bUnicode );
LRESULT MSG_SendMessage( HQUEUE hDestQueue, HWND hwnd, UINT msg,
WPARAM wParam, LPARAM lParam, WORD flags );
void joySendMessages(void);
#endif

View File

@@ -0,0 +1,80 @@
/*
* Window non-client functions definitions
*
* Copyright 1995 Alexandre Julliard
*/
#ifndef __WINE_NONCLIENT_H
#define __WINE_NONCLIENT_H
//#include "config.h"
#define WIN95_LOOK 1
#define WIN31_LOOK 0
extern int TWEAK_WineLook;
#include <user32/win.h>
#include <user32/sysmetr.h>
#include <user32/msg.h>
#include <user32/menu.h>
#include <user32/winpos.h>
#include <user32/hook.h>
#include <user32/scroll.h>
#define SC_ARRANGE 0xf110
#define WM_SETVISIBLE 0x0009
/* WM_NCHITTEST return codes */
#define HTERROR (-2)
#define HTTRANSPARENT (-1)
#define HTMINBUTTON 8
#define HTMAXBUTTON 9
#define HTBORDER 18
#define HTOBJECT 19
#define HTCLOSE 20
#define HTHELP 21
#define HTSIZEFIRST HTLEFT
#define HTSIZELAST HTBOTTOMRIGHT
/* CallMsgFilter() values */
#define MSGF_MESSAGEBOX 1
#define MSGF_MOVE 3
#define MSGF_SIZE 4
#define MAKEINTRESOURCEA(i) (LPSTR) ((DWORD) ((WORD) (i)))
#define DCX_USESTYLE 0x00010000
LONG NC_HandleNCPaint( HWND hwnd , HRGN clip);
LONG NC_HandleNCActivate( WND *pwnd, WPARAM wParam );
LONG NC_HandleNCCalcSize( WND *pWnd, RECT *winRect );
LONG NC_HandleNCHitTest( HWND hwnd, POINT pt );
LONG NC_HandleNCLButtonDown( WND* pWnd, WPARAM wParam, LPARAM lParam );
LONG NC_HandleNCLButtonDblClk( WND *pWnd, WPARAM wParam, LPARAM lParam);
LONG NC_HandleSysCommand( HWND hwnd, WPARAM wParam, POINT pt );
LONG NC_HandleSetCursor( HWND hwnd, WPARAM wParam, LPARAM lParam );
void NC_DrawSysButton( HWND hwnd, HDC hdc, WINBOOL down );
WINBOOL NC_DrawSysButton95( HWND hwnd, HDC hdc, WINBOOL down );
WINBOOL NC_GetSysPopupPos( WND* wndPtr, RECT* rect );
void NC_AdjustRect( LPRECT rect, DWORD style, WINBOOL menu,
DWORD exStyle );
//gdi
WINBOOL STDCALL FastWindowFrame(HDC,const RECT*,INT,INT,DWORD);
void NC_AdjustRectOuter95 (LPRECT rect, DWORD style, WINBOOL menu, DWORD exStyle);
void NC_AdjustRectInner95 (LPRECT rect, DWORD style, DWORD exStyle);
#endif /* __WINE_NONCLIENT_H */

View File

@@ -0,0 +1,22 @@
typedef struct tagPROPERTY
{
struct tagPROPERTY *next; /* Next property in window list */
HANDLE handle; /* User's data */
ATOM atom;
HANDLE app;
} PROPERTY;
typedef struct tagPROPVALUE
{
HANDLE hwnd;
HANDLE handle;
ATOM atom;
} PROPVALUE;
HANDLE PROPERTY_FindProp( HWND hwnd, ATOM Atom );
WINBOOL PROPERTY_SetProp( HANDLE hwnd, ATOM atom,HANDLE hData);
HANDLE PROPERTY_RemoveProp( HANDLE hwnd , ATOM atom );
void PROPERTY_RemoveWindowProps( HANDLE hwnd );
WINBOOL PROPERTY_EnumPropEx(HWND hwnd, PROPVALUE **pv , int maxsize, int *size );

View File

@@ -7,8 +7,9 @@
#ifndef __WINE_QUEUE_H
#define __WINE_QUEUE_H
//#include "wine/winuser16.h"
#include <windows.h>
#include <user32/win.h>
/***** Window hooks *****/
@@ -20,7 +21,6 @@
#define WH_MAXHOOK WH_MAX
#define WH_NB_HOOKS (WH_MAXHOOK-WH_MINHOOK+1)
#define HQUEUE HANDLE
/* Message as stored in the queue (contains the extraInfo field) */
@@ -113,11 +113,11 @@ void QUEUE_FlushMessages(HQUEUE);
void hardware_event( WORD message, WORD wParam, LONG lParam,
int xPos, int yPos, DWORD time, DWORD extraInfo );
HQUEUE STDCALL InitThreadInput( WORD unknown, WORD flags );
HQUEUE InitThreadInput( WORD unknown, WORD flags );
HQUEUE WINAPI SetThreadQueue( DWORD thread, HQUEUE hQueue );
HQUEUE WINAPI GetThreadQueue( DWORD thread );
VOID WINAPI SetFastQueue( DWORD thread, HANDLE hQueue );
HANDLE STDCALL GetFastQueue( void );
HQUEUE SetThreadQueue( DWORD thread, HQUEUE hQueue );
HQUEUE GetThreadQueue( DWORD thread );
VOID SetFastQueue( DWORD thread, HANDLE hQueue );
HANDLE GetFastQueue( void );
#endif /* __WINE_QUEUE_H */

View File

@@ -0,0 +1,62 @@
/*
* Resource definitions
*
* Copyright 1995 Alexandre Julliard
*/
#ifndef __WINE_RESOURCE_H
#define __WINE_RESOURCE_H
#include <windows.h>
//#ifndef __WRC_RSC_H
//#include "wrc_rsc.h"
//#endif
/*
* BS: I comment this out to catch all occurences
* of reference to this structure which is now
* rendered obsolete.
*
* struct resource
* {
* int id;
* int type;
* const char *name;
* const unsigned char* bytes;
* unsigned size;
* };
*/
/* Built-in resources */
typedef enum
{
SYSRES_MENU_SYSMENU,
SYSRES_MENU_EDITMENU,
SYSRES_DIALOG_MSGBOX,
SYSRES_DIALOG_SHELL_ABOUT_MSGBOX,
SYSRES_DIALOG_OPEN_FILE,
SYSRES_DIALOG_SAVE_FILE,
SYSRES_DIALOG_PRINT,
SYSRES_DIALOG_PRINT_SETUP,
SYSRES_DIALOG_CHOOSE_FONT,
SYSRES_DIALOG_CHOOSE_COLOR,
SYSRES_DIALOG_FIND_TEXT,
SYSRES_DIALOG_REPLACE_TEXT
} SYSTEM_RESOURCE;
//extern void LIBRES_RegisterResources(const wrc_resource32_t * const * Res);
#if defined(__GNUC__) && (__GNUC__ == 2) && (__GNUC_MINOR__ >= 7)
#define WINE_CONSTRUCTOR __attribute__((constructor))
#define HAVE_WINE_CONSTRUCTOR
#else
#define WINE_CONSTRUCTOR
#undef HAVE_WINE_CONSTRUCTOR
#endif
HGLOBAL SYSRES_LoadResource( SYSTEM_RESOURCE id );
void SYSRES_FreeResource( HGLOBAL handle );
LPCVOID SYSRES_GetResPtr( SYSTEM_RESOURCE id );
#endif /* __WINE_RESOURCE_H */

View File

@@ -0,0 +1,32 @@
/*
* Scroll-bar class extra info
*
* Copyright 1993 Martin Ayotte
* Copyright 1994 Alexandre Julliard
*/
#ifndef __WINE_SCROLL_H
#define __WINE_SCROLL_H
#include "windows.h"
typedef struct
{
INT CurVal; /* Current scroll-bar value */
INT MinVal; /* Minimum scroll-bar value */
INT MaxVal; /* Maximum scroll-bar value */
INT Page; /* Page size of scroll bar (Win32) */
UINT flags; /* EnableScrollBar flags */
} SCROLLBAR_INFO;
LRESULT STDCALL ScrollBarWndProc( HWND hwnd, UINT uMsg,
WPARAM wParam, LPARAM lParam );
void SCROLL_DrawScrollBar( HWND hwnd, HDC hdc, INT nBar,
WINBOOL arrows, WINBOOL interior );
void SCROLL_HandleScrollEvent( HWND hwnd, INT nBar,
UINT msg, POINT pt );
//#define WM_SYSTIMER (0x118)
#endif /* __WINE_SCROLL_H */

View File

@@ -0,0 +1,4 @@
/* loader/signal.c */
WINBOOL SIGNAL_Init(void);
void SIGNAL_SetHandler( int sig, void (*func)(), int flags );
void SIGNAL_MaskAsyncEvents( BOOL flag );

View File

@@ -0,0 +1,145 @@
/*
* System metrics definitions
*
* Copyright 1994 Alexandre Julliard
*/
#ifndef __WINE_SYSMETRICS_H
#define __WINE_SYSMETRICS_H
#include <windows.h>
/* Constant system metrics */
#if 0
#ifdef WIN_95_LOOK
#define SYSMETRICS_CXDLGFRAME 3
#define SYSMETRICS_CYDLGFRAME 3
#define SYSMETRICS_CYVTHUMB 13
#define SYSMETRICS_CXHTHUMB 13
#else
#define SYSMETRICS_CXDLGFRAME 4
#define SYSMETRICS_CYDLGFRAME 4
#define SYSMETRICS_CYVTHUMB 16
#define SYSMETRICS_CXHTHUMB 16
#endif
#define SYSMETRICS_CXICON 32
#define SYSMETRICS_CYICON 32
#define SYSMETRICS_CXCURSOR 32
#define SYSMETRICS_CYCURSOR 32
#ifdef WIN_95_LOOK
#define SYSMETRICS_CYVSCROLL 14
#define SYSMETRICS_CXHSCROLL 14
#define SYSMETRICS_CXMIN 112
#define SYSMETRICS_CYMIN 27
#else
#define SYSMETRICS_CYVSCROLL 16
#define SYSMETRICS_CXHSCROLL 16
#define SYSMETRICS_CXMIN 100
#define SYSMETRICS_CYMIN 28
#endif
#ifdef WIN_95_LOOK
#define SYSMETRICS_CXMINTRACK 112
#define SYSMETRICS_CYMINTRACK 27
#else
#define SYSMETRICS_CXMINTRACK 100
#define SYSMETRICS_CYMINTRACK 28
#endif
#endif 0
/* Some non-constant system metrics */
#define SYSMETRICS_CXSCREEN sysMetrics[SM_CXSCREEN] /* 0 */
#define SYSMETRICS_CYSCREEN sysMetrics[SM_CYSCREEN] /* 1 */
#define SYSMETRICS_CXVSCROLL sysMetrics[SM_CXVSCROLL] /* 2 */
#define SYSMETRICS_CYHSCROLL sysMetrics[SM_CYHSCROLL] /* 3 */
#define SYSMETRICS_CYCAPTION sysMetrics[SM_CYCAPTION] /* 4 */
#define SYSMETRICS_CXBORDER sysMetrics[SM_CXBORDER] /* 5 */
#define SYSMETRICS_CYBORDER sysMetrics[SM_CYBORDER] /* 6 */
#define SYSMETRICS_CXDLGFRAME sysMetrics[SM_CXDLGFRAME] /* 7 */
#define SYSMETRICS_CYDLGFRAME sysMetrics[SM_CYDLGFRAME] /* 8 */
#define SYSMETRICS_CYVTHUMB sysMetrics[SM_CYVTHUMB] /* 9 */
#define SYSMETRICS_CXHTHUMB sysMetrics[SM_CXHTHUMB] /* 10 */
#define SYSMETRICS_CXICON sysMetrics[SM_CXICON] /* 11 */
#define SYSMETRICS_CYICON sysMetrics[SM_CYICON] /* 12 */
#define SYSMETRICS_CXCURSOR sysMetrics[SM_CXCURSOR] /* 13 */
#define SYSMETRICS_CYCURSOR sysMetrics[SM_CYCURSOR] /* 14 */
#define SYSMETRICS_CYMENU sysMetrics[SM_CYMENU] /* 15 */
#define SYSMETRICS_CXFULLSCREEN sysMetrics[SM_CXFULLSCREEN] /* 16 */
#define SYSMETRICS_CYFULLSCREEN sysMetrics[SM_CYFULLSCREEN] /* 17 */
#define SYSMETRICS_CYKANJIWINDOW sysMetrics[SM_CYKANJIWINDOW] /* 18 */
#define SYSMETRICS_MOUSEPRESENT sysMetrics[SM_MOUSEPRESENT] /* 19 */
#define SYSMETRICS_CYVSCROLL sysMetrics[SM_CYVSCROLL] /* 20 */
#define SYSMETRICS_CXHSCROLL sysMetrics[SM_CXHSCROLL] /* 21 */
#define SYSMETRICS_DEBUG sysMetrics[SM_DEBUG] /* 22 */
#define SYSMETRICS_SWAPBUTTON sysMetrics[SM_SWAPBUTTON] /* 23 */
#define SYSMETRICS_RESERVED1 sysMetrics[SM_RESERVED1] /* 24 */
#define SYSMETRICS_RESERVED2 sysMetrics[SM_RESERVED2] /* 25 */
#define SYSMETRICS_RESERVED3 sysMetrics[SM_RESERVED3] /* 26 */
#define SYSMETRICS_RESERVED4 sysMetrics[SM_RESERVED4] /* 27 */
#define SYSMETRICS_CXMIN sysMetrics[SM_CXMIN] /* 28 */
#define SYSMETRICS_CYMIN sysMetrics[SM_CYMIN] /* 29 */
#define SYSMETRICS_CXSIZE sysMetrics[SM_CXSIZE] /* 30 */
#define SYSMETRICS_CYSIZE sysMetrics[SM_CYSIZE] /* 31 */
#define SYSMETRICS_CXFRAME sysMetrics[SM_CXFRAME] /* 32 */
#define SYSMETRICS_CYFRAME sysMetrics[SM_CYFRAME] /* 33 */
#define SYSMETRICS_CXMINTRACK sysMetrics[SM_CXMINTRACK] /* 34 */
#define SYSMETRICS_CYMINTRACK sysMetrics[SM_CYMINTRACK] /* 35 */
#define SYSMETRICS_CXDOUBLECLK sysMetrics[SM_CXDOUBLECLK] /* 36 */
#define SYSMETRICS_CYDOUBLECLK sysMetrics[SM_CYDOUBLECLK] /* 37 */
#define SYSMETRICS_CXICONSPACING sysMetrics[SM_CXICONSPACING] /* 38 */
#define SYSMETRICS_CYICONSPACING sysMetrics[SM_CYICONSPACING] /* 39 */
#define SYSMETRICS_MENUDROPALIGNMENT sysMetrics[SM_MENUDROPALIGNMENT] /* 40 */
#define SYSMETRICS_PENWINDOWS sysMetrics[SM_PENWINDOWS] /* 41 */
#define SYSMETRICS_DBCSENABLED sysMetrics[SM_DBCSENABLED] /* 42 */
#define SYSMETRICS_CMOUSEBUTTONS sysMetrics[SM_CMOUSEBUTTONS] /* 43 */
#define SYSMETRICS_CXFIXEDFRAME sysMetrics[SM_CXDLGFRAME] /* win40 name change */
#define SYSMETRICS_CYFIXEDFRAME sysMetrics[SM_CYDLGFRAME] /* win40 name change */
#define SYSMETRICS_CXSIZEFRAME sysMetrics[SM_CXFRAME] /* win40 name change */
#define SYSMETRICS_CYSIZEFRAME sysMetrics[SM_CYFRAME] /* win40 name change */
#define SYSMETRICS_SECURE sysMetrics[SM_SECURE] /* 44 */
#define SYSMETRICS_CXEDGE sysMetrics[SM_CXEDGE] /* 45 */
#define SYSMETRICS_CYEDGE sysMetrics[SM_CYEDGE] /* 46 */
#define SYSMETRICS_CXMINSPACING sysMetrics[SM_CXMINSPACING] /* 47 */
#define SYSMETRICS_CYMINSPACING sysMetrics[SM_CYMINSPACING] /* 48 */
#define SYSMETRICS_CXSMICON sysMetrics[SM_CXSMICON] /* 49 */
#define SYSMETRICS_CYSMICON sysMetrics[SM_CYSMICON] /* 50 */
#define SYSMETRICS_CYSMCAPTION sysMetrics[SM_CYSMCAPTION] /* 51 */
#define SYSMETRICS_CXSMSIZE sysMetrics[SM_CXSMSIZE] /* 52 */
#define SYSMETRICS_CYSMSIZE sysMetrics[SM_CYSMSIZE] /* 53 */
#define SYSMETRICS_CXMENUSIZE sysMetrics[SM_CXMENUSIZE] /* 54 */
#define SYSMETRICS_CYMENUSIZE sysMetrics[SM_CYMENUSIZE] /* 55 */
#define SYSMETRICS_ARRANGE sysMetrics[SM_ARRANGE] /* 56 */
#define SYSMETRICS_CXMINIMIZED sysMetrics[SM_CXMINIMIZED] /* 57 */
#define SYSMETRICS_CYMINIMIZED sysMetrics[SM_CYMINIMIZED] /* 58 */
#define SYSMETRICS_CXMAXTRACK sysMetrics[SM_CXMAXTRACK] /* 59 */
#define SYSMETRICS_CYMAXTRACK sysMetrics[SM_CYMAXTRACK] /* 60 */
#define SYSMETRICS_CXMAXIMIZED sysMetrics[SM_CXMAXIMIZED] /* 61 */
#define SYSMETRICS_CYMAXIMIZED sysMetrics[SM_CYMAXIMIZED] /* 62 */
#define SYSMETRICS_NETWORK sysMetrics[SM_NETWORK] /* 63 */
#define SYSMETRICS_CLEANBOOT sysMetrics[SM_CLEANBOOT] /* 67 */
#define SYSMETRICS_CXDRAG sysMetrics[SM_CXDRAG] /* 68 */
#define SYSMETRICS_CYDRAG sysMetrics[SM_CYDRAG] /* 69 */
#define SYSMETRICS_SHOWSOUNDS sysMetrics[SM_SHOWSOUNDS] /* 70 */
/* Use the following instead of sysMetrics[SM_CXMENUCHECK] GetMenuCheckMarkDimensions()! */
#define SYSMETRICS_CXMENUCHECK sysMetrics[SM_CXMENUCHECK] /* 71 */
#define SYSMETRICS_CYMENUCHECK sysMetrics[SM_CYMENUCHECK] /* 72 */
#define SYSMETRICS_SLOWMACHINE sysMetrics[SM_SLOWMACHINE] /* 73 */
#define SYSMETRICS_MIDEASTENABLED sysMetrics[SM_MIDEASTENABLED] /* 74 */
#define SYSMETRICS_MOUSEWHEELPRESENT sysMetrics[SM_MOUSEWHEELPRESENT] /* 75 */
#define SYSMETRICS_CXVIRTUALSCREEN sysMetrics[SM_CXVIRTUALSCREEN] /* 77 */
#define SYSMETRICS_CYVIRTUALSCREEN sysMetrics[SM_CYVIRTUALSCREEN] /* 77 */
#define SYSMETRICS_YVIRTUALSCREEN sysMetrics[SM_YVIRTUALSCREEN] /* 78 */
#define SYSMETRICS_XVIRTUALSCREEN sysMetrics[SM_XVIRTUALSCREEN] /* 79 */
#define SYSMETRICS_CMONITORS sysMetrics[SM_CMONITORS] /* 81 */
#define SYSMETRICS_SAMEDISPLAYFORMAT sysMetrics[SM_SAMEDISPLAYFORMAT] /* 82 */
#undef SM_CMETRICS
#define SM_CMETRICS (83)
extern short sysMetrics[SM_CMETRICS+1];
#endif /* __WINE_SYSMETRICS_H */

View File

@@ -0,0 +1,34 @@
#ifndef __WINE_TEXT_H
#define __WINE_TEXT_H
//typedef WINBOOL (CALLBACK *GRAYSTRINGPROC)(HDC,LPARAM,INT);
#define TAB 9
#define LF 10
#define CR 13
#define SPACE 32
#define PREFIX 38
#define SWAP_INT(a,b) { int t = a; a = b; b = t; }
int TEXT_DrawTextEx(HDC hDC,void *strPtr,int nCount,LPRECT lpRect,UINT uFormat,LPDRAWTEXTPARAMS dtp,WINBOOL Unicode );
LPCSTR TEXT_NextLineA( HDC hdc, LPCSTR str, INT *count,
LPSTR dest, INT *len, INT width, WORD format);
LPCWSTR TEXT_NextLineW( HDC hdc, LPCWSTR str, INT *count,
LPWSTR dest, INT *len, INT width, WORD format);
WINBOOL TEXT_GrayString(HDC hdc, HBRUSH hb,
GRAYSTRINGPROC fn, LPARAM lp, INT len,
INT x, INT y, INT cx, INT cy, WINBOOL Unicode);
LONG TEXT_TabbedTextOutA( HDC hdc, INT x, INT y, LPCSTR lpstr,
INT count, INT cTabStops, const INT *lpTabPos,
INT nTabOrg, WINBOOL fDisplayText );
LONG TEXT_TabbedTextOutW( HDC hdc, INT x, INT y, LPCWSTR lpstr,
INT count, INT cTabStops, const INT *lpTabPos,
INT nTabOrg, WINBOOL fDisplayText );
#endif

View File

@@ -0,0 +1,38 @@
#include <user32/win.h>
#include <user32/queue.h>
typedef struct tagTIMER
{
HWND hwnd;
HQUEUE hq;
UINT msg; /* WM_TIMER or WM_SYSTIMER */
UINT id;
UINT timeout;
struct tagTIMER *next;
DWORD expires; /* Next expiration, or 0 if already expired */
TIMERPROC proc;
} TIMER;
#define NB_TIMERS 34
#define NB_RESERVED_TIMERS 2 /* for SetSystemTimer */
#define WM_SYSTIMER 0x0118
void TIMER_InsertTimer( TIMER * pTimer );
void TIMER_RemoveTimer( TIMER * pTimer );
void TIMER_ClearTimer( TIMER * pTimer );
void TIMER_SwitchQueue( HQUEUE old, HQUEUE newQ );
void TIMER_RemoveWindowTimers( HWND hwnd );
void TIMER_RemoveQueueTimers( HQUEUE hqueue );
void TIMER_RestartTimer( TIMER * pTimer, DWORD curTime );
LONG TIMER_GetNextExpiration(void);
void TIMER_ExpireTimers(void);
WINBOOL TIMER_GetTimerMsg( MSG *msg, HWND hwnd,
HQUEUE hQueue,WINBOOL remove );
UINT TIMER_SetTimer( HWND hwnd, UINT id, UINT timeout,
TIMERPROC proc, WINBOOL sys );
WINBOOL TIMER_KillTimer( HWND hwnd, UINT id,WINBOOL sys );

View File

@@ -11,9 +11,12 @@
typedef HANDLE HTASK;
typedef HANDLE HQUEUE;
#define STRING2ATOMA(str) HIWORD(str) ? GlobalFindAtomA(str) : (ATOM)LOWORD(str)
#define STRING2ATOMW(str) HIWORD(str) ? GlobalFindAtomW(str) : (ATOM)LOWORD(str)
#include <user32/class.h>
#include <user32/heapdup.h>
#include <user32/dce.h>
#define WND_MAGIC 0x444e4957 /* 'WIND' */
@@ -56,53 +59,50 @@ struct tagDCE;
struct tagDC;
struct tagCLASS;
typedef struct tagWND
{
struct tagWND *next; /* Next sibling */
struct tagWND *child; /* First child */
struct tagWND *parent; /* Window parent (from CreateWindow) */
struct tagWND *owner; /* Window owner */
struct tagCLASS *class; /* Window class */
struct tagCLASS *class; /* Window class */
void *winproc; /* Window procedure */
DWORD dwMagic; /* Magic number (must be WND_MAGIC) */
HWND hwndSelf; /* Handle of this window */
HINSTANCE hInstance; /* Window hInstance (from CreateWindow) */
RECT rectClient; /* Client area rel. to parent client area */
RECT rectWindow; /* Whole window rel. to parent client area */
LPWSTR text; /* Window text */
HANDLE hmemTaskQ; /* This should be hThread */
DWORD dwMagic; /* Magic number (must be WND_MAGIC) */
HWND hwndSelf; /* Handle of this window */
HINSTANCE hInstance; /* Window hInstance (from CreateWindow) */
RECT rectClient; /* Client area rel. to parent client area */
RECT rectWindow; /* Whole window rel. to parent client area */
LPWSTR text; /* Window text */
void *pVScroll; /* Vertical scroll-bar info */
void *pHScroll; /* Horizontal scroll-bar info */
void *pProp; /* Pointer to properties list */
struct tagDCE *dce; /* Window DCE (if CS_OWNDC or CS_CLASSDC) */
HGLOBAL hmemTaskQ; /* Task queue global memory handle */
HRGN hrgnUpdate; /* Update region */
HRGN hrgnWindow; /* region where the os permits drawing == max update region */
HWND hwndLastActive;/* Last active popup hwnd */
DWORD dwStyle; /* Window style (from CreateWindow) */
DWORD dwExStyle; /* Extended style (from CreateWindowEx) */
UINT wIDmenu; /* ID or hmenu (from CreateWindow) */
DWORD helpContext; /* Help context ID */
WORD flags; /* Misc. flags (see below) */
HMENU hSysMenu; /* window's copy of System Menu */
DWORD userdata; /* User private data */
// struct _WND_DRIVER *pDriver; /* Window driver */
// void *pDriverData; /* Window driver data */
DWORD wExtra[1]; /* Window extra bytes */
HRGN hrgnUpdate; /* Update region */
HRGN hrgnWindow; /* region where the os permits drawing == max update region */
HWND hwndLastActive;/* Last active popup hwnd */
DWORD dwStyle; /* Window style (from CreateWindow) */
DWORD dwExStyle; /* Extended style (from CreateWindowEx) */
UINT wIDmenu; /* ID or hmenu (from CreateWindow) */
DWORD helpContext; /* Help context ID */
WORD flags; /* Misc. flags (see below) */
HMENU hSysMenu; /* window's copy of System Menu */
DWORD userdata; /* User private data */
DWORD wExtra[1]; /* Window extra bytes */
} WND;
typedef struct tagCREATESTRUCTA {
LPVOID lpCreateParams;
HINSTANCE hInstance;
HMENU hMenu;
HWND hwndParent;
HWND hWndParent;
int cy;
int cx;
int y;
int x;
LONG style;
LPCSTR lpszName;
LPCSTR lpszClass;
LPCSTR lpszName;
LPCSTR lpszClass;
DWORD dwExStyle;
} CREATESTRUCTA, *LPCREATESTRUCTA;
@@ -110,7 +110,7 @@ typedef struct tagCREATESTRUCTW {
LPVOID lpCreateParams;
HINSTANCE hInstance;
HMENU hMenu;
HWND hwndParent;
HWND hWndParent;
int cy;
int cx;
int y;
@@ -154,24 +154,7 @@ typedef struct _STARTUPINFOW {
HANDLE hStdError;
} STARTUPINFOW, *LPSTARTUPINFOW;
typedef struct _WND_DRIVER
{
void (*pInitialize)(WND *);
void (*pFinalize)(WND *);
WINBOOL (*pCreateDesktopWindow)(WND *, struct tagCLASS *, WINBOOL);
WINBOOL (*pCreateWindow)(WND *, struct tagCLASS*, CREATESTRUCTW *, WINBOOL);
WINBOOL (*pDestroyWindow)(WND *);
WND* (*pSetParent)(WND *, WND *);
void (*pForceWindowRaise)(WND *);
void (*pSetWindowPos)(WND *, const WINDOWPOS *, WINBOOL);
void (*pSetText)(WND *, LPCSTR);
void (*pSetFocus)(WND *);
void (*pPreSizeMove)(WND *);
void (*pPostSizeMove)(WND *);
void (*pScrollWindow)(WND *, struct tagDC *, INT, INT, const RECT *, WINBOOL);
void (*pSetDrawable)(WND *, struct tagDC *, WORD, WINBOOL);
WINBOOL (*pIsSelfClipping)(WND *);
} WND_DRIVER;
typedef struct
{
@@ -212,11 +195,8 @@ typedef struct
#define GWL_WNDPROC (-4)
/* Window functions */
HWND WIN_CreateWindowEx( CREATESTRUCTW *cs, ATOM classAtom );
HANDLE WIN_CreateWindowEx( CREATESTRUCTW *cs, ATOM atomName );
WND* WIN_FindWndPtr( HWND hwnd );
WND* WIN_GetDesktop(void);
void WIN_DumpWindow( HWND hwnd );
@@ -235,7 +215,7 @@ WND** WIN_BuildWinArray( WND *wndPtr, UINT bwa, UINT* pnum );
void WIN_UpdateNCArea(WND* wnd, WINBOOL bUpdate);
void WIN_SendDestroyMsg( WND* pWnd );
WND* WIN_DestroyWindow( WND* wndPtr );
WINBOOL WIN_DestroyWindow( WND* wndPtr );
HWND WIN_FindWindow( HWND parent, HWND child, ATOM className,
LPCWSTR title );
LONG WIN_GetWindowLong( HWND hwnd, INT offset );

View File

@@ -0,0 +1,84 @@
/*
* *DeferWindowPos() structure and definitions
*
* Copyright 1994 Alexandre Julliard
*/
#ifndef __WINE_WINPOS_H
#define __WINE_WINPOS_H
#include <user32/win.h>
#define DWP_MAGIC ((INT)('W' | ('P' << 8) | ('O' << ) | ('S' << 24)))
/* undocumented SWP flags - from SDK 3.1 */
#define SWP_NOCLIENTSIZE 0x0800
#define SWP_NOCLIENTMOVE 0x1000
#define SWP_DEFERERASE 0x2000
#define HAS_DLGFRAME(style,exStyle) \
(((exStyle) & WS_EX_DLGMODALFRAME) || \
(((style) & WS_DLGFRAME) && !((style) & WS_BORDER)))
#define HAS_THICKFRAME(style) \
(((style) & WS_THICKFRAME) && \
!(((style) & (WS_DLGFRAME|WS_BORDER)) == WS_DLGFRAME))
#define SWP_AGG_NOGEOMETRYCHANGE \
(SWP_NOSIZE | SWP_NOMOVE | SWP_NOCLIENTSIZE | SWP_NOCLIENTMOVE)
#define SWP_AGG_NOPOSCHANGE \
(SWP_AGG_NOGEOMETRYCHANGE | SWP_NOZORDER)
#define SWP_AGG_STATUSFLAGS \
(SWP_AGG_NOPOSCHANGE | SWP_FRAMECHANGED | SWP_HIDEWINDOW | SWP_SHOWWINDOW)
#define EMPTYPOINT(pt) ((*(LONG*)&(pt)) == -1)
#define PLACE_MIN 0x0001
#define PLACE_MAX 0x0002
#define PLACE_RECT 0x0004
#define SMC_NOCOPY 0x0001
#define SMC_NOPARENTERASE 0x0002
#define SMC_DRAWFRAME 0x0004
#define SMC_SETXPOS 0x0008
typedef struct
{
INT actualCount;
INT suggestedCount;
WINBOOL valid;
INT wMagic;
HWND hwndParent;
WINDOWPOS winPos[1];
} DWP;
WINBOOL WINPOS_RedrawIconTitle( HWND hWnd );
WINBOOL WINPOS_ShowIconTitle( WND* pWnd, WINBOOL bShow );
void WINPOS_GetMinMaxInfo( WND* pWnd, POINT *maxSize,
POINT *maxPos, POINT *minTrack,
POINT *maxTrack );
UINT WINPOS_MinMaximize( WND* pWnd, UINT cmd, LPRECT lpPos);
WINBOOL WINPOS_SetActiveWindow( HWND hWnd, WINBOOL fMouse,
WINBOOL fChangeFocus );
WINBOOL WINPOS_ChangeActiveWindow( HWND hwnd, WINBOOL mouseMsg );
LONG WINPOS_SendNCCalcSize(HWND hwnd, WINBOOL calcValidRect,
RECT *newWindowRect, RECT *oldWindowRect,
RECT *oldClientRect, WINDOWPOS *winpos,
RECT *newClientRect );
LONG WINPOS_HandleWindowPosChanging(WND *wndPtr, WINDOWPOS *winpos);
LONG WINPOS_HandleWindowPosChanging(WND *wndPtr, WINDOWPOS *winpos);
INT WINPOS_WindowFromPoint( WND* scopeWnd, POINT pt, WND **ppWnd );
void WINPOS_CheckInternalPos( HWND hwnd );
WINBOOL WINPOS_ActivateOtherWindow(WND* pWnd);
WINBOOL WINPOS_CreateInternalPosAtom(void);
void WINPOS_GetWinOffset( HWND hwndFrom, HWND hwndTo,
POINT *offset );
WINBOOL WINPOS_CanActivate(WND* pWnd);
LPINTERNALPOS WINPOS_InitInternalPos( WND* wnd, POINT pt,
LPRECT restoreRect );
WINBOOL WINPOS_SetPlacement( HWND hwnd, const WINDOWPLACEMENT *wndpl,
UINT flags );
#endif /* __WINE_WINPOS_H */

View File

@@ -7,7 +7,7 @@
#ifndef __WINE_WINPROC_H
#define __WINE_WINPROC_H
//#include "wintypes.h"
#include <windows.h>
typedef enum
{
@@ -41,5 +41,10 @@ WINBOOL WINPROC_SetProc( HWINDOWPROC *pFirst, WNDPROC func,
void WINPROC_FreeProc( HWINDOWPROC proc, WINDOWPROCUSER user );
WINDOWPROCTYPE WINPROC_GetProcType( HWINDOWPROC proc );
INT WINPROC_MapMsg32ATo32W( HWND hwnd, UINT msg, WPARAM wParam, LPARAM *plparam );
void WINPROC_UnmapMsg32ATo32W( HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam );
INT WINPROC_MapMsg32WTo32A( HWND hwnd, UINT msg, WPARAM wParam, LPARAM *plparam );
void WINPROC_UnmapMsg32WTo32A( HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam );
#endif /* __WINE_WINPROC_H */

View File

@@ -0,0 +1,297 @@
/*
* Caret functions
*
* Copyright 1993 David Metcalfe
* Copyright 1996 Frans van Dorsselaer
*/
#include <windows.h>
#include <user32/caret.h>
#include <user32/debug.h>
static CARET Caret = { 0, 0, FALSE, 0, 0, 2, 12, 0, 500, 0 };
WINBOOL STDCALL CreateCaret( HWND hwnd, HBITMAP bitmap,
INT width, INT height )
{
DPRINT("hwnd=%04x\n",(UINT) hwnd);
if (!hwnd) return FALSE;
/* if cursor already exists, destroy it */
if (Caret.hwnd) DestroyCaret();
if (bitmap && ((UINT)bitmap != 1))
{
BITMAP bmp;
if (!GetObject( bitmap, sizeof(bmp), &bmp )) return FALSE;
Caret.width = bmp.bmWidth;
Caret.height = bmp.bmHeight;
/* FIXME: we should make a copy of the bitmap instead of a brush */
Caret.hBrush = CreatePatternBrush( bitmap );
}
else
{
Caret.width = width ? width : GetSystemMetrics(SM_CXBORDER);
Caret.height = height ? height : GetSystemMetrics(SM_CYBORDER);
Caret.hBrush = CreateSolidBrush(bitmap ?
GetSysColor(COLOR_GRAYTEXT) :
GetSysColor(COLOR_WINDOW) );
}
Caret.hwnd = hwnd;
Caret.hidden = 1;
Caret.on = FALSE;
Caret.x = 0;
Caret.y = 0;
Caret.timeout = GetProfileIntA( "windows", "CursorBlinkRate", 500 );
return TRUE;
}
WINBOOL STDCALL DestroyCaret(void)
{
if (!Caret.hwnd) return FALSE;
DPRINT("hwnd=%04x, timerid=%d\n", (UINT)Caret.hwnd,(UINT) Caret.timerid);
CARET_KillTimer();
CARET_DisplayCaret(CARET_OFF);
DeleteObject( Caret.hBrush );
Caret.hwnd = 0;
return TRUE;
}
WINBOOL STDCALL SetCaretPos( INT x, INT y)
{
if (!Caret.hwnd) return FALSE;
if ((x == Caret.x) && (y == Caret.y)) return TRUE;
DPRINT("x=%d, y=%d\n", x, y);
CARET_KillTimer();
CARET_DisplayCaret(CARET_OFF);
Caret.x = x;
Caret.y = y;
if (!Caret.hidden)
{
CARET_DisplayCaret(CARET_ON);
CARET_SetTimer();
}
return TRUE;
}
/*****************************************************************
* HideCaret (USER.317)
*/
WINBOOL STDCALL HideCaret( HWND hwnd )
{
if (!Caret.hwnd) return FALSE;
if (hwnd && (Caret.hwnd != hwnd)) return FALSE;
DPRINT("hwnd=%04x, hidden=%d\n",
hwnd, Caret.hidden);
CARET_KillTimer();
CARET_DisplayCaret(CARET_OFF);
Caret.hidden++;
return TRUE;
}
/*****************************************************************
* ShowCaret (USER.529)
*/
WINBOOL STDCALL ShowCaret( HWND hwnd )
{
if (!Caret.hwnd) return FALSE;
if (hwnd && (Caret.hwnd != hwnd)) return FALSE;
DPRINT("hwnd=%04x, hidden=%d\n",
hwnd, Caret.hidden);
if (Caret.hidden)
{
Caret.hidden--;
if (!Caret.hidden)
{
CARET_DisplayCaret(CARET_ON);
CARET_SetTimer();
}
}
return TRUE;
}
/*****************************************************************
* SetCaretBlinkTime (USER.465)
*/
WINBOOL STDCALL SetCaretBlinkTime( UINT msecs )
{
if (!Caret.hwnd) return FALSE;
DPRINT("hwnd=%04x, msecs=%d\n",
Caret.hwnd, msecs);
Caret.timeout = msecs;
CARET_ResetTimer();
return TRUE;
}
/*****************************************************************
* GetCaretBlinkTime (USER.209)
*/
UINT STDCALL GetCaretBlinkTime(void)
{
return Caret.timeout;
}
/*****************************************************************
* GetCaretPos (USER.210)
*/
WINBOOL STDCALL GetCaretPos( LPPOINT pt )
{
if (!Caret.hwnd || !pt) return FALSE;
pt->x = Caret.x;
pt->y = Caret.y;
return TRUE;
}
/*****************************************************************
* CARET_GetHwnd
*/
HWND CARET_GetHwnd(void)
{
return Caret.hwnd;
}
/*****************************************************************
* CARET_GetRect
*/
void CARET_GetRect(LPRECT lprc)
{
lprc->right = (lprc->left = Caret.x) + Caret.width - 1;
lprc->bottom = (lprc->top = Caret.y) + Caret.height - 1;
}
/*****************************************************************
* CARET_DisplayCaret
*/
void CARET_DisplayCaret( DISPLAY_CARET status )
{
HDC hdc;
HBRUSH hPrevBrush;
if (Caret.on && (status == CARET_ON)) return;
if (!Caret.on && (status == CARET_OFF)) return;
/* So now it's always a toggle */
Caret.on = !Caret.on;
/* do not use DCX_CACHE here, for x,y,width,height are in logical units */
if (!(hdc = GetDCEx( Caret.hwnd, 0, DCX_USESTYLE /*| DCX_CACHE*/ ))) return;
hPrevBrush = SelectObject( hdc, Caret.hBrush );
PatBlt( hdc, Caret.x, Caret.y, Caret.width, Caret.height, PATINVERT );
SelectObject( hdc, hPrevBrush );
ReleaseDC( Caret.hwnd, hdc );
}
/*****************************************************************
* CARET_Callback
*/
VOID CALLBACK CARET_Callback( HWND hwnd, UINT msg, UINT id, DWORD ctime)
{
DPRINT("hwnd=%04x, timerid=%d, caret=%d\n", hwnd, id, Caret.on);
CARET_DisplayCaret(CARET_TOGGLE);
}
/*****************************************************************
* CARET_SetTimer
*/
void CARET_SetTimer(void)
{
if (Caret.timerid)
KillTimer( (HWND)0, Caret.timerid );
Caret.timerid = SetTimer( (HWND)0, 0, Caret.timeout,CARET_Callback );
}
/*****************************************************************
* CARET_ResetTimer
*/
void CARET_ResetTimer(void)
{
if (Caret.timerid)
{
KillTimer( (HWND)0, Caret.timerid );
Caret.timerid = SetTimer( (HWND)0, 0, Caret.timeout,
CARET_Callback );
}
}
/*****************************************************************
* CARET_KillTimer
*/
void CARET_KillTimer(void)
{
if (Caret.timerid)
{
KillTimer( (HWND)0, Caret.timerid );
Caret.timerid = 0;
}
}
/**********************************************************************
* CreateIconFromResource (USER32.76)
*/
HICON STDCALL CreateIconFromResource( LPBYTE bits, UINT cbSize,
WINBOOL bIcon, DWORD dwVersion)
{
return CreateIconFromResourceEx( bits, cbSize, bIcon, dwVersion, 0,0,0);
}
/**********************************************************************
* CreateIconFromResourceEx (USER32.77)
*/
HICON STDCALL CreateIconFromResourceEx( LPBYTE bits, UINT cbSize,
WINBOOL bIcon, DWORD dwVersion,
INT width, INT height,
UINT cFlag )
{
/*
TDB* pTask = (TDB*)GlobalLock( GetCurrentTask() );
if( pTask )
return CURSORICON_CreateFromResource( pTask->hInstance, 0, bits, cbSize, bIcon, dwVersion,
width, height, cFlag );
*/
return 0;
}

View File

@@ -0,0 +1,22 @@
#include <windows.h>
WINBOOL STDCALL DrawEdge( HDC hdc, LPRECT rc, UINT edge, UINT flags )
{
}
WINBOOL
STDCALL
DrawIconEx(HDC hdc, int xLeft, int yTop,
HICON hIcon, int cxWidth, int cyWidth,
UINT istepIfAniCur, HBRUSH hbrFlickerFreeDraw, UINT diFlags)
{
}
WINBOOL
STDCALL
DrawFocusRect(
HDC hDC,
CONST RECT * lprc)
{
}

View File

@@ -0,0 +1,20 @@
#include <windows.h>
INT STDCALL FillRect( HDC hdc, const RECT *rect, HBRUSH hbrush )
{
HBRUSH prevBrush;
if (!(prevBrush = SelectObject( hdc, hbrush ))) return 0;
PatBlt( hdc, rect->left, rect->top,
rect->right - rect->left, rect->bottom - rect->top, PATCOPY );
SelectObject( hdc, prevBrush );
return 1;
}
WINBOOL STDCALL InvertRect( HDC hDC, CONST RECT *lprc)
{
return PatBlt( hDC, lprc->left, lprc->top,
lprc->right - lprc->left, lprc->bottom - lprc->top, DSTINVERT );
}

View File

@@ -0,0 +1,251 @@
/*
* Rectangle-related functions
*
* CopyxRight 1993, 1996 Alexandre Julliard
*
*/
#include <windows.h>
WINBOOL
STDCALL
SetRect(
LPRECT lprc,
int xLeft,
int yTop,
int xRight,
int yBottom)
{
if ( lprc == NULL )
return FALSE;
lprc->left = xLeft;
lprc->right = xRight;
lprc->top = yTop;
lprc->bottom = yBottom;
return TRUE;
}
/***********************************************************************
* SetRectEmpty32 (USER32.500)
*/
WINBOOL STDCALL SetRectEmpty( LPRECT lprc )
{
if ( lprc == NULL )
return FALSE;
lprc->left = lprc->right = lprc->top = lprc->bottom = 0;
return TRUE;
}
//added memcpy and check BD
/***********************************************************************
* CopyRect32 (USER32.62)
*/
WINBOOL
STDCALL
CopyRect(
LPRECT lprcDst,
CONST RECT *lprcSrc)
{
if ( lprcDst == NULL || lprcSrc == NULL )
return FALSE;
*lprcDst = *lprcSrc;
return TRUE;
}
/***********************************************************************
* IsRectEmpty32 (USER32.347)
*/
WINBOOL STDCALL IsRectEmpty( const RECT *lprc )
{
if ( lprc == NULL )
return TRUE;
return ((lprc->left == lprc->right) || (lprc->top == lprc->bottom));
}
/***********************************************************************
* PtInRect32 (USER32.424)
*/
WINBOOL
STDCALL
PtInRect(
CONST RECT *lprc,
POINT pt)
{
return ((pt.x >= lprc->left) && (pt.x < lprc->right) &&
(pt.y >= lprc->top) && (pt.y < lprc->bottom));
}
/***********************************************************************
* OffsetRect32 (USER32.406)
*/
WINBOOL
STDCALL
OffsetRect(
LPRECT lprc,
int dx,
int dy)
{
if ( lprc == NULL )
return FALSE;
lprc->left += dx;
lprc->right += dx;
lprc->top += dy;
lprc->bottom += dy;
return TRUE;
}
/***********************************************************************
* InflateRect32 (USER32.321)
*/
WINBOOL STDCALL InflateRect( LPRECT lprc, INT dx, INT dy )
{
lprc->left -= dx;
lprc->top -= dy;
lprc->right += dx;
lprc->bottom += dy;
return TRUE;
}
/***********************************************************************
* IntersectRect32 (USER32.327)
*/
WINBOOL
STDCALL
IntersectRect(
LPRECT lprcDst,
CONST RECT *lprcSrc1,
CONST RECT *lprcSrc2)
{
if (IsRectEmpty(lprcSrc1) || IsRectEmpty(lprcSrc2) ||
(lprcSrc1->left >= lprcSrc2->right) || (lprcSrc2->left >= lprcSrc1->right) ||
(lprcSrc1->top >= lprcSrc2->bottom) || (lprcSrc2->top >= lprcSrc1->bottom))
{
SetRectEmpty( lprcDst );
return FALSE;
}
lprcDst->left = max( lprcSrc1->left, lprcSrc2->left );
lprcDst->right = min( lprcSrc1->right, lprcSrc2->right );
lprcDst->top = max( lprcSrc1->top, lprcSrc2->top );
lprcDst->bottom = min( lprcSrc1->bottom, lprcSrc2->bottom );
return TRUE;
}
/***********************************************************************
* UnionRect32 (USER32.559)
*/
WINBOOL STDCALL UnionRect( LPRECT lprcDst, const RECT *lprcSrc1,
const RECT *lprcSrc2 )
{
if (IsRectEmpty(lprcSrc1))
{
if (IsRectEmpty(lprcSrc2))
{
SetRectEmpty( lprcDst );
return FALSE;
}
else *lprcDst = *lprcSrc2;
}
else
{
if (IsRectEmpty(lprcSrc2))
*lprcDst = *lprcSrc1;
else
{
lprcDst->left = min( lprcSrc1->left, lprcSrc2->left );
lprcDst->right = max( lprcSrc1->right, lprcSrc2->right );
lprcDst->top = min( lprcSrc1->top, lprcSrc2->top );
lprcDst->bottom = max( lprcSrc1->bottom, lprcSrc2->bottom );
}
}
return TRUE;
}
/***********************************************************************
* EqualRect32 (USER32.194)
*/
WINBOOL
STDCALL
EqualRect(
CONST RECT *lprc1,
CONST RECT *lprc2)
{
return ((lprc1->left == lprc2->left) && (lprc1->right == lprc2->right) &&
(lprc1->top == lprc2->top) && (lprc1->bottom == lprc2->bottom));
}
/***********************************************************************
* SubtractRect32 (USER32.536)
*/
WINBOOL
STDCALL
SubtractRect(
LPRECT lprcDst,
CONST RECT *lprcSrc1,
CONST RECT *lprcSrc2)
{
RECT tmp;
if (IsRectEmpty( lprcSrc1 ))
{
SetRectEmpty( lprcDst );
return FALSE;
}
// changed BD
CopyRect(lprcDst,lprcSrc1);
if (IntersectRect( &tmp, lprcSrc1, lprcSrc2 ))
{
if (EqualRect( &tmp, lprcDst ))
{
SetRectEmpty( lprcDst );
return FALSE;
}
if ((tmp.top == lprcDst->top) && (tmp.bottom == lprcDst->bottom))
{
if (tmp.left == lprcDst->left) lprcDst->left = tmp.right;
else if (tmp.right == lprcDst->right) lprcDst->right = tmp.left;
}
else if ((tmp.left == lprcDst->left) && (tmp.right == lprcDst->right))
{
if (tmp.top == lprcDst->top) lprcDst->top = tmp.bottom;
else if (tmp.bottom == lprcDst->bottom) lprcDst->bottom = tmp.top;
}
}
return TRUE;
}

View File

@@ -0,0 +1,95 @@
/*
* Support for system colors
*
* Copyright David W. Metcalfe, 1993
* Copyright Alexandre Julliard, 1994
*
*/
#include <windows.h>
//#include <user32/syscolor.h>
void SYSCOLOR_SetColor( int index, COLORREF color );
//#define NUM_SYS_COLORS (COLOR_GRADIENTINACTIVECAPTION+1)
#define NUM_SYS_COLORS 100
static COLORREF SysColors[NUM_SYS_COLORS];
static HBRUSH SysColorBrushes[NUM_SYS_COLORS];
static HPEN SysColorPens[NUM_SYS_COLORS];
DWORD STDCALL GetSysColor( INT nIndex )
{
if (nIndex >= 0 && nIndex < NUM_SYS_COLORS)
return SysColors[nIndex];
else
return 0;
}
/*************************************************************************
* SetSysColors (USER.505)
*/
WINBOOL STDCALL SetSysColors( INT nChanges, const INT *lpSysColor,
const COLORREF *lpColorValues )
{
int i;
for (i = 0; i < nChanges; i++)
{
SYSCOLOR_SetColor( lpSysColor[i], lpColorValues[i] );
}
/* Send WM_SYSCOLORCHANGE message to all windows */
SendMessageA( HWND_BROADCAST, WM_SYSCOLORCHANGE, 0, 0 );
/* Repaint affected portions of all visible windows */
RedrawWindow( GetDesktopWindow(), NULL, 0,
RDW_INVALIDATE | RDW_ERASE | RDW_UPDATENOW | RDW_ALLCHILDREN );
return TRUE;
}
HBRUSH STDCALL GetSysColorBrush( INT index )
{
if (0 <= index && index < NUM_SYS_COLORS)
return SysColorBrushes[index];
return GetStockObject(LTGRAY_BRUSH);
}
/////////////////////////////////////////////////////////////////////////////////////
void SYSCOLOR_SetColor( int index, COLORREF color )
{
if (index < 0 || index >= NUM_SYS_COLORS) return;
SysColors[index] = color;
if (SysColorBrushes[index]) DeleteObject( SysColorBrushes[index] );
SysColorBrushes[index] = CreateSolidBrush( color );
if (SysColorPens[index]) DeleteObject( SysColorPens[index] );
SysColorPens[index] = CreatePen( PS_SOLID, 1, color );
}
/***********************************************************************
* GetSysColorPen (Not a Windows API)
*
* This function is new to the Wine lib -- it does not exist in
* Windows. However, it is a natural complement for GetSysColorBrush
* in the Win API and is needed quite a bit inside Wine.
*/
HPEN STDCALL GetSysColorPen( INT index )
{
/* We can assert here, because this function is internal to Wine */
//assert (0 <= index && index < NUM_SYS_COLORS);
return SysColorPens[index];
}

View File

@@ -0,0 +1,28 @@
#include <windows.h>
int
STDCALL
DrawTextA(
HDC hDC,LPCSTR lpString,
int nCount, LPRECT lpRect, UINT uFormat)
{
DRAWTEXTPARAMS dtp;
dtp.cbSize = sizeof(DRAWTEXTPARAMS);
dtp.iTabLength = 0;
//return TEXT_DrawTextEx(hDC,(void *)lpString, nCount,lpRect,uFormat, &dtp, FALSE);
}
int
STDCALL
DrawTextW(
HDC hDC, LPCWSTR lpString,
int nCount, LPRECT lpRect, UINT uFormat)
{
DRAWTEXTPARAMS dtp;
dtp.cbSize = sizeof(DRAWTEXTPARAMS);
dtp.iTabLength = 0;
return TEXT_DrawTextEx(hDC,(void *)lpString,nCount,lpRect,uFormat, &dtp,TRUE);
}

View File

@@ -0,0 +1,320 @@
#include <windows.h>
#include <user32/dce.h>
#include <user32/win.h>
DCE *firstDCE = 0;
HDC defaultDCstate = 0;
/***********************************************************************
* DCE_AllocDCE
*
* Allocate a new DCE.
*/
DCE *DCE_AllocDCE( HWND hWnd, DCE_TYPE type )
{
DCE * dce;
if (!(dce = HeapAlloc( GetProcessHeap(), 0, sizeof(DCE) ))) return NULL;
if (!(dce->hDC = CreateDC( "DISPLAY", NULL, NULL, NULL )))
{
HeapFree( GetProcessHeap(), 0, dce );
return 0;
}
/* store DCE handle in DC hook data field */
//SetDCHook( dce->hDC, (FARPROC)DCHook, (DWORD)dce );
dce->hwndCurrent = hWnd;
dce->hClipRgn = 0;
dce->next = firstDCE;
firstDCE = dce;
if( type != DCE_CACHE_DC ) /* owned or class DC */
{
dce->DCXflags = DCX_DCEBUSY;
if( hWnd )
{
WND* wnd = WIN_FindWndPtr(hWnd);
if( wnd->dwStyle & WS_CLIPCHILDREN ) dce->DCXflags |= DCX_CLIPCHILDREN;
if( wnd->dwStyle & WS_CLIPSIBLINGS ) dce->DCXflags |= DCX_CLIPSIBLINGS;
}
//SetHookFlags(dce->hDC,DCHF_INVALIDATEVISRGN);
}
else dce->DCXflags = DCX_CACHE | DCX_DCEEMPTY;
return dce;
}
/***********************************************************************
* DCE_FreeDCE
*/
DCE* DCE_FreeDCE( DCE *dce )
{
DCE **ppDCE = &firstDCE;
if (!dce) return NULL;
while (*ppDCE && (*ppDCE != dce)) ppDCE = &(*ppDCE)->next;
if (*ppDCE == dce) *ppDCE = dce->next;
// SetDCHook(dce->hDC, NULL, 0L);
DeleteDC( dce->hDC );
if( dce->hClipRgn && !(dce->DCXflags & DCX_KEEPCLIPRGN) )
DeleteObject(dce->hClipRgn);
HeapFree( GetProcessHeap(), 0, dce );
return *ppDCE;
}
/***********************************************************************
* DCE_DeleteClipRgn
*/
void DCE_DeleteClipRgn( DCE* dce )
{
dce->DCXflags &= ~(DCX_EXCLUDERGN | DCX_INTERSECTRGN | DCX_WINDOWPAINT);
if( dce->DCXflags & DCX_KEEPCLIPRGN )
dce->DCXflags &= ~DCX_KEEPCLIPRGN;
else
if( dce->hClipRgn > 1 )
DeleteObject( dce->hClipRgn );
dce->hClipRgn = 0;
//TRACE(dc,"\trestoring VisRgn\n");
RestoreVisRgn(dce->hDC);
}
/***********************************************************************
* DCE_GetVisRect
*
* Calculate the visible rectangle of a window (i.e. the client or
* window area clipped by the client area of all ancestors) in the
* corresponding coordinates. Return FALSE if the visible region is empty.
*/
WINBOOL DCE_GetVisRect( WND *wndPtr, WINBOOL clientArea, RECT *lprect )
{
*lprect = clientArea ? wndPtr->rectClient : wndPtr->rectWindow;
if (wndPtr->dwStyle & WS_VISIBLE)
{
INT xoffset = lprect->left;
INT yoffset = lprect->top;
while (wndPtr->dwStyle & WS_CHILD)
{
wndPtr = wndPtr->parent;
if ( (wndPtr->dwStyle & (WS_ICONIC | WS_VISIBLE)) != WS_VISIBLE )
goto fail;
xoffset += wndPtr->rectClient.left;
yoffset += wndPtr->rectClient.top;
OffsetRect( lprect, wndPtr->rectClient.left,
wndPtr->rectClient.top );
if( (wndPtr->rectClient.left >= wndPtr->rectClient.right) ||
(wndPtr->rectClient.top >= wndPtr->rectClient.bottom) ||
(lprect->left >= wndPtr->rectClient.right) ||
(lprect->right <= wndPtr->rectClient.left) ||
(lprect->top >= wndPtr->rectClient.bottom) ||
(lprect->bottom <= wndPtr->rectClient.top) )
goto fail;
lprect->left = max( lprect->left, wndPtr->rectClient.left );
lprect->right = min( lprect->right, wndPtr->rectClient.right );
lprect->top = max( lprect->top, wndPtr->rectClient.top );
lprect->bottom = min( lprect->bottom, wndPtr->rectClient.bottom );
}
OffsetRect( lprect, -xoffset, -yoffset );
return TRUE;
}
fail:
SetRectEmpty( lprect );
return FALSE;
}
/***********************************************************************
* DCE_AddClipRects
*
* Go through the linked list of windows from pWndStart to pWndEnd,
* adding to the clip region the intersection of the target rectangle
* with an offset window rectangle.
*/
WINBOOL DCE_AddClipRects( WND *pWndStart, WND *pWndEnd,
HRGN hrgnClip, LPRECT lpRect, int x, int y )
{
RECT rect;
// if( pWndStart->pDriver->pIsSelfClipping( pWndStart ) )
// return TRUE; /* The driver itself will do the clipping */
for (; pWndStart != pWndEnd; pWndStart = pWndStart->next)
{
if( !(pWndStart->dwStyle & WS_VISIBLE) ) continue;
rect.left = pWndStart->rectWindow.left + x;
rect.top = pWndStart->rectWindow.top + y;
rect.right = pWndStart->rectWindow.right + x;
rect.bottom = pWndStart->rectWindow.bottom + y;
if( IntersectRect( &rect, &rect, lpRect ))
if(!REGION_UnionRectWithRgn( hrgnClip, &rect ))
break;
}
return (pWndStart == pWndEnd);
}
/***********************************************************************
* DCE_GetVisRgn
*
* Return the visible region of a window, i.e. the client or window area
* clipped by the client area of all ancestors, and then optionally
* by siblings and children.
*/
HRGN DCE_GetVisRgn( HWND hwnd, WORD flags )
{
HRGN hrgnVis = 0;
RECT rect;
WND *wndPtr = WIN_FindWndPtr( hwnd );
/* Get visible rectangle and create a region with it. */
if (wndPtr && DCE_GetVisRect(wndPtr, !(flags & DCX_WINDOW), &rect))
{
if((hrgnVis = CreateRectRgnIndirect( &rect )))
{
HRGN hrgnClip = CreateRectRgn( 0, 0, 0, 0 );
INT xoffset, yoffset;
if( hrgnClip )
{
/* Compute obscured region for the visible rectangle by
* clipping children, siblings, and ancestors. Note that
* DCE_GetVisRect() returns a rectangle either in client
* or in window coordinates (for DCX_WINDOW request). */
if( (flags & DCX_CLIPCHILDREN) && wndPtr->child )
{
if( flags & DCX_WINDOW )
{
/* adjust offsets since child window rectangles are
* in client coordinates */
xoffset = wndPtr->rectClient.left - wndPtr->rectWindow.left;
yoffset = wndPtr->rectClient.top - wndPtr->rectWindow.top;
}
else
xoffset = yoffset = 0;
DCE_AddClipRects( wndPtr->child, NULL, hrgnClip,
&rect, xoffset, yoffset );
}
/* sibling window rectangles are in client
* coordinates of the parent window */
if (flags & DCX_WINDOW)
{
xoffset = -wndPtr->rectWindow.left;
yoffset = -wndPtr->rectWindow.top;
}
else
{
xoffset = -wndPtr->rectClient.left;
yoffset = -wndPtr->rectClient.top;
}
if (flags & DCX_CLIPSIBLINGS && wndPtr->parent )
DCE_AddClipRects( wndPtr->parent->child,
wndPtr, hrgnClip, &rect, xoffset, yoffset );
/* Clip siblings of all ancestors that have the
* WS_CLIPSIBLINGS style
*/
while (wndPtr->dwStyle & WS_CHILD)
{
wndPtr = wndPtr->parent;
xoffset -= wndPtr->rectClient.left;
yoffset -= wndPtr->rectClient.top;
if(wndPtr->dwStyle & WS_CLIPSIBLINGS && wndPtr->parent)
{
DCE_AddClipRects( wndPtr->parent->child, wndPtr,
hrgnClip, &rect, xoffset, yoffset );
}
}
/* Now once we've got a jumbo clip region we have
* to substract it from the visible rectangle.
*/
CombineRgn( hrgnVis, hrgnVis, hrgnClip, RGN_DIFF );
DeleteObject( hrgnClip );
}
else
{
DeleteObject( hrgnVis );
hrgnVis = 0;
}
}
}
else
hrgnVis = CreateRectRgn(0, 0, 0, 0); /* empty */
return hrgnVis;
}
/***********************************************************************
* DCE_OffsetVisRgn
*
* Change region from DC-origin relative coordinates to screen coords.
*/
void DCE_OffsetVisRgn( HDC hDC, HRGN hVisRgn )
{
/*
DC *dc;
if (!(dc = (DC *) GDI_GetObjPtr( hDC, DC_MAGIC ))) return;
OffsetRgn( hVisRgn, dc->w.DCOrgX, dc->w.DCOrgY );
GDI_HEAP_UNLOCK( hDC );
*/
}
/***********************************************************************
* DCE_ExcludeRgn
*
* Translate given region from the wnd client to the DC coordinates
* and add it to the clipping region.
*/
INT DCE_ExcludeRgn( HDC hDC, WND* wnd, HRGN hRgn )
{
POINT pt = {0, 0};
DCE *dce = firstDCE;
while (dce && (dce->hDC != hDC)) dce = dce->next;
if( dce )
{
MapWindowPoints( wnd->hwndSelf, dce->hwndCurrent, &pt, 1);
if( dce->DCXflags & DCX_WINDOW )
{
wnd = WIN_FindWndPtr(dce->hwndCurrent);
pt.x += wnd->rectClient.left - wnd->rectWindow.left;
pt.y += wnd->rectClient.top - wnd->rectWindow.top;
}
}
else return ERROR;
OffsetRgn(hRgn, pt.x, pt.y);
return ExtSelectClipRgn( hDC, hRgn, RGN_DIFF );
}

View File

@@ -0,0 +1,399 @@
/*
* Default window procedure
*
* Copyright 1993, 1996 Alexandre Julliard
* 1995 Alex Korobka
*/
#include <stdlib.h>
#include <user32/win.h>
#include "user.h"
#include "heap.h"
#include "nonclient.h"
#include "winpos.h"
#include "dce.h"
#include "sysmetrics.h"
#include "debug.h"
#include "spy.h"
#include "tweak.h"
#include "wine/winuser.h"
/* Last COLOR id */
#define COLOR_MAX COLOR_BTNHIGHLIGHT
/* bits in the dwKeyData */
#define KEYDATA_ALT 0x2000
#define KEYDATA_PREVSTATE 0x4000
static short iF10Key = 0;
static short iMenuSysKey = 0;
/***********************************************************************
* DEFWND_HandleWindowPosChanged
*
* Handle the WM_WINDOWPOSCHANGED message.
*/
static void DEFWND_HandleWindowPosChanged( WND *wndPtr, UINT flags )
{
WPARAM wp = SIZE_RESTORED;
if (!(flags & SWP_NOCLIENTMOVE))
SendMessage( wndPtr->hwndSelf, WM_MOVE, 0,
MAKELONG(wndPtr->rectClient.left, wndPtr->rectClient.top));
if (!(flags & SWP_NOCLIENTSIZE))
{
if (wndPtr->dwStyle & WS_MAXIMIZE) wp = SIZE_MAXIMIZED;
else if (wndPtr->dwStyle & WS_MINIMIZE) wp = SIZE_MINIMIZED;
SendMessage( wndPtr->hwndSelf, WM_SIZE, wp,
MAKELONG(wndPtr->rectClient.right-wndPtr->rectClient.left,
wndPtr->rectClient.bottom-wndPtr->rectClient.top));
}
}
/***********************************************************************
* DEFWND_SetText
*
* Set the window text.
*/
void DEFWND_SetTextA( WND *wndPtr, LPCSTR text )
{
if (!text) text = "";
if (wndPtr->text) HeapFree( GetProcessHeap(), 0, wndPtr->text );
wndPtr->text = HEAP_strdupA( GetProcessHeap(), 0, text );
wndPtr->pDriver->pSetText(wndPtr, wndPtr->text);
}
void DEFWND_SetTextW( WND *wndPtr, LPCSTR text )
{
if (!text) text = "";
if (wndPtr->text) HeapFree( GetProcessHeap(), 0, wndPtr->text );
wndPtr->text = HEAP_strdupW( GetProcessHeap(), 0, text );
}
/***********************************************************************
* DEFWND_ControlColor
*
* Default colors for control painting.
*/
HBRUSH DEFWND_ControlColor( HDC hDC, UINT ctlType )
{
if( ctlType == CTLCOLOR_SCROLLBAR)
{
HBRUSH hb = GetSysColorBrush(COLOR_SCROLLBAR);
SetBkColor( hDC, RGB(255, 255, 255) );
SetTextColor( hDC, RGB(0, 0, 0) );
UnrealizeObject( hb );
return hb;
}
SetTextColor( hDC, GetSysColor(COLOR_WINDOWTEXT));
if (TWEAK_WineLook > WIN31_LOOK) {
if ((ctlType == CTLCOLOR_EDIT) || (ctlType == CTLCOLOR_LISTBOX))
SetBkColor( hDC, GetSysColor(COLOR_WINDOW) );
else {
SetBkColor( hDC, GetSysColor(COLOR_3DFACE) );
return GetSysColorBrush(COLOR_3DFACE);
}
}
else
SetBkColor( hDC, GetSysColor(COLOR_WINDOW) );
return GetSysColorBrush(COLOR_WINDOW);
}
/***********************************************************************
* DEFWND_SetRedraw
*/
static void DEFWND_SetRedraw( WND* wndPtr, WPARAM wParam )
{
WINBOOL bVisible = wndPtr->dwStyle & WS_VISIBLE;
TRACE(win,"%04x %i\n", wndPtr->hwndSelf, (wParam!=0) );
if( wParam )
{
if( !bVisible )
{
wndPtr->dwStyle |= WS_VISIBLE;
DCE_InvalidateDCE( wndPtr, &wndPtr->rectWindow );
}
}
else if( bVisible )
{
if( wndPtr->dwStyle & WS_MINIMIZE ) wParam = RDW_VALIDATE;
else wParam = RDW_ALLCHILDREN | RDW_VALIDATE;
PAINT_RedrawWindow( wndPtr->hwndSelf, NULL, 0, wParam, 0 );
DCE_InvalidateDCE( wndPtr, &wndPtr->rectWindow );
wndPtr->dwStyle &= ~WS_VISIBLE;
}
}
/***********************************************************************
* DEFWND_DefWinProc
*
* Default window procedure for messages that are the same in Win and Win.
*/
static LRESULT DEFWND_DefWinProc( WND *wndPtr, UINT msg, WPARAM wParam,
LPARAM lParam )
{
switch(msg)
{
case WM_NCPAINT:
return NC_HandleNCPaint( wndPtr->hwndSelf, (HRGN)wParam );
case WM_NCHITTEST:
return NC_HandleNCHitTest( wndPtr->hwndSelf, MAKEPOINT(lParam) );
case WM_NCLBUTTONDOWN:
return NC_HandleNCLButtonDown( wndPtr, wParam, lParam );
case WM_LBUTTONDBLCLK:
case WM_NCLBUTTONDBLCLK:
return NC_HandleNCLButtonDblClk( wndPtr, wParam, lParam );
case WM_RBUTTONDOWN:
case WM_NCRBUTTONDOWN:
if ((wndPtr->flags & WIN_ISWIN) || (TWEAK_WineLook > WIN31_LOOK))
{
ClientToScreen(wndPtr->hwndSelf, (LPPOINT)&lParam);
SendMessageA( wndPtr->hwndSelf, WM_CONTEXTMENU,
wndPtr->hwndSelf, lParam);
}
break;
case WM_CONTEXTMENU:
if( wndPtr->dwStyle & WS_CHILD )
SendMessageA( wndPtr->parent->hwndSelf, msg, wParam, lParam );
else
if (wndPtr->hSysMenu)
{ /*
TrackPopupMenu(wndPtr->hSysMenu,TPM_LEFTALIGN | TPM_RETURNCMD,LOWORD(lParam),HIWORD(lParam),0,wndPtr->hwndSelf,NULL);
DestroyMenu(wndPtr->hSysMenu);
*/
FIXME(win,"Display default popup menu\n");
/* Track system popup if click was in the caption area. */
}
break;
case WM_NCACTIVATE:
return NC_HandleNCActivate( wndPtr, wParam );
case WM_NCDESTROY:
if (wndPtr->text) HeapFree( GetProcessHeap(), 0, wndPtr->text );
wndPtr->text = NULL;
if (wndPtr->pVScroll) HeapFree( GetProcessHeap(), 0, wndPtr->pVScroll );
if (wndPtr->pHScroll) HeapFree( GetProcessHeap(), 0, wndPtr->pHScroll );
wndPtr->pVScroll = wndPtr->pHScroll = NULL;
return 0;
case WM_PAINTICON:
case WM_PAINT:
{
PAINTSTRUCT ps;
HDC hdc = BeginPaint( wndPtr->hwndSelf, &ps );
if( hdc )
{
if( (wndPtr->dwStyle & WS_MINIMIZE) && wndPtr->class->hIcon )
{
int x = (wndPtr->rectWindow.right - wndPtr->rectWindow.left -
SYSMETRICS_CXICON)/2;
int y = (wndPtr->rectWindow.bottom - wndPtr->rectWindow.top -
SYSMETRICS_CYICON)/2;
TRACE(win,"Painting class icon: vis rect=(%i,%i - %i,%i)\n",
ps.rcPaint.left, ps.rcPaint.top, ps.rcPaint.right, ps.rcPaint.bottom );
DrawIcon( hdc, x, y, wndPtr->class->hIcon );
}
EndPaint( wndPtr->hwndSelf, &ps );
}
return 0;
}
case WM_SETREDRAW:
DEFWND_SetRedraw( wndPtr, wParam );
return 0;
case WM_CLOSE:
DestroyWindow( wndPtr->hwndSelf );
return 0;
case WM_MOUSEACTIVATE:
if (wndPtr->dwStyle & WS_CHILD)
{
LONG ret = SendMessage( wndPtr->parent->hwndSelf,
WM_MOUSEACTIVATE, wParam, lParam );
if (ret) return ret;
}
/* Caption clicks are handled by the NC_HandleNCLButtonDown() */
return (LOWORD(lParam) == HTCAPTION) ? MA_NOACTIVATE : MA_ACTIVATE;
case WM_ACTIVATE:
if (LOWORD(wParam) != WA_INACTIVE)
SetWindowPos(wndPtr->hwndSelf, HWND_TOP, 0, 0, 0, 0,
SWP_NOMOVE | SWP_NOSIZE);
break;
case WM_ERASEBKGND:
case WM_ICONERASEBKGND:
{
if (!wndPtr->class->hbrBackground) return 0;
if (wndPtr->class->hbrBackground <= (HBRUSH)(COLOR_MAX+1))
{
HBRUSH hbrush = CreateSolidBrush(
GetSysColor(((DWORD)wndPtr->class->hbrBackground)-1));
FillWindow( GetParent(wndPtr->hwndSelf), wndPtr->hwndSelf,
(HDC)wParam, hbrush);
DeleteObject( hbrush );
}
else FillWindow( GetParent(wndPtr->hwndSelf), wndPtr->hwndSelf,
(HDC)wParam, wndPtr->class->hbrBackground );
return 1;
}
case WM_GETDLGCODE:
return 0;
case WM_CTLCOLORMSGBOX:
case WM_CTLCOLOREDIT:
case WM_CTLCOLORLISTBOX:
case WM_CTLCOLORBTN:
case WM_CTLCOLORDLG:
case WM_CTLCOLORSTATIC:
case WM_CTLCOLORSCROLLBAR:
return (LRESULT)DEFWND_ControlColor( (HDC)wParam, msg - WM_CTLCOLORMSGBOX );
case WM_CTLCOLOR:
return (LRESULT)DEFWND_ControlColor( (HDC)wParam, HIWORD(lParam) );
case WM_GETTEXTLENGTH:
if (wndPtr->text) return (LRESULT)strlen(wndPtr->text);
return 0;
case WM_SETCURSOR:
if (wndPtr->dwStyle & WS_CHILD)
if (SendMessage(wndPtr->parent->hwndSelf, WM_SETCURSOR,
wParam, lParam))
return TRUE;
return NC_HandleSetCursor( wndPtr->hwndSelf, wParam, lParam );
case WM_SYSCOMMAND:
return NC_HandleSysCommand( wndPtr->hwndSelf, wParam,
MAKEPOINT(lParam) );
case WM_KEYDOWN:
if(wParam == VK_F10) iF10Key = VK_F10;
break;
case WM_SYSKEYDOWN:
if( HIWORD(lParam) & KEYDATA_ALT )
{
/* if( HIWORD(lParam) & ~KEYDATA_PREVSTATE ) */
if( wParam == VK_MENU && !iMenuSysKey )
iMenuSysKey = 1;
else
iMenuSysKey = 0;
iF10Key = 0;
if( wParam == VK_F4 ) /* try to close the window */
{
HWND hWnd = WIN_GetTopParent( wndPtr->hwndSelf );
wndPtr = WIN_FindWndPtr( hWnd );
if( wndPtr && !(wndPtr->class->style & CS_NOCLOSE) )
PostMessage( hWnd, WM_SYSCOMMAND, SC_CLOSE, 0 );
}
}
else if( wParam == VK_F10 )
iF10Key = 1;
else
if( wParam == VK_ESCAPE && (GetKeyState(VK_SHIFT) & 0x8000))
SendMessage( wndPtr->hwndSelf, WM_SYSCOMMAND,
(WPARAM)SC_KEYMENU, (LPARAM)VK_SPACE);
break;
case WM_KEYUP:
case WM_SYSKEYUP:
/* Press and release F10 or ALT */
if (((wParam == VK_MENU) && iMenuSysKey) ||
((wParam == VK_F10) && iF10Key))
SendMessage( WIN_GetTopParent(wndPtr->hwndSelf),
WM_SYSCOMMAND, SC_KEYMENU, 0L );
iMenuSysKey = iF10Key = 0;
break;
case WM_SYSCHAR:
iMenuSysKey = 0;
if (wParam == VK_RETURN && (wndPtr->dwStyle & WS_MINIMIZE))
{
PostMessage( wndPtr->hwndSelf, WM_SYSCOMMAND,
(WPARAM)SC_RESTORE, 0L );
break;
}
if ((HIWORD(lParam) & KEYDATA_ALT) && wParam)
{
if (wParam == VK_TAB || wParam == VK_ESCAPE) break;
if (wParam == VK_SPACE && (wndPtr->dwStyle & WS_CHILD))
SendMessage( wndPtr->parent->hwndSelf, msg, wParam, lParam );
else
SendMessage( wndPtr->hwndSelf, WM_SYSCOMMAND,
(WPARAM)SC_KEYMENU, (LPARAM)(DWORD)wParam );
}
else /* check for Ctrl-Esc */
if (wParam != VK_ESCAPE) MessageBeep(0);
break;
case WM_SHOWWINDOW:
if (!lParam) return 0; /* sent from ShowWindow */
if (!(wndPtr->dwStyle & WS_POPUP) || !wndPtr->owner) return 0;
if ((wndPtr->dwStyle & WS_VISIBLE) && wParam) return 0;
else if (!(wndPtr->dwStyle & WS_VISIBLE) && !wParam) return 0;
ShowWindow( wndPtr->hwndSelf, wParam ? SW_SHOWNOACTIVATE : SW_HIDE );
break;
case WM_CANCELMODE:
if (wndPtr->parent == WIN_GetDesktop()) EndMenu();
if (GetCapture() == wndPtr->hwndSelf) ReleaseCapture();
break;
case WM_VKEYTOITEM:
case WM_CHARTOITEM:
return -1;
case WM_DROPOBJECT:
return DRAG_FILE;
case WM_QUERYDROPOBJECT:
if (wndPtr->dwExStyle & WS_EX_ACCEPTFILES) return 1;
break;
case WM_QUERYDRAGICON:
{
HICON hIcon=0;
UINT len;
if( (hIcon=wndPtr->class->hCursor) ) return (LRESULT)hIcon;
for(len=1; len<64; len++)
if((hIcon=LoadIcon(wndPtr->hInstance,MAKEINTRESOURCE(len))))
return (LRESULT)hIcon;
return (LRESULT)LoadIcon(0,IDI_APPLICATION);
}
break;
case WM_ISACTIVEICON:
return ((wndPtr->flags & WIN_NCACTIVATED) != 0);
case WM_QUERYOPEN:
case WM_QUERYENDSESSION:
return 1;
}
return 0;
}

View File

@@ -0,0 +1,45 @@
/*
* X events handling functions
*
* Copyright 1993 Alexandre Julliard
*
*/
#include <windows.h>
/***********************************************************************
* EVENT_WaitNetEvent
*
* Wait for a network event, optionally sleeping until one arrives.
* Return TRUE if an event is pending, FALSE on timeout or error
* (for instance lost connection with the server).
*/
WINBOOL EVENT_WaitNetEvent(WINBOOL sleep, WINBOOL peek)
{
return TRUE;
}
/**********************************************************************
* EVENT_CheckFocus
*/
WINBOOL EVENT_CheckFocus(void)
{
return TRUE;
}
/**********************************************************************
* X11DRV_EVENT_Pending
*/
WINBOOL EVENT_Pending()
{
return FALSE;
}
UINT EVENT_GetCaptureInfo(void)
{
}

View File

@@ -0,0 +1,112 @@
#include <windows.h>
#include <user32/heapdup.h>
LPVOID HEAP_strdupAtoW(HANDLE hHeap,DWORD dwFlags, LPCSTR lpszAsciiString )
{
int i;
INT len = lstrlenA(lpszAsciiString);
LPWSTR lpszUnicodeString = HeapAlloc( GetProcessHeap(), 0, (len + 1)*2 );
for(i=0;i<len;i++)
lpszUnicodeString[i] = lpszAsciiString[i];
lpszUnicodeString[i] = 0;
return lpszUnicodeString;
}
//FIXME should use multi byte strings instead
LPVOID HEAP_strdupWtoA(HANDLE hHeap,DWORD dwFlags, LPCWSTR lpszUnicodeString )
{
int i;
INT len = lstrlenW(lpszUnicodeString);
LPSTR lpszAsciiString = HeapAlloc( GetProcessHeap(), 0, (len + 1) );
for(i=0;i<len;i++)
lpszAsciiString[i] = lpszUnicodeString[i];
lpszAsciiString[i] = 0;
return lpszAsciiString;
}
//FIXME should use multi byte strings instead
LPVOID HEAP_wcsdup(HANDLE hHeap, DWORD dwFlags, LPCWSTR lpszUnicodeString )
{
int i;
INT len = lstrlenW(lpszUnicodeString);
LPWSTR lpszString = HeapAlloc( GetProcessHeap(), 0, (len + 1)*2 );
for(i=0;i<len;i++)
lpszString[i] = lpszUnicodeString[i];
lpszString[i] = 0;
return lpszString;
}
int lstrcpynWtoA( LPSTR ptr1, LPWSTR ptr2, int n )
{
int i;
for(i=0;i<n;i++) {
ptr1[i] = ptr2[i];
if ( ptr1[i] == 0 )
break;
}
return i;
}
int lstrcpynAtoW( LPWSTR ptr1, LPSTR ptr2, int n )
{
int i;
for(i=0;i<n;i++) {
ptr1[i] = ptr2[i];
if ( ptr1[i] == 0 )
break;
}
return i;
}
int lstrcpyWtoA( LPSTR ptr1, LPWSTR ptr2 )
{
int n = lstrlenW(ptr2);
return lstrcpynWtoA(ptr1,ptr2,n);
}
int lstrcpyAtoW( LPWSTR ptr1, LPSTR ptr2 )
{
int n = lstrlenA(ptr2);
return lstrcpynAtoW(ptr1,ptr2,n);
}
int lpstrncpyA( LPSTR ptr1,LPSTR ptr2, int n)
{
int i;
for(i=0;i<n;i++) {
ptr1[i] = ptr2[i];
if ( ptr1[i] == 0 )
break;
}
}
int lpstrncpyW( LPWSTR ptr1,LPWSTR ptr2, int n)
{
int i;
for(i=0;i<n;i++) {
ptr1[i] = ptr2[i];
if ( ptr1[i] == 0 )
break;
}
}
LPSTR HEAP_strdupA(LPSTR ptr)
{
INT len = lstrlenA(ptr);
LPSTR lpszString = HeapAlloc( GetProcessHeap(), 0, (len + 1) );
if ( lpszString != NULL )
lstrcpyA(lpszString,ptr);
return lpszString;
}
LPWSTR HEAP_strdupW(LPWSTR ptr)
{
INT len = lstrlenW(ptr);
LPWSTR lpszString = HeapAlloc( GetProcessHeap(), 0, (len + 1)*2 );
if ( lpszString != NULL )
lstrcpyW(lpszString,ptr);
return lpszString;
}

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,138 @@
/*
* Window properties
*
* Copyright 1995, 1996 Alexandre Julliard
*/
#include <windows.h>
#include <user32/win.h>
#include <user32/property.h>
/***********************************************************************
* PROP_FindProp
*/
HANDLE PROPERTY_FindProp( HWND hwnd, ATOM atom )
{
PROPERTY *prop;
WND *pWnd = WIN_FindWndPtr( hwnd );
if (!pWnd)
return NULL;
for (prop = pWnd->pProp; (prop); prop = prop->next)
{
if ( prop->atom == atom)
return prop->handle;
}
return NULL;
}
WINBOOL PROPERTY_SetProp(HANDLE hwnd,ATOM atom,HANDLE hData)
{
PROPERTY *prop;
if (!(prop = PROPERTY_FindProp( hwnd, atom )))
{
/* We need to create it */
WND *pWnd = WIN_FindWndPtr( hwnd );
if (!pWnd)
return FALSE;
if (!(prop = HeapAlloc( GetProcessHeap(), 0, sizeof(PROPERTY) )))
return FALSE;
prop->next = pWnd->pProp;
pWnd->pProp = prop;
prop->atom = atom;
prop->handle = hData;
}
else {
prop->handle = hData;
}
return TRUE;
}
HANDLE PROPERTY_RemoveProp( HANDLE hwnd , ATOM atom )
{
HANDLE handle = NULL;
PROPERTY **pprop, *prop;
WND *pWnd = WIN_FindWndPtr( hwnd );
if (!pWnd)
return (HANDLE)0;
for (pprop=(PROPERTY**)&pWnd->pProp; (*pprop); pprop = &(*pprop)->next)
{
if ( (*pprop)->atom == atom ) {
prop = *pprop;
handle = prop->handle;
*pprop = prop->next;
HeapFree( GetProcessHeap(), 0, prop );
break;
}
}
return handle;
}
/***********************************************************************
* PROPERTY_RemoveWindowProps
*
* Remove all properties of a window.
*/
void PROPERTY_RemoveWindowProps( HANDLE hwnd )
{
PROPERTY *prop, *next;
WND *pWnd = WIN_FindWndPtr( hwnd );
if (!pWnd)
return (HANDLE)0;
for (prop = pWnd->pProp; (prop); prop = next)
{
next = prop->next;
HeapFree(GetProcessHeap(),0, prop );
}
pWnd->pProp = NULL;
}
WINBOOL PROPERTY_EnumPropEx(HWND hwnd, PROPVALUE **pv , int maxsize, int *size )
{
PROPERTY *prop, *next;
WND *pWnd;
INT ret = -1;
int i;
if (!(pWnd = WIN_FindWndPtr( hwnd )))
return FALSE;
for (prop = pWnd->pProp; (prop); prop = next)
{
/* Already get the next in case the callback */
/* function removes the current property. */
next = prop->next;
pv[i]->hwnd = hwnd;
pv[i]->handle = prop->handle;
pv[i]->atom = prop->atom;
i++;
if ( i > maxsize )
return FALSE;
}
return TRUE;
}

View File

@@ -0,0 +1,706 @@
/*
* Message queues related functions
*
* Copyright 1993, 1994 Alexandre Julliard
*/
#include <windows.h>
#include <user32/win.h>
#include <user32/queue.h>
#include <user32/debug.h>
HWND GetSysModalWindow(void);
#define MAX_QUEUE_SIZE 120 /* Max. size of a message queue */
static HQUEUE hFirstQueue = 0;
static HQUEUE hExitingQueue = 0;
static HQUEUE hmemSysMsgQueue = 0;
static MESSAGEQUEUE *sysMsgQueue = NULL;
static MESSAGEQUEUE *pMouseQueue = NULL; /* Queue for last mouse message */
static MESSAGEQUEUE *pKbdQueue = NULL; /* Queue for last kbd message */
MESSAGEQUEUE *pCursorQueue = NULL;
MESSAGEQUEUE *pActiveQueue = NULL;
/***********************************************************************
* QUEUE_DumpQueue
*/
void QUEUE_DumpQueue( HQUEUE hQueue )
{
MESSAGEQUEUE *pq;
if (!(pq = (MESSAGEQUEUE*) GlobalLock( hQueue )) ||
GlobalSize(hQueue) < sizeof(MESSAGEQUEUE)+pq->queueSize*sizeof(QMSG))
{
DPRINT( "%04x is not a queue handle\n", hQueue );
return;
}
DPRINT( "next: %12.4x Intertask SendMessage:\n"
"hTask: %11.4x ----------------------\n"
"msgSize: %9.4x hWnd: %10.4x\n"
"msgCount: %8.4x msg: %11.4x\n"
"msgNext: %9.4x wParam: %8.4x\n"
"msgFree: %9.4x lParam: %8.8x\n"
"qSize: %11.4x lRet: %10.8x\n"
"wWinVer: %9.4x ISMH: %10.4x\n"
"paints: %10.4x hSendTask: %5.4x\n"
"timers: %10.4x hPrevSend: %5.4x\n"
"wakeBits: %8.4x\n"
"wakeMask: %8.4x\n"
"hCurHook: %8.4x\n",
pq->next, pq->hTask, pq->msgSize, pq->hWnd,
pq->msgCount, pq->msg, pq->nextMessage, pq->wParam,
pq->nextFreeMessage, (unsigned)pq->lParam, pq->queueSize,
(unsigned)pq->SendMessageReturn, pq->wWinVersion, pq->InSendMessageHandle,
pq->wPaintCount, pq->hSendingTask, pq->wTimerCount,
pq->hPrevSendingTask, pq->wakeBits, pq->wakeMask, pq->hCurHook);
}
/***********************************************************************
* QUEUE_WalkQueues
*/
void QUEUE_WalkQueues(void)
{
char module[10];
HQUEUE hQueue = hFirstQueue;
DPRINT( "Queue Size Msgs Task\n" );
while (hQueue)
{
MESSAGEQUEUE *queue = (MESSAGEQUEUE *)GlobalLock( hQueue );
if (!queue)
{
DPRINT( "Bad queue handle %04x\n", hQueue );
return;
}
// if (!GetModuleFileName( queue->hTask, module, sizeof(module )))
// strcpy( module, "???" );
// DPRINT( "%04x %5d %4d %04x %s\n", hQueue, queue->msgSize,
// queue->msgCount, queue->hTask, module );
hQueue = queue->next;
}
DPRINT( "\n" );
}
/***********************************************************************
* QUEUE_IsExitingQueue
*/
WINBOOL QUEUE_IsExitingQueue( HQUEUE hQueue )
{
return (hExitingQueue && (hQueue == hExitingQueue));
}
/***********************************************************************
* QUEUE_SetExitingQueue
*/
void QUEUE_SetExitingQueue( HQUEUE hQueue )
{
hExitingQueue = hQueue;
}
/***********************************************************************
* QUEUE_CreateMsgQueue
*
* Creates a message queue. Doesn't link it into queue list!
*/
HQUEUE QUEUE_CreateMsgQueue( int size )
{
HQUEUE hQueue;
MESSAGEQUEUE * msgQueue;
int queueSize;
//TDB *pTask = (TDB *)GlobalLock( GetCurrentTask() );
DPRINT("Creating message queue...\n");
queueSize = sizeof(MESSAGEQUEUE) + size * sizeof(QMSG);
if (!(hQueue = GlobalAlloc( GMEM_FIXED | GMEM_ZEROINIT, queueSize )))
return 0;
msgQueue = (MESSAGEQUEUE *) GlobalLock( hQueue );
msgQueue->self = hQueue;
msgQueue->msgSize = sizeof(QMSG);
msgQueue->queueSize = size;
msgQueue->wakeBits = msgQueue->changeBits = QS_SMPARAMSFREE;
//msgQueue->wWinVersion = pTask ? pTask->version : 0;
GlobalUnlock( hQueue );
return hQueue;
}
/***********************************************************************
* QUEUE_DeleteMsgQueue
*
* Unlinks and deletes a message queue.
*
* Note: We need to mask asynchronous events to make sure PostMessage works
* even in the signal handler.
*/
WINBOOL QUEUE_DeleteMsgQueue( HQUEUE hQueue )
{
MESSAGEQUEUE * msgQueue = (MESSAGEQUEUE*)GlobalLock(hQueue);
HQUEUE senderQ;
HQUEUE *pPrev;
DPRINT("Deleting message queue %04x\n", hQueue);
if (!hQueue || !msgQueue)
{
DPRINT( "invalid argument.\n");
return 0;
}
if( pCursorQueue == msgQueue ) pCursorQueue = NULL;
if( pActiveQueue == msgQueue ) pActiveQueue = NULL;
/* flush sent messages */
senderQ = msgQueue->hSendingTask;
while( senderQ )
{
MESSAGEQUEUE* sq = (MESSAGEQUEUE*)GlobalLock(senderQ);
if( !sq ) break;
sq->SendMessageReturn = 0L;
QUEUE_SetWakeBit( sq, QS_SMRESULT );
senderQ = sq->hPrevSendingTask;
}
SIGNAL_MaskAsyncEvents( TRUE );
pPrev = &hFirstQueue;
while (*pPrev && (*pPrev != hQueue))
{
MESSAGEQUEUE *msgQ = (MESSAGEQUEUE*)GlobalLock(*pPrev);
pPrev = &msgQ->next;
}
if (*pPrev) *pPrev = msgQueue->next;
msgQueue->self = 0;
SIGNAL_MaskAsyncEvents( FALSE );
GlobalFree( hQueue );
return 1;
}
/***********************************************************************
* QUEUE_CreateSysMsgQueue
*
* Create the system message queue, and set the double-click speed.
* Must be called only once.
*/
WINBOOL QUEUE_CreateSysMsgQueue( int size )
{
if (size > MAX_QUEUE_SIZE) size = MAX_QUEUE_SIZE;
else if (size <= 0) size = 1;
if (!(hmemSysMsgQueue = QUEUE_CreateMsgQueue( size ))) return FALSE;
sysMsgQueue = (MESSAGEQUEUE *) GlobalLock( hmemSysMsgQueue );
return TRUE;
}
/***********************************************************************
* QUEUE_GetSysQueue
*/
MESSAGEQUEUE *QUEUE_GetSysQueue(void)
{
return sysMsgQueue;
}
/***********************************************************************
* QUEUE_Signal
*/
void QUEUE_Signal( HTASK hTask )
{
#if 0
PDB32 *pdb;
THREAD_ENTRY *entry;
TDB *pTask = (TDB *)GlobalLock( hTask );
if ( !pTask ) return;
/* Wake up thread waiting for message */
SetEvent( pTask->thdb->event );
PostEvent( hTask );
#endif
}
/***********************************************************************
* QUEUE_Wait
*/
static void QUEUE_Wait( DWORD wait_mask )
{
#if 0
if ( THREAD_IsWin16( THREAD_Current() ) )
WaitEvent( 0 );
else
{
DPRINT( "current task is 32-bit, calling SYNC_DoWait\n");
MsgWaitForMultipleObjects( 0, NULL, FALSE, INFINITE32, wait_mask );
}
#endif
}
/***********************************************************************
* QUEUE_SetWakeBit
*
* See "Windows Internals", p.449
*/
void QUEUE_SetWakeBit( MESSAGEQUEUE *queue, WORD bit )
{
DPRINT("queue = %04x (wm=%04x), bit = %04x\n",
queue->self, queue->wakeMask, bit );
if (bit & QS_MOUSE) pMouseQueue = queue;
if (bit & QS_KEY) pKbdQueue = queue;
queue->changeBits |= bit;
queue->wakeBits |= bit;
if (queue->wakeMask & bit)
{
queue->wakeMask = 0;
QUEUE_Signal( queue->hTask );
}
}
/***********************************************************************
* QUEUE_ClearWakeBit
*/
void QUEUE_ClearWakeBit( MESSAGEQUEUE *queue, WORD bit )
{
queue->changeBits &= ~bit;
queue->wakeBits &= ~bit;
}
/***********************************************************************
* QUEUE_WaitBits
*
* See "Windows Internals", p.447
*/
void QUEUE_WaitBits( WORD bits )
{
MESSAGEQUEUE *queue;
DPRINT("q %04x waiting for %04x\n", GetFastQueue(), bits);
for (;;)
{
if (!(queue = (MESSAGEQUEUE *)GlobalLock( GetFastQueue() ))) return;
if (queue->changeBits & bits)
{
/* One of the bits is set; we can return */
queue->wakeMask = 0;
return;
}
if (queue->wakeBits & QS_SENDMESSAGE)
{
/* Process the sent message immediately */
queue->wakeMask = 0;
QUEUE_ReceiveMessage( queue );
continue; /* nested sm crux */
}
queue->wakeMask = bits | QS_SENDMESSAGE;
if(queue->changeBits & bits) continue;
DPRINT("%04x) wakeMask is %04x, waiting\n", queue->self, queue->wakeMask);
QUEUE_Wait( queue->wakeMask );
}
}
/***********************************************************************
* QUEUE_ReceiveMessage
*
* This routine is called when a sent message is waiting for the queue.
*/
void QUEUE_ReceiveMessage( MESSAGEQUEUE *queue )
{
MESSAGEQUEUE *senderQ = NULL;
HQUEUE prevSender = 0;
QSMCTRL* prevCtrlPtr = NULL;
LRESULT result = 0;
DPRINT( "ReceiveMessage, queue %04x\n", queue->self );
if (!(queue->wakeBits & QS_SENDMESSAGE) ||
!(senderQ = (MESSAGEQUEUE*)GlobalLock( queue->hSendingTask)))
{ DPRINT("\trcm: nothing to do\n"); return; }
if( !senderQ->hPrevSendingTask )
QUEUE_ClearWakeBit( queue, QS_SENDMESSAGE ); /* no more sent messages */
/* Save current state on stack */
prevSender = queue->InSendMessageHandle;
prevCtrlPtr = queue->smResultCurrent;
/* Remove sending queue from the list */
queue->InSendMessageHandle = queue->hSendingTask;
queue->smResultCurrent = senderQ->smResultInit;
queue->hSendingTask = senderQ->hPrevSendingTask;
DPRINT( "\trcm: smResultCurrent = %08x, prevCtrl = %08x\n",
(unsigned)queue->smResultCurrent, (unsigned)prevCtrlPtr );
QUEUE_SetWakeBit( senderQ, QS_SMPARAMSFREE );
DPRINT( "\trcm: calling wndproc - %04x %04x %04x%04x %08x\n",
senderQ->hWnd, senderQ->msg, senderQ->wParamHigh,
senderQ->wParam, (unsigned)senderQ->lParam );
if (IsWindow( senderQ->hWnd ))
{
WND *wndPtr = WIN_FindWndPtr( senderQ->hWnd );
DWORD extraInfo = queue->GetMessageExtraInfoVal;
queue->GetMessageExtraInfoVal = senderQ->GetMessageExtraInfoVal;
if (senderQ->flags & QUEUE_SM_ASCII)
{
WPARAM wParam = MAKELONG( senderQ->wParam, senderQ->wParamHigh );
DPRINT( "\trcm: msg is Win32\n" );
if (senderQ->flags & QUEUE_SM_UNICODE)
result = CallWindowProcW( wndPtr->winproc,
senderQ->hWnd, senderQ->msg,
wParam, senderQ->lParam );
else
result = CallWindowProcA( wndPtr->winproc,
senderQ->hWnd, senderQ->msg,
wParam, senderQ->lParam );
}
else /* Win16 message */
result = CallWindowProc( (WNDPROC)wndPtr->winproc,
senderQ->hWnd, senderQ->msg,
senderQ->wParam, senderQ->lParam );
queue->GetMessageExtraInfoVal = extraInfo; /* Restore extra info */
DPRINT("\trcm: result = %08x\n", (unsigned)result );
}
else DPRINT( "\trcm: bad hWnd\n");
/* Return the result to the sender task */
ReplyMessage( result );
queue->InSendMessageHandle = prevSender;
queue->smResultCurrent = prevCtrlPtr;
DPRINT("done!\n");
}
/***********************************************************************
* QUEUE_FlushMessage
*
* Try to reply to all pending sent messages on exit.
*/
void QUEUE_FlushMessages( HQUEUE hQueue )
{
MESSAGEQUEUE *queue = (MESSAGEQUEUE*)GlobalLock( hQueue );
if( queue )
{
MESSAGEQUEUE *senderQ = (MESSAGEQUEUE*)GlobalLock( queue->hSendingTask);
QSMCTRL* CtrlPtr = queue->smResultCurrent;
DPRINT("Flushing queue %04x:\n", hQueue );
while( senderQ )
{
if( !CtrlPtr )
CtrlPtr = senderQ->smResultInit;
DPRINT("\tfrom queue %04x, smResult %08x\n", queue->hSendingTask, (unsigned)CtrlPtr );
if( !(queue->hSendingTask = senderQ->hPrevSendingTask) )
QUEUE_ClearWakeBit( queue, QS_SENDMESSAGE );
QUEUE_SetWakeBit( senderQ, QS_SMPARAMSFREE );
queue->smResultCurrent = CtrlPtr;
// while( senderQ->wakeBits & QS_SMRESULT ) OldYield();
while( senderQ->wakeBits & QS_SMRESULT ) Sleep(100);
senderQ->SendMessageReturn = 0;
senderQ->smResult = queue->smResultCurrent;
QUEUE_SetWakeBit( senderQ, QS_SMRESULT);
senderQ = (MESSAGEQUEUE*)GlobalLock( queue->hSendingTask);
CtrlPtr = NULL;
}
queue->InSendMessageHandle = 0;
}
}
/***********************************************************************
* QUEUE_AddMsg
*
* Add a message to the queue. Return FALSE if queue is full.
*/
WINBOOL QUEUE_AddMsg( HQUEUE hQueue, MSG * msg, DWORD extraInfo )
{
int pos;
MESSAGEQUEUE *msgQueue;
SIGNAL_MaskAsyncEvents( TRUE );
if (!(msgQueue = (MESSAGEQUEUE *)GlobalLock( hQueue ))) return FALSE;
pos = msgQueue->nextFreeMessage;
/* Check if queue is full */
if ((pos == msgQueue->nextMessage) && (msgQueue->msgCount > 0))
{
SIGNAL_MaskAsyncEvents( FALSE );
DPRINT("Queue is full!\n" );
return FALSE;
}
/* Store message */
msgQueue->messages[pos].msg = *msg;
msgQueue->messages[pos].extraInfo = extraInfo;
if (pos < msgQueue->queueSize-1) pos++;
else pos = 0;
msgQueue->nextFreeMessage = pos;
msgQueue->msgCount++;
SIGNAL_MaskAsyncEvents( FALSE );
QUEUE_SetWakeBit( msgQueue, QS_POSTMESSAGE );
return TRUE;
}
/***********************************************************************
* QUEUE_FindMsg
*
* Find a message matching the given parameters. Return -1 if none available.
*/
int QUEUE_FindMsg( MESSAGEQUEUE * msgQueue, HWND hwnd, int first, int last )
{
int i, pos = msgQueue->nextMessage;
DPRINT("hwnd=%04x pos=%d\n", hwnd, pos );
if (!msgQueue->msgCount) return -1;
if (!hwnd && !first && !last) return pos;
for (i = 0; i < msgQueue->msgCount; i++)
{
MSG * msg = &msgQueue->messages[pos].msg;
if (!hwnd || (msg->hwnd == hwnd))
{
if (!first && !last) return pos;
if ((msg->message >= first) && (msg->message <= last)) return pos;
}
if (pos < msgQueue->queueSize-1) pos++;
else pos = 0;
}
return -1;
}
/***********************************************************************
* QUEUE_RemoveMsg
*
* Remove a message from the queue (pos must be a valid position).
*/
void QUEUE_RemoveMsg( MESSAGEQUEUE * msgQueue, int pos )
{
SIGNAL_MaskAsyncEvents( TRUE );
if (pos >= msgQueue->nextMessage)
{
for ( ; pos > msgQueue->nextMessage; pos--)
msgQueue->messages[pos] = msgQueue->messages[pos-1];
msgQueue->nextMessage++;
if (msgQueue->nextMessage >= msgQueue->queueSize)
msgQueue->nextMessage = 0;
}
else
{
for ( ; pos < msgQueue->nextFreeMessage; pos++)
msgQueue->messages[pos] = msgQueue->messages[pos+1];
if (msgQueue->nextFreeMessage) msgQueue->nextFreeMessage--;
else msgQueue->nextFreeMessage = msgQueue->queueSize-1;
}
msgQueue->msgCount--;
if (!msgQueue->msgCount) msgQueue->wakeBits &= ~QS_POSTMESSAGE;
SIGNAL_MaskAsyncEvents( FALSE );
}
/***********************************************************************
* QUEUE_WakeSomeone
*
* Wake a queue upon reception of a hardware event.
*/
static void QUEUE_WakeSomeone( UINT message )
{
WND* wndPtr = NULL;
WORD wakeBit;
HWND hwnd;
MESSAGEQUEUE *queue = pCursorQueue;
if( (message >= WM_KEYFIRST) && (message <= WM_KEYLAST) )
{
wakeBit = QS_KEY;
if( pActiveQueue ) queue = pActiveQueue;
}
else
{
wakeBit = (message == WM_MOUSEMOVE) ? QS_MOUSEMOVE : QS_MOUSEBUTTON;
if( (hwnd = GetCapture()) )
if( (wndPtr = WIN_FindWndPtr( hwnd )) )
queue = (MESSAGEQUEUE *)GlobalLock( wndPtr->hmemTaskQ );
}
if( (hwnd = GetSysModalWindow()) )
if( (wndPtr = WIN_FindWndPtr( hwnd )) )
queue = (MESSAGEQUEUE *)GlobalLock( wndPtr->hmemTaskQ );
if( !queue )
{
queue = GlobalLock( hFirstQueue );
while( queue )
{
if (queue->wakeMask & wakeBit) break;
queue = GlobalLock( queue->next );
}
if( !queue )
{
DPRINT( "couldn't find queue\n");
return;
}
}
QUEUE_SetWakeBit( queue, wakeBit );
}
/***********************************************************************
* hardware_event
*
* Add an event to the system message queue.
* Note: the position is relative to the desktop window.
*/
void hardware_event( WORD message, WORD wParam, LONG lParam,
int xPos, int yPos, DWORD time, DWORD extraInfo )
{
MSG *msg;
int pos;
if (!sysMsgQueue) return;
pos = sysMsgQueue->nextFreeMessage;
/* Merge with previous event if possible */
if ((message == WM_MOUSEMOVE) && sysMsgQueue->msgCount)
{
if (pos > 0) pos--;
else pos = sysMsgQueue->queueSize - 1;
msg = &sysMsgQueue->messages[pos].msg;
if ((msg->message == message) && (msg->wParam == wParam))
sysMsgQueue->msgCount--; /* Merge events */
else
pos = sysMsgQueue->nextFreeMessage; /* Don't merge */
}
/* Check if queue is full */
if ((pos == sysMsgQueue->nextMessage) && sysMsgQueue->msgCount)
{
/* Queue is full, beep (but not on every mouse motion...) */
if (message != WM_MOUSEMOVE) MessageBeep(0);
return;
}
/* Store message */
msg = &sysMsgQueue->messages[pos].msg;
msg->hwnd = 0;
msg->message = message;
msg->wParam = wParam;
msg->lParam = lParam;
msg->time = time;
msg->pt.x = xPos & 0xffff;
msg->pt.y = yPos & 0xffff;
sysMsgQueue->messages[pos].extraInfo = extraInfo;
if (pos < sysMsgQueue->queueSize - 1) pos++;
else pos = 0;
sysMsgQueue->nextFreeMessage = pos;
sysMsgQueue->msgCount++;
QUEUE_WakeSomeone( message );
}
/***********************************************************************
* QUEUE_GetQueueTask
*/
HTASK QUEUE_GetQueueTask( HQUEUE hQueue )
{
MESSAGEQUEUE *queue = GlobalLock( hQueue );
return (queue) ? queue->hTask : 0 ;
}
/***********************************************************************
* QUEUE_IncPaintCount
*/
void QUEUE_IncPaintCount( HQUEUE hQueue )
{
MESSAGEQUEUE *queue;
if (!(queue = (MESSAGEQUEUE *)GlobalLock( hQueue ))) return;
queue->wPaintCount++;
QUEUE_SetWakeBit( queue, QS_PAINT );
}
/***********************************************************************
* QUEUE_DecPaintCount
*/
void QUEUE_DecPaintCount( HQUEUE hQueue )
{
MESSAGEQUEUE *queue;
if (!(queue = (MESSAGEQUEUE *)GlobalLock( hQueue ))) return;
queue->wPaintCount--;
if (!queue->wPaintCount) queue->wakeBits &= ~QS_PAINT;
}
/***********************************************************************
* QUEUE_IncTimerCount
*/
void QUEUE_IncTimerCount( HQUEUE hQueue )
{
MESSAGEQUEUE *queue;
if (!(queue = (MESSAGEQUEUE *)GlobalLock( hQueue ))) return;
queue->wTimerCount++;
QUEUE_SetWakeBit( queue, QS_TIMER );
}
/***********************************************************************
* QUEUE_DecTimerCount
*/
void QUEUE_DecTimerCount( HQUEUE hQueue )
{
MESSAGEQUEUE *queue;
if (!(queue = (MESSAGEQUEUE *)GlobalLock( hQueue ))) return;
queue->wTimerCount--;
if (!queue->wTimerCount) queue->wakeBits &= ~QS_TIMER;
}

View File

@@ -0,0 +1,37 @@
#include <windows.h>
INT SelectVisRgn(HDC hdc,HRGN hrgn)
{
return SelectClipRgn(hdc,hrgn);
}
INT RestoreVisRgn(HDC hdc)
{
return SelectClipRgn(hdc,NULL);
}
INT ExcludeVisRect(HDC hDC,INT nLeftRect,INT nTopRect,INT nRightRect,INT nBottomRect)
{
return ExcludeClipRect(hDC, nLeftRect, nTopRect,nRightRect,nBottomRect );
}
HRGN InquireVisRgn(HDC hdc)
{
return hdc;
}
HRGN SaveVisRgn(HDC hdc)
{
return NULL;
}
/***********************************************************************
* REGION_UnionRectWithRgn
* Adds a rectangle to a HRGN32
* A helper used by scroll.c
*/
WINBOOL REGION_UnionRectWithRgn( HRGN hrgn, const RECT *lpRect )
{
return TRUE;
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,6 @@
#include <windows.h>
void SIGNAL_MaskAsyncEvents( WINBOOL flag )
{
// sigprocmask( (flag) ? SIG_BLOCK : SIG_UNBLOCK , &async_signal_set, NULL);
}

View File

@@ -0,0 +1,719 @@
/*
* text functions
*
* Copyright 1993, 1994 Alexandre Julliard
*
*/
//#include <stdlib.h>
#include <windows.h>
#include <user32/text.h>
int tabstop;
int tabwidth;
int spacewidth;
int prefix_offset;
/*
typedef struct {
UINT cbSize;
int iTabLength;
int iLeftMargin;
int iRightMargin;
UINT uiLengthDrawn;
} DRAWTEXTPARAMS, FAR *LPDRAWTEXTPARAMS;
*/
int TEXT_DrawTextEx(HDC hDC,void *strPtr,int nCount,LPRECT lpRect,UINT uFormat,LPDRAWTEXTPARAMS dtp,WINBOOL Unicode )
{
SIZE size;
int line[1024];
int len, lh, count=nCount;
int prefix_x = 0;
int prefix_end = 0;
TEXTMETRIC tm;
int x = lpRect->left, y = lpRect->top;
int width = lpRect->right - lpRect->left;
int max_width = 0;
//TRACE(text,"%s, %d , [(%d,%d),(%d,%d)]\n",
// debugstr_an (lpString, count), count,
// lpRect->left, lpRect->top, lpRect->right, lpRect->bottom);
if (count == -1) {
if ( Unicode )
count = lstrlenW(strPtr);
else
count = lstrlenA(strPtr);
}
if ( Unicode )
GetTextMetricsW(hDC, &tm);
else
GetTextMetricsA(hDC, &tm);
if (uFormat & DT_EXTERNALLEADING)
lh = tm.tmHeight + tm.tmExternalLeading;
else
lh = tm.tmHeight;
if (uFormat & DT_TABSTOP)
tabstop = uFormat >> 8;
if (uFormat & DT_EXPANDTABS)
{
GetTextExtentPointA(hDC, " ", 1, &size);
spacewidth = size.cx;
if ( dtp->iTabLength == 0 ) {
GetTextExtentPointA(hDC, "o", 1, &size);
tabwidth = size.cx * tabstop;
}
else
tabwidth = tabstop * dtp->iTabLength;
}
if (uFormat & DT_CALCRECT) uFormat |= DT_NOCLIP;
do
{
prefix_offset = -1;
if ( Unicode )
strPtr = TEXT_NextLineW(hDC, strPtr, &count, (LPWSTR)line, &len, width, uFormat);
else
strPtr = TEXT_NextLineA(hDC, strPtr, &count, (LPSTR)line, &len, width, uFormat);
if ( Unicode ) {
if (prefix_offset != -1)
{
GetTextExtentPointW(hDC, (LPWSTR)line, prefix_offset, &size);
prefix_x = size.cx;
GetTextExtentPointW(hDC, (LPWSTR)line, prefix_offset + 1, &size);
prefix_end = size.cx - 1;
}
if (!GetTextExtentPointW(hDC, (LPWSTR)line, len, &size))
return 0;
}
else {
if (prefix_offset != -1)
{
GetTextExtentPointA(hDC, (LPSTR)line, prefix_offset, &size);
prefix_x = size.cx;
GetTextExtentPointA(hDC, (LPSTR)line, prefix_offset + 1, &size);
prefix_end = size.cx - 1;
}
if (!GetTextExtentPointA(hDC, (LPSTR)line, len, &size))
return 0;
}
if (uFormat & DT_CENTER)
x = (lpRect->left + lpRect->right - size.cx) / 2;
else if (uFormat & DT_RIGHT)
x = lpRect->right - size.cx;
if (uFormat & DT_SINGLELINE)
{
if (uFormat & DT_VCENTER) y = lpRect->top +
(lpRect->bottom - lpRect->top) / 2 - size.cy / 2;
else if (uFormat & DT_BOTTOM) y = lpRect->bottom - size.cy;
}
if (!(uFormat & DT_CALCRECT))
{
if ( Unicode ) {
if (!ExtTextOutW(hDC, x, y, (uFormat & DT_NOCLIP) ? 0 : ETO_CLIPPED,lpRect, (LPWSTR)line, len, NULL ))
return 0;
}
else {
if (!ExtTextOutA(hDC, x, y, (uFormat & DT_NOCLIP) ? 0 : ETO_CLIPPED,lpRect, (LPSTR)line, len, NULL ))
return 0;
}
if (prefix_offset != -1)
{
HPEN hpen = CreatePen( PS_SOLID, 1, GetTextColor(hDC) );
HPEN oldPen = SelectObject( hDC, hpen );
MoveToEx(hDC, x + prefix_x, y + tm.tmAscent + 1,NULL );
LineTo(hDC, x + prefix_end + 1, y + tm.tmAscent + 1 );
SelectObject( hDC, oldPen );
DeleteObject( hpen );
}
}
else if (size.cx > max_width)
max_width = size.cx;
y += lh;
if (strPtr)
{
if (!(uFormat & DT_NOCLIP))
{
if (y > lpRect->bottom - lh)
break;
}
}
}
while (strPtr);
if (uFormat & DT_CALCRECT)
{
lpRect->right = lpRect->left + max_width;
lpRect->bottom = y;
}
return y - lpRect->top;
}
LPCSTR TEXT_NextLineA( HDC hdc, LPCSTR str, INT *count,
LPSTR dest, INT *len, INT width, WORD format)
{
/* Return next line of text from a string.
*
* hdc - handle to DC.
* str - string to parse into lines.
* count - length of str.
* dest - destination in which to return line.
* len - length of resultant line in dest in chars.
* width - maximum width of line in pixels.
* format - format type passed to DrawText.
*
* Returns pointer to next char in str after end of the line
* or NULL if end of str reached.
*/
int i = 0, j = 0, k;
int plen = 0;
int numspaces;
SIZE size;
int lasttab = 0;
int wb_i = 0, wb_j = 0, wb_count = 0;
while (*count)
{
switch (str[i])
{
case CR:
case LF:
if (!(format & DT_SINGLELINE))
{
if ((*count > 1) && (str[i] == CR) && (str[i+1] == LF))
{
(*count)--;
i++;
}
i++;
*len = j;
(*count)--;
return (&str[i]);
}
dest[j++] = str[i++];
if (!(format & DT_NOCLIP) || !(format & DT_NOPREFIX) ||
(format & DT_WORDBREAK))
{
if (!GetTextExtentPointA(hdc, &dest[j-1], 1, &size))
return NULL;
plen += size.cx;
}
break;
case PREFIX:
if (!(format & DT_NOPREFIX) && *count > 1)
{
if (str[++i] == PREFIX)
(*count)--;
else {
prefix_offset = j;
break;
}
}
dest[j++] = str[i++];
if (!(format & DT_NOCLIP) || !(format & DT_NOPREFIX) ||
(format & DT_WORDBREAK))
{
if (!GetTextExtentPointA(hdc, &dest[j-1], 1, &size))
return NULL;
plen += size.cx;
}
break;
case TAB:
if (format & DT_EXPANDTABS)
{
wb_i = ++i;
wb_j = j;
wb_count = *count;
if (!GetTextExtentPointA(hdc, &dest[lasttab], j - lasttab,
&size))
return NULL;
numspaces = (tabwidth - size.cx) / spacewidth;
for (k = 0; k < numspaces; k++)
dest[j++] = SPACE;
plen += tabwidth - size.cx;
lasttab = wb_j + numspaces;
}
else
{
dest[j++] = str[i++];
if (!(format & DT_NOCLIP) || !(format & DT_NOPREFIX) ||
(format & DT_WORDBREAK))
{
if (!GetTextExtentPointA(hdc, &dest[j-1], 1, &size))
return NULL;
plen += size.cx;
}
}
break;
case SPACE:
dest[j++] = str[i++];
if (!(format & DT_NOCLIP) || !(format & DT_NOPREFIX) ||
(format & DT_WORDBREAK))
{
wb_i = i;
wb_j = j - 1;
wb_count = *count;
if (!GetTextExtentPointA(hdc, &dest[j-1], 1, &size))
return NULL;
plen += size.cx;
}
break;
default:
dest[j++] = str[i++];
if (!(format & DT_NOCLIP) || !(format & DT_NOPREFIX) ||
(format & DT_WORDBREAK))
{
if (!GetTextExtentPointA(hdc, &dest[j-1], 1, &size))
return NULL;
plen += size.cx;
}
}
(*count)--;
if (!(format & DT_NOCLIP) || (format & DT_WORDBREAK))
{
if (plen > width)
{
if (format & DT_WORDBREAK)
{
if (wb_j)
{
*len = wb_j;
*count = wb_count - 1;
return (&str[wb_i]);
}
}
else
{
*len = j;
return (&str[i]);
}
}
}
}
*len = j;
return NULL;
}
LPCWSTR TEXT_NextLineW( HDC hdc, LPCWSTR str, INT *count,
LPWSTR dest, INT *len, INT width, WORD format)
{
/* Return next line of text from a string.
*
* hdc - handle to DC.
* str - string to parse into lines.
* count - length of str.
* dest - destination in which to return line.
* len - length of resultant line in dest in chars.
* width - maximum width of line in pixels.
* format - format type passed to DrawText.
*
* Returns pointer to next char in str after end of the line
* or NULL if end of str reached.
*/
int i = 0, j = 0, k;
int plen = 0;
int numspaces;
SIZE size;
int lasttab = 0;
int wb_i = 0, wb_j = 0, wb_count = 0;
while (*count)
{
switch (str[i])
{
case CR:
case LF:
if (!(format & DT_SINGLELINE))
{
if ((*count > 1) && (str[i] == CR) && (str[i+1] == LF))
{
(*count)--;
i++;
}
i++;
*len = j;
(*count)--;
return (&str[i]);
}
dest[j++] = str[i++];
if (!(format & DT_NOCLIP) || !(format & DT_NOPREFIX) ||
(format & DT_WORDBREAK))
{
if (!GetTextExtentPointW(hdc, &dest[j-1], 1, &size))
return NULL;
plen += size.cx;
}
break;
case PREFIX:
if (!(format & DT_NOPREFIX) && *count > 1)
{
if (str[++i] == PREFIX)
(*count)--;
else {
prefix_offset = j;
break;
}
}
dest[j++] = str[i++];
if (!(format & DT_NOCLIP) || !(format & DT_NOPREFIX) ||
(format & DT_WORDBREAK))
{
if (!GetTextExtentPointW(hdc, &dest[j-1], 1, &size))
return NULL;
plen += size.cx;
}
break;
case TAB:
if (format & DT_EXPANDTABS)
{
wb_i = ++i;
wb_j = j;
wb_count = *count;
if (!GetTextExtentPointW(hdc, &dest[lasttab], j - lasttab,
&size))
return NULL;
numspaces = (tabwidth - size.cx) / spacewidth;
for (k = 0; k < numspaces; k++)
dest[j++] = SPACE;
plen += tabwidth - size.cx;
lasttab = wb_j + numspaces;
}
else
{
dest[j++] = str[i++];
if (!(format & DT_NOCLIP) || !(format & DT_NOPREFIX) ||
(format & DT_WORDBREAK))
{
if (!GetTextExtentPointW(hdc, &dest[j-1], 1, &size))
return NULL;
plen += size.cx;
}
}
break;
case SPACE:
dest[j++] = str[i++];
if (!(format & DT_NOCLIP) || !(format & DT_NOPREFIX) ||
(format & DT_WORDBREAK))
{
wb_i = i;
wb_j = j - 1;
wb_count = *count;
if (!GetTextExtentPointW(hdc, &dest[j-1], 1, &size))
return NULL;
plen += size.cx;
}
break;
default:
dest[j++] = str[i++];
if (!(format & DT_NOCLIP) || !(format & DT_NOPREFIX) ||
(format & DT_WORDBREAK))
{
if (!GetTextExtentPointW(hdc, &dest[j-1], 1, &size))
return NULL;
plen += size.cx;
}
}
(*count)--;
if (!(format & DT_NOCLIP) || (format & DT_WORDBREAK))
{
if (plen > width)
{
if (format & DT_WORDBREAK)
{
if (wb_j)
{
*len = wb_j;
*count = wb_count - 1;
return (&str[wb_i]);
}
}
else
{
*len = j;
return (&str[i]);
}
}
}
}
*len = j;
return NULL;
}
#if 0
WINBOOL TEXT_GrayString(HDC hdc, HBRUSH hb,
GRAYSTRINGPROC fn, LPARAM lp, INT len,
INT x, INT y, INT cx, INT cy, WINBOOL Unicode)
{
HBITMAP hbm, hbmsave;
HBRUSH hbsave;
HFONT hfsave;
HDC memdc = CreateCompatibleDC(hdc);
int slen = len;
WINBOOL retval = TRUE;
RECT r;
COLORREF fg, bg;
if(!hdc) return FALSE;
if(len == 0)
{
if ( Unicode )
slen = lstrlenW((LPCWSTR)lp);
else
slen = lstrlenA((LPCSTR)lp);
}
if((cx == 0 || cy == 0) && slen != -1)
{
SIZE s;
if ( Unicode )
GetTextExtentPointW(hdc, (LPCWSTR)lp, slen, &s);
else
GetTextExtentPointA(hdc, (LPCSTR)lp, slen, &s);
if(cx == 0) cx = s.cx;
if(cy == 0) cy = s.cy;
}
r.left = r.top = 0;
r.right = cx;
r.bottom = cy;
hbm = CreateBitmap(cx, cy, 1, 1, NULL);
hbmsave = (HBITMAP)SelectObject(memdc, hbm);
FillRect(memdc, &r, (HBRUSH)GetStockObject(BLACK_BRUSH));
SetTextColor(memdc, RGB(255, 255, 255));
SetBkColor(memdc, RGB(0, 0, 0));
hfsave = (HFONT)SelectObject(memdc, GetCurrentObject(hdc, OBJ_FONT));
if(fn)
retval = fn(memdc, lp, slen);
else {
if (Unicode )
TextOutW(memdc, 0, 0, (LPCWSTR)lp, slen);
else
TextOutA(memdc, 0, 0, (LPCSTR)lp, slen);
}
SelectObject(memdc, hfsave);
/*
* Windows doc says that the bitmap isn't grayed when len == -1 and
* the callback function returns FALSE. However, testing this on
* win95 showed otherwise...
*/
#ifdef GRAYSTRING_USING_DOCUMENTED_BEHAVIOUR
if(retval || len != -1)
#endif
{
hbsave = (HBRUSH)SelectObject(memdc, CACHE_GetPattern55AABrush());
PatBlt(memdc, 0, 0, cx, cy, 0x000A0329);
SelectObject(memdc, hbsave);
}
if(hb) hbsave = (HBRUSH)SelectObject(hdc, hb);
fg = SetTextColor(hdc, RGB(0, 0, 0));
bg = SetBkColor(hdc, RGB(255, 255, 255));
BitBlt(hdc, x, y, cx, cy, memdc, 0, 0, 0x00E20746);
SetTextColor(hdc, fg);
SetBkColor(hdc, bg);
if(hb) SelectObject(hdc, hbsave);
SelectObject(memdc, hbmsave);
DeleteObject(hbm);
DeleteDC(memdc);
return retval;
}
#endif
/***********************************************************************
* TEXT_TabbedTextOut
*
* Helper function for TabbedTextOut() and GetTabbedTextExtent().
* Note: this doesn't work too well for text-alignment modes other
* than TA_LEFT|TA_TOP. But we want bug-for-bug compatibility :-)
*/
LONG TEXT_TabbedTextOutA( HDC hdc, INT x, INT y, LPCSTR lpstr,
INT count, INT cTabStops, const INT *lpTabPos,
INT nTabOrg, WINBOOL fDisplayText )
{
INT defWidth;
DWORD extent = 0;
int i, tabPos = x;
int start = x;
SIZE szSize;
if (cTabStops == 1)
{
defWidth = lpTabPos ? *lpTabPos : 0;
cTabStops = 0;
}
else
{
TEXTMETRIC tm;
GetTextMetricsA( hdc, &tm );
defWidth = 8 * tm.tmAveCharWidth;
}
while (count > 0)
{
for (i = 0; i < count; i++)
if (lpstr[i] == '\t') break;
GetTextExtentPoint32A( hdc, lpstr, i, &szSize );
extent = szSize.cx;
if (lpTabPos)
{
while ((cTabStops > 0) &&
(nTabOrg + *lpTabPos <= x + LOWORD(extent)))
{
lpTabPos++;
cTabStops--;
}
}
else
{
while ((cTabStops > 0) &&
(nTabOrg + *lpTabPos <= x + LOWORD(extent)))
{
lpTabPos++;
cTabStops--;
}
}
if (i == count)
tabPos = x + LOWORD(extent);
else if (cTabStops > 0)
tabPos = nTabOrg + (lpTabPos ? *lpTabPos : 0);
else
tabPos = nTabOrg + ((x + LOWORD(extent) - nTabOrg) / defWidth + 1) * defWidth;
if (fDisplayText)
{
RECT r;
SetRect( &r, x, y, tabPos, y+HIWORD(extent) );
ExtTextOutA( hdc, x, y,
GetBkMode(hdc) == OPAQUE ? ETO_OPAQUE : 0,
&r, lpstr, i, NULL );
}
x = tabPos;
count -= i+1;
lpstr += i+1;
}
return MAKELONG(tabPos - start, HIWORD(extent));
}
/***********************************************************************
* TEXT_TabbedTextOut
*
* Helper function for TabbedTextOut() and GetTabbedTextExtent().
* Note: this doesn't work too well for text-alignment modes other
* than TA_LEFT|TA_TOP. But we want bug-for-bug compatibility :-)
*/
LONG TEXT_TabbedTextOutW( HDC hdc, INT x, INT y, LPCWSTR lpstr,
INT count, INT cTabStops, const INT *lpTabPos,
INT nTabOrg, WINBOOL fDisplayText )
{
INT defWidth;
DWORD extent = 0;
int i, tabPos = x;
int start = x;
SIZE szSize;
if (cTabStops == 1)
{
defWidth = lpTabPos ? *lpTabPos : 0;
cTabStops = 0;
}
else
{
TEXTMETRIC tm;
GetTextMetricsW( hdc, &tm );
defWidth = 8 * tm.tmAveCharWidth;
}
while (count > 0)
{
for (i = 0; i < count; i++)
if (lpstr[i] == '\t') break;
GetTextExtentPoint32W( hdc, lpstr, i, &szSize );
extent = szSize.cx;
if (lpTabPos)
{
while ((cTabStops > 0) &&
(nTabOrg + *lpTabPos <= x + LOWORD(extent)))
{
lpTabPos++;
cTabStops--;
}
}
else
{
while ((cTabStops > 0) &&
(nTabOrg + *lpTabPos <= x + LOWORD(extent)))
{
lpTabPos++;
cTabStops--;
}
}
if (i == count)
tabPos = x + LOWORD(extent);
else if (cTabStops > 0)
tabPos = nTabOrg + (lpTabPos ? *lpTabPos : 0);
else
tabPos = nTabOrg + ((x + LOWORD(extent) - nTabOrg) / defWidth + 1) * defWidth;
if (fDisplayText)
{
RECT r;
SetRect( &r, x, y, tabPos, y+HIWORD(extent) );
ExtTextOutW( hdc, x, y,
GetBkMode(hdc) == OPAQUE ? ETO_OPAQUE : 0,
&r, lpstr, i, NULL );
}
x = tabPos;
count -= i+1;
lpstr += i+1;
}
return MAKELONG(tabPos - start, HIWORD(extent));
}
int _alloca(int x)
{
return malloc(x);
}

View File

@@ -0,0 +1,293 @@
/*
* Timer functions
*
* Copyright 1993 Alexandre Julliard
*/
#include <windows.h>
#include <user32/timer.h>
#include <user32/debug.h>
static TIMER TimersArray[NB_TIMERS];
static TIMER * pNextTimer = NULL; /* Next timer to expire */
/* Duration from 'time' until expiration of the timer */
#define EXPIRE_TIME(pTimer,time) \
(((pTimer)->expires <= (time)) ? 0 : (pTimer)->expires - (time))
/***********************************************************************
* TIMER_InsertTimer
*
* Insert the timer at its place in the chain.
*/
void TIMER_InsertTimer( TIMER * pTimer )
{
if (!pNextTimer || (pTimer->expires < pNextTimer->expires))
{
pTimer->next = pNextTimer;
pNextTimer = pTimer;
}
else
{
TIMER * ptr = pNextTimer;
while (ptr->next && (pTimer->expires >= ptr->next->expires))
ptr = ptr->next;
pTimer->next = ptr->next;
ptr->next = pTimer;
}
}
/***********************************************************************
* TIMER_RemoveTimer
*
* Remove the timer from the chain.
*/
void TIMER_RemoveTimer( TIMER * pTimer )
{
TIMER **ppTimer = &pNextTimer;
while (*ppTimer && (*ppTimer != pTimer)) ppTimer = &(*ppTimer)->next;
if (*ppTimer) *ppTimer = pTimer->next;
pTimer->next = NULL;
if (!pTimer->expires) QUEUE_DecTimerCount( pTimer->hq );
}
/***********************************************************************
* TIMER_ClearTimer
*
* Clear and remove a timer.
*/
void TIMER_ClearTimer( TIMER * pTimer )
{
TIMER_RemoveTimer( pTimer );
pTimer->hwnd = 0;
pTimer->msg = 0;
pTimer->id = 0;
pTimer->timeout = 0;
//WINPROC_FreeProc( pTimer->proc, WIN_PROC_TIMER );
}
/***********************************************************************
* TIMER_SwitchQueue
*/
void TIMER_SwitchQueue( HQUEUE old, HQUEUE newQ )
{
TIMER * pT = pNextTimer;
while (pT)
{
if (pT->hq == old) pT->hq = newQ;
pT = pT->next;
}
}
/***********************************************************************
* TIMER_RemoveWindowTimers
*
* Remove all timers for a given window.
*/
void TIMER_RemoveWindowTimers( HWND hwnd )
{
int i;
TIMER *pTimer;
for (i = NB_TIMERS, pTimer = TimersArray; i > 0; i--, pTimer++)
if ((pTimer->hwnd == hwnd) && pTimer->timeout)
TIMER_ClearTimer( pTimer );
}
/***********************************************************************
* TIMER_RemoveQueueTimers
*
* Remove all timers for a given queue.
*/
void TIMER_RemoveQueueTimers( HQUEUE hqueue )
{
int i;
TIMER *pTimer;
for (i = NB_TIMERS, pTimer = TimersArray; i > 0; i--, pTimer++)
if ((pTimer->hq == hqueue) && pTimer->timeout)
TIMER_ClearTimer( pTimer );
}
/***********************************************************************
* TIMER_RestartTimers
*
* Restart an expired timer.
*/
void TIMER_RestartTimer( TIMER * pTimer, DWORD curTime )
{
TIMER_RemoveTimer( pTimer );
pTimer->expires = curTime + pTimer->timeout;
TIMER_InsertTimer( pTimer );
}
/***********************************************************************
* TIMER_GetNextExpiration
*
* Return next timer expiration time, or -1 if none.
*/
LONG TIMER_GetNextExpiration(void)
{
return pNextTimer ? EXPIRE_TIME( pNextTimer, GetTickCount() ) : -1;
}
/***********************************************************************
* TIMER_ExpireTimers
*
* Mark expired timers and wake the appropriate queues.
*/
void TIMER_ExpireTimers(void)
{
TIMER *pTimer = pNextTimer;
DWORD curTime = GetTickCount();
while (pTimer && !pTimer->expires) /* Skip already expired timers */
pTimer = pTimer->next;
while (pTimer && (pTimer->expires <= curTime))
{
pTimer->expires = 0;
QUEUE_IncTimerCount( pTimer->hq );
pTimer = pTimer->next;
}
}
/***********************************************************************
* TIMER_GetTimerMsg
*
* Build a message for an expired timer.
*/
WINBOOL TIMER_GetTimerMsg( MSG *msg, HWND hwnd,
HQUEUE hQueue,WINBOOL remove )
{
TIMER *pTimer = pNextTimer;
DWORD curTime = GetTickCount();
if (hwnd) /* Find first timer for this window */
while (pTimer && (pTimer->hwnd != hwnd)) pTimer = pTimer->next;
else /* Find first timer for this queue */
while (pTimer && (pTimer->hq != hQueue)) pTimer = pTimer->next;
if (!pTimer || (pTimer->expires > curTime)) return FALSE; /* No timer */
if (remove) TIMER_RestartTimer( pTimer, curTime ); /* Restart it */
DPRINT( "Timer expired: %04x, %04x, %04x, %08lx\n",
pTimer->hwnd, pTimer->msg, pTimer->id, (DWORD)pTimer->proc);
/* Build the message */
msg->hwnd = (HWND)pTimer->hwnd;
msg->message = pTimer->msg;
msg->wParam = (UINT)pTimer->id;
msg->lParam = (LONG)pTimer->proc;
msg->time = curTime;
return TRUE;
}
/***********************************************************************
* TIMER_SetTimer
*/
UINT TIMER_SetTimer( HWND hwnd, UINT id, UINT timeout,
TIMERPROC proc, WINBOOL sys )
{
int i;
TIMER * pTimer;
int type = 0;
if (!timeout) return 0;
/* Check if there's already a timer with the same hwnd and id */
for (i = 0, pTimer = TimersArray; i < NB_TIMERS; i++, pTimer++)
if ((pTimer->hwnd == hwnd) && (pTimer->id == id) &&
(pTimer->timeout != 0))
{
/* Got one: set new values and return */
TIMER_RemoveTimer( pTimer );
pTimer->timeout = timeout;
// WINPROC_FreeProc( pTimer->proc, WIN_PROC_TIMER );
pTimer->proc = (HWINDOWPROC)0;
if (proc) {
pTimer->proc = proc;
//WINPROC_SetProc( &pTimer->proc, proc, type,WIN_PROC_TIMER );
}
pTimer->expires = GetTickCount() + timeout;
TIMER_InsertTimer( pTimer );
return id;
}
/* Find a free timer */
for (i = 0, pTimer = TimersArray; i < NB_TIMERS; i++, pTimer++)
if (!pTimer->timeout) break;
if (i >= NB_TIMERS) return 0;
if (!sys && (i >= NB_TIMERS-NB_RESERVED_TIMERS)) return 0;
if (!hwnd) id = i + 1;
/* Add the timer */
pTimer->hwnd = hwnd;
pTimer->hq = (hwnd) ? GetThreadQueue( GetWindowThreadProcessId( hwnd, NULL ) )
: GetFastQueue( );
pTimer->msg = sys ? WM_SYSTIMER : WM_TIMER;
pTimer->id = id;
pTimer->timeout = timeout;
pTimer->expires = GetTickCount() + timeout;
pTimer->proc = (HWINDOWPROC)0;
if (proc) {
pTimer->proc = proc;
// WINPROC_SetProc( &pTimer->proc, proc, type, WIN_PROC_TIMER );
}
DPRINT( "Timer added: %p, %04x, %04x, %04x, %08lx\n",
pTimer, pTimer->hwnd, pTimer->msg, pTimer->id,
(DWORD)pTimer->proc );
TIMER_InsertTimer( pTimer );
if (!id) return TRUE;
else return id;
}
/***********************************************************************
* TIMER_KillTimer
*/
WINBOOL TIMER_KillTimer( HWND hwnd, UINT id,WINBOOL sys )
{
int i;
TIMER * pTimer;
/* Find the timer */
for (i = 0, pTimer = TimersArray; i < NB_TIMERS; i++, pTimer++)
if ((pTimer->hwnd == hwnd) && (pTimer->id == id) &&
(pTimer->timeout != 0)) break;
if (i >= NB_TIMERS) return FALSE;
if (!sys && (i >= NB_TIMERS-NB_RESERVED_TIMERS)) return FALSE;
if (!sys && (pTimer->msg != WM_TIMER)) return FALSE;
else if (sys && (pTimer->msg != WM_SYSTIMER)) return FALSE;
/* Delete the timer */
TIMER_ClearTimer( pTimer );
return TRUE;
}

View File

@@ -0,0 +1,893 @@
#include <windows.h>
#include <user32/win.h>
#include <user32/class.h>
#include <user32/menu.h>
#include <user32/winpos.h>
#include <user32/hook.h>
#include <user32/property.h>
#include <user32/dce.h>
#include <user32/caret.h>
#include <user32/debug.h>
WND *rootWnd;
//////////////////////////////////////////////////////////////////////////////////
WND *pWndDesktop;
HANDLE WIN_CreateWindowEx( CREATESTRUCTW *cs, ATOM classAtom)
{
HANDLE hWnd;
WND *wndPtr;
STARTUPINFO StartupInfo;
CLASS *classPtr = NULL;
POINT maxSize, maxPos, minTrack, maxTrack;
HWND hWndLinkAfter = NULL;
/* Create the window structure */
classPtr = CLASS_FindClassByAtom(classAtom,cs->hInstance);
if ( classPtr == NULL )
return NULL;
if (!(wndPtr = HeapAlloc(GetProcessHeap(),0, sizeof(WND) + classPtr->cbWndExtra
- sizeof(classPtr->wExtra) )))
{
return NULL;
}
wndPtr->next = rootWnd;
rootWnd = wndPtr;
wndPtr->class = classPtr;
// if ( CreatePipe(&(wndPtr->hmemTaskQ), &(wndPtr->hwndSelf),NULL,4096) == FALSE )
// return -1;
wndPtr->hwndSelf = wndPtr;
hWnd = wndPtr->hwndSelf;
/* Fill the window structure */
wndPtr->next = NULL;
wndPtr->child = NULL;
if ((cs->style & WS_CHILD) && cs->hWndParent)
{
wndPtr->parent = WIN_FindWndPtr( cs->hWndParent );
wndPtr->owner = NULL;
}
else
{
wndPtr->parent = pWndDesktop;
if (!cs->hWndParent || (cs->hWndParent == pWndDesktop->hwndSelf))
wndPtr->owner = NULL;
else
wndPtr->owner = WIN_GetTopParentPtr(WIN_FindWndPtr(cs->hWndParent));
}
wndPtr->winproc = classPtr->winproc;
wndPtr->dwMagic = WND_MAGIC;
//wndPtr->hwndSelf = hWnd;
wndPtr->hInstance = cs->hInstance;
wndPtr->text = NULL;
wndPtr->hmemTaskQ = GetFastQueue();
wndPtr->hrgnUpdate = 0;
wndPtr->hwndLastActive = wndPtr->hwndSelf;
wndPtr->dwStyle = cs->style & ~WS_VISIBLE;
wndPtr->dwExStyle = cs->dwExStyle;
wndPtr->wIDmenu = 0;
wndPtr->helpContext = 0;
wndPtr->flags = 0;
wndPtr->pVScroll = NULL;
wndPtr->pHScroll = NULL;
wndPtr->pProp = NULL;
wndPtr->userdata = 0;
wndPtr->hSysMenu = (wndPtr->dwStyle & WS_SYSMENU)
? MENU_GetSysMenu( hWnd, 0 ) : 0;
if (classPtr->cbWndExtra)
memset( wndPtr->wExtra, 0, classPtr->cbWndExtra);
/* Call the WH_CBT hook */
hWndLinkAfter = ((cs->style & (WS_CHILD|WS_MAXIMIZE)) == WS_CHILD) ? HWND_BOTTOM : HWND_TOP;
if (HOOK_IsHooked( WH_CBT ))
{
CBT_CREATEWNDW cbtc;
LRESULT ret;
cbtc.lpcs = cs;
cbtc.hwndInsertAfter = hWndLinkAfter;
ret = HOOK_CallHooksW(WH_CBT, HCBT_CREATEWND, hWnd, (LPARAM)&cbtc);
if (ret)
{
HeapFree( GetProcessHeap(),0,wndPtr );
return NULL;
}
}
/* Increment class window counter */
classPtr->cWindows++;
/* Correct the window style */
if (!(cs->style & (WS_POPUP | WS_CHILD))) /* Overlapped window */
{
wndPtr->dwStyle |= WS_CAPTION | WS_CLIPSIBLINGS;
wndPtr->flags |= WIN_NEED_SIZE;
}
if (cs->dwExStyle & WS_EX_DLGMODALFRAME)
wndPtr->dwStyle &= ~WS_THICKFRAME;
/* Get class or window DC if needed */
if (classPtr->style & CS_OWNDC) wndPtr->dce = DCE_AllocDCE(hWnd,DCE_WINDOW_DC);
else if (classPtr->style & CS_CLASSDC) wndPtr->dce = classPtr->dce;
else wndPtr->dce = NULL;
GetStartupInfoW((STARTUPINFO *)&StartupInfo);
if (cs->x == CW_USEDEFAULT)
{
if ( !(cs->style & (WS_CHILD | WS_POPUP))
&& (StartupInfo.dwFlags & STARTF_USEPOSITION) )
{
cs->x = StartupInfo.dwX;
cs->y = StartupInfo.dwY;
}
else
{
cs->x = 0;
cs->y = 0;
}
}
if (cs->cx == CW_USEDEFAULT)
{
if ( !(cs->style & (WS_CHILD | WS_POPUP))
&& (StartupInfo.dwFlags & STARTF_USESIZE) )
{
cs->cx = StartupInfo.dwXSize;
cs->cy = StartupInfo.dwYSize;
}
else
{
cs->cx = 600; /* FIXME */
cs->cy = 400;
}
}
/* Send the WM_GETMINMAXINFO message and fix the size if needed */
if ((cs->style & WS_THICKFRAME) || !(cs->style & (WS_POPUP | WS_CHILD)))
{
WINPOS_GetMinMaxInfo( wndPtr, &maxSize, &maxPos, &minTrack, &maxTrack);
if (maxSize.x < cs->cx) cs->cx = maxSize.x;
if (maxSize.y < cs->cy) cs->cy = maxSize.y;
if (cs->cx < minTrack.x ) cs->cx = minTrack.x;
if (cs->cy < minTrack.y ) cs->cy = minTrack.y;
}
if(cs->style & WS_CHILD)
{
if(cs->cx < 0) cs->cx = 0;
if(cs->cy < 0) cs->cy = 0;
}
else
{
if (cs->cx <= 0) cs->cx = 1;
if (cs->cy <= 0) cs->cy = 1;
}
wndPtr->rectWindow.left = cs->x;
wndPtr->rectWindow.top = cs->y;
wndPtr->rectWindow.right = cs->x + cs->cx;
wndPtr->rectWindow.bottom = cs->y + cs->cy;
wndPtr->rectClient = wndPtr->rectWindow;
/* Set the window menu */
if ((wndPtr->dwStyle & (WS_CAPTION | WS_CHILD)) == WS_CAPTION )
{
if (cs->hMenu)
SetMenu(hWnd, cs->hMenu);
else
{
if (classPtr->menuName) {
if ( classPtr->bUnicode == FALSE )
cs->hMenu = LoadMenuA(cs->hInstance,classPtr->menuName);
else
cs->hMenu = LoadMenuW(cs->hInstance,classPtr->menuName);
}
}
}
else
wndPtr->wIDmenu = (UINT)cs->hMenu;
/* Send the WM_CREATE message
* Perhaps we shouldn't allow width/height changes as well.
* See p327 in "Internals".
*/
maxPos.x = wndPtr->rectWindow.left;
maxPos.y = wndPtr->rectWindow.top;
if( SendMessageW( hWnd, WM_NCCREATE, 0, (LPARAM)cs) == 0)
{
/* Abort window creation */
WIN_DestroyWindow( wndPtr );
return NULL;
}
/* Insert the window in the linked list */
WIN_LinkWindow( hWnd, hWndLinkAfter );
WINPOS_SendNCCalcSize( hWnd, FALSE, &wndPtr->rectWindow,
NULL, NULL, 0, &wndPtr->rectClient );
OffsetRect(&wndPtr->rectWindow, maxPos.x - wndPtr->rectWindow.left,
maxPos.y - wndPtr->rectWindow.top);
if( (SendMessageW( hWnd, WM_CREATE, 0, (LPARAM)cs )) == -1 )
{
WIN_UnlinkWindow( hWnd );
WIN_DestroyWindow( wndPtr );
return NULL;
}
/* Send the size messages */
if (!(wndPtr->flags & WIN_NEED_SIZE))
{
/* send it anyway */
if (((wndPtr->rectClient.right-wndPtr->rectClient.left) <0)
||((wndPtr->rectClient.bottom-wndPtr->rectClient.top)<0))
SendMessageA( hWnd, WM_SIZE, SIZE_RESTORED,
MAKELONG(wndPtr->rectClient.right-wndPtr->rectClient.left,
wndPtr->rectClient.bottom-wndPtr->rectClient.top));
SendMessageA( hWnd, WM_MOVE, 0,
MAKELONG( wndPtr->rectClient.left,
wndPtr->rectClient.top ) );
}
/* Show the window, maximizing or minimizing if needed */
if (wndPtr->dwStyle & (WS_MINIMIZE | WS_MAXIMIZE))
{
RECT newPos;
UINT swFlag = (wndPtr->dwStyle & WS_MINIMIZE) ? SW_MINIMIZE : SW_MAXIMIZE;
wndPtr->dwStyle &= ~(WS_MAXIMIZE | WS_MINIMIZE);
WINPOS_MinMaximize( wndPtr, swFlag, &newPos );
swFlag = ((wndPtr->dwStyle & WS_CHILD) || GetActiveWindow())
? SWP_NOACTIVATE | SWP_NOZORDER | SWP_FRAMECHANGED
: SWP_NOZORDER | SWP_FRAMECHANGED;
SetWindowPos( hWnd, 0, newPos.left, newPos.top,
newPos.right, newPos.bottom, swFlag );
}
if( wndPtr->dwStyle & WS_CHILD && !(wndPtr->dwExStyle & WS_EX_NOPARENTNOTIFY) )
{
/* Notify the parent window only */
SendMessageA( wndPtr->parent->hwndSelf, WM_PARENTNOTIFY,
MAKEWPARAM(WM_CREATE, wndPtr->wIDmenu), (LPARAM)hWnd );
if( !IsWindow(hWnd) ) return 0;
}
if (cs->style & WS_VISIBLE)
ShowWindow( hWnd, SW_SHOW );
/* Call WH_SHELL hook */
if (!(wndPtr->dwStyle & WS_CHILD) && !wndPtr->owner)
HOOK_CallHooksW( WH_SHELL, HSHELL_WINDOWCREATED, hWnd, 0L );
return hWnd;
}
/***********************************************************************
* WIN_FindWinToRepaint
*
* Find a window that needs repaint.
*/
HWND WIN_FindWinToRepaint( HWND hwnd, HQUEUE hQueue )
{
HWND hwndRet;
WND *pWnd = pWndDesktop;
/* Note: the desktop window never gets WM_PAINT messages
* The real reason why is because Windows DesktopWndProc
* does ValidateRgn inside WM_ERASEBKGND handler.
*/
pWnd = hwnd ? WIN_FindWndPtr( hwnd ) : pWndDesktop->child;
for ( ; pWnd ; pWnd = pWnd->next )
{
if (!(pWnd->dwStyle & WS_VISIBLE))
{
DPRINT( "skipping window %04x\n",
pWnd->hwndSelf );
continue;
}
if ((pWnd->hmemTaskQ == hQueue) &&
(pWnd->hrgnUpdate || (pWnd->flags & WIN_INTERNAL_PAINT))) break;
if (pWnd->child )
if ((hwndRet = WIN_FindWinToRepaint( pWnd->child->hwndSelf, hQueue )) )
return hwndRet;
}
if (!pWnd) return 0;
hwndRet = pWnd->hwndSelf;
/* look among siblings if we got a transparent window */
while (pWnd && ((pWnd->dwExStyle & WS_EX_TRANSPARENT) ||
!(pWnd->hrgnUpdate || (pWnd->flags & WIN_INTERNAL_PAINT))))
{
pWnd = pWnd->next;
}
if (pWnd) hwndRet = pWnd->hwndSelf;
DPRINT("found %04x\n",hwndRet);
return hwndRet;
}
/**********************************************************************
* WIN_GetWindowLong
*
* Helper function for GetWindowLong().
*/
LONG WIN_GetWindowLong( HWND hwnd, INT offset )
{
LONG retval;
WND * wndPtr = WIN_FindWndPtr( hwnd );
if (!wndPtr) return 0;
if (offset >= 0)
{
if (offset + sizeof(LONG) > wndPtr->class->cbWndExtra)
{
DPRINT( "Invalid offset %d\n", offset );
return 0;
}
retval = *(LONG *)(((char *)wndPtr->wExtra) + offset);
return retval;
}
switch(offset)
{
case GWL_USERDATA: return wndPtr->userdata;
case GWL_STYLE: return wndPtr->dwStyle;
case GWL_EXSTYLE: return wndPtr->dwExStyle;
case GWL_ID: return (LONG)wndPtr->wIDmenu;
case GWL_WNDPROC: return (LONG)wndPtr->winproc;
case GWL_HWNDPARENT: return wndPtr->parent ? (LONG)wndPtr->parent->hwndSelf : (LONG)0;
case GWL_HINSTANCE: return (LONG)wndPtr->hInstance;
default:
DPRINT( "Unknown offset %d\n", offset );
}
return 0;
}
/**********************************************************************
* WIN_SetWindowLong
*
* Helper function for SetWindowLong().
*
* 0 is the failure code. However, in the case of failure SetLastError
* must be set to distinguish between a 0 return value and a failure.
*
* FIXME: The error values for SetLastError may not be right. Can
* someone check with the real thing?
*/
LONG WIN_SetWindowLong( HWND hwnd, INT offset, LONG newval )
{
LONG *ptr, retval = 0;
WND * wndPtr = WIN_FindWndPtr( hwnd );
STYLESTRUCT style;
//DPRINT("%x=%p %x %lx %x\n",hwnd, wndPtr, offset, newval, type);
if (!wndPtr)
{
/* Is this the right error? */
SetLastError( ERROR_INVALID_WINDOW_HANDLE );
return 0;
}
if (offset >= 0)
{
if (offset + sizeof(LONG) > wndPtr->class->cbWndExtra)
{
DPRINT( "Invalid offset %d\n", offset );
/* Is this the right error? */
SetLastError( ERROR_OUTOFMEMORY );
return 0;
}
ptr = (LONG *)(((char *)wndPtr->wExtra) + offset);
/* Special case for dialog window procedure */
if ((offset == DWL_DLGPROC) && (wndPtr->flags & WIN_ISDIALOG))
{
retval = ptr;
*ptr = newval;
return (LONG)retval;
}
}
else switch(offset)
{
case GWL_ID:
ptr = (DWORD*)&wndPtr->wIDmenu;
break;
case GWL_HINSTANCE:
return SetWindowWord( hwnd, offset, newval );
case GWL_WNDPROC:
retval = wndPtr->winproc;
wndPtr->winproc = (WNDPROC)newval;
return retval;
case GWL_STYLE:
style.styleOld = wndPtr->dwStyle;
newval &= ~(WS_VISIBLE | WS_CHILD); /* Some bits can't be changed this way */
style.styleNew = newval | (style.styleOld & (WS_VISIBLE | WS_CHILD));
//if (wndPtr->flags & WIN_ISWIN32)
SendMessageA(hwnd,WM_STYLECHANGING,GWL_STYLE,(LPARAM)&style);
wndPtr->dwStyle = style.styleNew;
//if (wndPtr->flags & WIN_ISWIN32)
SendMessageA(hwnd,WM_STYLECHANGED,GWL_STYLE,(LPARAM)&style);
return style.styleOld;
case GWL_USERDATA:
ptr = &wndPtr->userdata;
break;
case GWL_EXSTYLE:
style.styleOld = wndPtr->dwExStyle;
style.styleNew = newval;
//if (wndPtr->flags & WIN_ISWIN32)
SendMessageA(hwnd,WM_STYLECHANGING,GWL_EXSTYLE,(LPARAM)&style);
wndPtr->dwExStyle = newval;
//if (wndPtr->flags & WIN_ISWIN32)
SendMessageA(hwnd,WM_STYLECHANGED,GWL_EXSTYLE,(LPARAM)&style);
return style.styleOld;
default:
DPRINT( "Invalid offset %d\n", offset );
/* Don't think this is right error but it should do */
SetLastError( ERROR_OUTOFMEMORY );
return 0;
}
retval = *ptr;
*ptr = newval;
return retval;
}
/***********************************************************************
* WIN_DestroyWindow
*
* Destroy storage associated to a window. "Internals" p.358
*/
WINBOOL WIN_DestroyWindow( WND* wndPtr )
{
HWND hWnd;
WND *pWnd;
hWnd = wndPtr->hwndSelf;
#ifdef CONFIG_IPC
if (main_block)
DDE_DestroyWindow(wndPtr->hwndSelf);
#endif /* CONFIG_IPC */
/* free child windows */
while ((pWnd = wndPtr->child))
wndPtr->child = WIN_DestroyWindow( pWnd );
SendMessageA( wndPtr->hwndSelf, WM_NCDESTROY, 0, 0);
/* FIXME: do we need to fake QS_MOUSEMOVE wakebit? */
WINPOS_CheckInternalPos( hWnd );
if( hWnd == GetCapture()) ReleaseCapture();
/* free resources associated with the window */
// TIMER_RemoveWindowTimers( wndPtr->hwndSelf );
PROPERTY_RemoveWindowProps( wndPtr );
wndPtr->dwMagic = 0; /* Mark it as invalid */
if ((wndPtr->hrgnUpdate) || (wndPtr->flags & WIN_INTERNAL_PAINT))
{
if ((UINT)wndPtr->hrgnUpdate > 1)
DeleteObject( wndPtr->hrgnUpdate );
//QUEUE_DecPaintCount( wndPtr->hmemTaskQ );
}
// changed message queue implementation with pipes
/* toss stale messages from the queue */
#if 0
if( wndPtr->hmemTaskQ )
{
int pos;
WINBOOL bPostQuit = FALSE;
WPARAM wQuitParam = 0;
MESSAGEQUEUE* msgQ = (MESSAGEQUEUE*) GlobalLock(wndPtr->hmemTaskQ);
while( (pos = QUEUE_FindMsg(msgQ, hWnd, 0, 0)) != -1 )
{
if( msgQ->messages[pos].msg.message == WM_QUIT )
{
bPostQuit = TRUE;
wQuitParam = msgQ->messages[pos].msg.wParam;
}
QUEUE_RemoveMsg(msgQ, pos);
}
/* repost WM_QUIT to make sure this app exits its message loop */
if( bPostQuit ) PostQuitMessage(wQuitParam);
wndPtr->hmemTaskQ = 0;
}
#endif
if (!(wndPtr->dwStyle & WS_CHILD))
if (wndPtr->wIDmenu) DestroyMenu( (HMENU)wndPtr->wIDmenu );
if (wndPtr->hSysMenu) DestroyMenu( wndPtr->hSysMenu );
//wndPtr->pDriver->pDestroyWindow( wndPtr );
//DeleteDC(wndPtr->dc) /* Always do this to catch orphaned DCs */
wndPtr->winproc = NULL;
wndPtr->hwndSelf = NULL;
wndPtr->class->cWindows--;
wndPtr->class = NULL;
pWnd = wndPtr->next;
//wndPtr->pDriver->pFinalize(wndPtr);
HeapFree( GetProcessHeap(),0,wndPtr );
return 0;
}
/***********************************************************************
* WIN_ResetQueueWindows
*
* Reset the queue of all the children of a given window.
* Return TRUE if something was done.
*/
WINBOOL WIN_ResetQueueWindows( WND* wnd, HQUEUE hQueue, HQUEUE hNew )
{
WINBOOL ret = FALSE;
if (hNew) /* Set a new queue */
{
for (wnd = wnd->child; (wnd); wnd = wnd->next)
{
if (wnd->hmemTaskQ == hQueue)
{
wnd->hmemTaskQ = hNew;
ret = TRUE;
}
if (wnd->child)
ret |= WIN_ResetQueueWindows( wnd, hQueue, hNew );
}
}
else /* Queue is being destroyed */
{
while (wnd->child)
{
WND *tmp = wnd->child;
ret = FALSE;
while (tmp)
{
if (tmp->hmemTaskQ == hQueue)
{
DestroyWindow( tmp->hwndSelf );
ret = TRUE;
break;
}
if (tmp->child && WIN_ResetQueueWindows(tmp->child,hQueue,0))
ret = TRUE;
else
tmp = tmp->next;
}
if (!ret) break;
}
}
return ret;
}
#if 0
WND * WIN_FindWndPtr( HWND hWnd )
{
WND *wndPtr = rootWnd;
while ( wndPtr != NULL ) {
if ( wndPtr->hwndSelf == hWnd )
return wndPtr;
wndPtr->next = wndPtr;
}
return NULL;
}
#endif
WND * WIN_FindWndPtr( HWND hwnd )
{
WND * ptr;
if ( hwnd == NULL ) return NULL;
ptr = (WND *)( hwnd );
if (ptr->dwMagic != WND_MAGIC) return NULL;
if (ptr->hwndSelf != hwnd)
{
DPRINT( "Can't happen: hwnd %04x self pointer is %04x\n",
hwnd, ptr->hwndSelf );
return NULL;
}
return ptr;
}
WND* WIN_GetDesktop(void)
{
return NULL;
}
WND **WIN_BuildWinArray( WND *wndPtr, UINT bwaFlags, UINT* pTotal )
{
WND **list, **ppWnd;
WND *pWnd;
UINT count, skipOwned, skipHidden;
DWORD skipFlags;
skipHidden = bwaFlags & BWA_SKIPHIDDEN;
skipOwned = bwaFlags & BWA_SKIPOWNED;
skipFlags = (bwaFlags & BWA_SKIPDISABLED) ? WS_DISABLED : 0;
if( bwaFlags & BWA_SKIPICONIC ) skipFlags |= WS_MINIMIZE;
/* First count the windows */
if (!wndPtr) wndPtr = pWndDesktop;
for (pWnd = wndPtr->child, count = 0; pWnd; pWnd = pWnd->next)
{
if( (pWnd->dwStyle & skipFlags) || (skipOwned && pWnd->owner) ) continue;
if( !skipHidden || pWnd->dwStyle & WS_VISIBLE ) count++;
}
if( count )
{
/* Now build the list of all windows */
if ((list = (WND **)HeapAlloc( GetProcessHeap(), 0, sizeof(WND *) * (count + 1))))
{
for (pWnd = wndPtr->child, ppWnd = list, count = 0; pWnd; pWnd = pWnd->next)
{
if( (pWnd->dwStyle & skipFlags) || (skipOwned && pWnd->owner) ) continue;
if( !skipHidden || pWnd->dwStyle & WS_VISIBLE )
{
*ppWnd++ = pWnd;
count++;
}
}
*ppWnd = NULL;
}
else count = 0;
} else list = NULL;
if( pTotal ) *pTotal = count;
return list;
}
void WIN_DestroyList( WND **list )
{
HeapFree(GetProcessHeap(),0,*list);
}
/***********************************************************************
* WIN_UnlinkWindow
*
* Remove a window from the siblings linked list.
*/
WINBOOL WIN_UnlinkWindow( HWND hWnd )
{
WND *wndPtr, **ppWnd;
if (!(wndPtr = WIN_FindWndPtr( hWnd )) || !wndPtr->parent) return FALSE;
ppWnd = &wndPtr->parent->child;
while (*ppWnd != wndPtr) ppWnd = &(*ppWnd)->next;
*ppWnd = wndPtr->next;
return TRUE;
}
/***********************************************************************
* WIN_LinkWindow
*
* Insert a window into the siblings linked list.
* The window is inserted after the specified window, which can also
* be specified as HWND_TOP or HWND_BOTTOM.
*/
WINBOOL WIN_LinkWindow( HWND hWnd, HWND hWndInsertAfter )
{
WND *wndPtr, **ppWnd;
if (!(wndPtr = WIN_FindWndPtr( hWnd )) || !wndPtr->parent) return FALSE;
if ((hWndInsertAfter == HWND_TOP) || (hWndInsertAfter == HWND_BOTTOM))
{
ppWnd = &wndPtr->parent->child; /* Point to first sibling hWnd */
if (hWndInsertAfter == HWND_BOTTOM) /* Find last sibling hWnd */
while (*ppWnd) ppWnd = &(*ppWnd)->next;
}
else /* Normal case */
{
WND * afterPtr = WIN_FindWndPtr( hWndInsertAfter );
if (!afterPtr) return FALSE;
ppWnd = &afterPtr->next;
}
wndPtr->next = *ppWnd;
*ppWnd = wndPtr;
return TRUE;
}
void WIN_UpdateNCArea(WND* wnd, BOOL bUpdate)
{
POINT pt = {0, 0};
HRGN hClip = 1;
DPRINT("hwnd %04x, hrgnUpdate %04x\n",
wnd->hwndSelf, wnd->hrgnUpdate );
/* desktop window doesn't have nonclient area */
if(wnd == WIN_GetDesktop())
{
wnd->flags &= ~WIN_NEEDS_NCPAINT;
return;
}
if( wnd->hrgnUpdate > 1 )
{
ClientToScreen(wnd->hwndSelf, &pt);
hClip = CreateRectRgn( 0, 0, 0, 0 );
if (!CombineRgn( hClip, wnd->hrgnUpdate, 0, RGN_COPY ))
{
DeleteObject(hClip);
hClip = 1;
}
else
OffsetRgn( hClip, pt.x, pt.y );
if (bUpdate)
{
/* exclude non-client area from update region */
HRGN hrgn = CreateRectRgn( 0, 0,
wnd->rectClient.right - wnd->rectClient.left,
wnd->rectClient.bottom - wnd->rectClient.top);
if (hrgn && (CombineRgn( wnd->hrgnUpdate, wnd->hrgnUpdate,
hrgn, RGN_AND) == NULLREGION))
{
DeleteObject( wnd->hrgnUpdate );
wnd->hrgnUpdate = 1;
}
DeleteObject( hrgn );
}
}
wnd->flags &= ~WIN_NEEDS_NCPAINT;
if ((wnd->hwndSelf == GetActiveWindow()) &&
!(wnd->flags & WIN_NCACTIVATED))
{
wnd->flags |= WIN_NCACTIVATED;
if( hClip > 1) DeleteObject( hClip );
hClip = 1;
}
if (hClip) SendMessage( wnd->hwndSelf, WM_NCPAINT, hClip, 0L );
if (hClip > 1) DeleteObject( hClip );
}
/***********************************************************************
* WIN_IsWindowDrawable
*
* hwnd is drawable when it is visible, all parents are not
* minimized, and it is itself not minimized unless we are
* trying to draw its default class icon.
*/
WINBOOL WIN_IsWindowDrawable( WND* wnd, WINBOOL icon )
{
if( (wnd->dwStyle & WS_MINIMIZE &&
icon && wnd->class->hIcon) ||
!(wnd->dwStyle & WS_VISIBLE) ) return FALSE;
for(wnd = wnd->parent; wnd; wnd = wnd->parent)
if( wnd->dwStyle & WS_MINIMIZE ||
!(wnd->dwStyle & WS_VISIBLE) ) break;
return (wnd == NULL);
}
WND* WIN_GetTopParentPtr( WND* pWnd )
{
while( pWnd && (pWnd->dwStyle & WS_CHILD)) pWnd = pWnd->parent;
return pWnd;
}
HWND WIN_GetTopParent( HWND hwnd )
{
WND *wndPtr = WIN_GetTopParentPtr ( WIN_FindWndPtr( hwnd ) );
return wndPtr ? wndPtr->hwndSelf : 0;
}
void WIN_CheckFocus( WND* pWnd )
{
if( GetFocus() == pWnd->hwndSelf )
SetFocus( (pWnd->dwStyle & WS_CHILD) ? pWnd->parent->hwndSelf : 0 );
}
void WIN_SendDestroyMsg( WND* pWnd )
{
WIN_CheckFocus(pWnd);
if( CARET_GetHwnd() == pWnd->hwndSelf ) DestroyCaret();
// CLIPBOARD_GetDriver()->pResetOwner( pWnd, TRUE );
SendMessageA( pWnd->hwndSelf, WM_DESTROY, 0, 0);
if( IsWindow(pWnd->hwndSelf) )
{
WND* pChild = pWnd->child;
while( pChild )
{
WIN_SendDestroyMsg( pChild );
pChild = pChild->next;
}
WIN_CheckFocus(pWnd);
}
else
DPRINT( "\tdestroyed itself while in WM_DESTROY!\n");
}
/*******************************************************************
* GetSysModalWindow16 (USER.52)
*/
HWND GetSysModalWindow(void)
{
return NULL;
}

View File

@@ -0,0 +1,29 @@
all: user32.exe
INTERNAL_OBJECTS = internal/property.o internal/menu.o internal/heapdup.o internal/nc.o\
internal/scroll.o internal/win.o internal/dce.o internal/msg.o internal/queue.o\
internal/signal.o internal/event.o internal/timer.o internal/region.o\
internal/text.o
MISC_OBJECTS = misc/sprintf.o misc/dllmain.o misc/string.o misc/sysmetr.o\
misc/main.o misc/bitmap.o misc/cursor.o misc/vk.o
WINDOWS_OBJECTS = windows/wndproc.o windows/win.o windows/hook.o windows/spy.o\
windows/queue.o windows/winpos.o windows/class.o windows/menu.o windows/dc.o\
windows/timer.o windows/rect.o windows/msg.o windows/input.o windows/property.o\
windows/focus.o
GRAPHICS_OBJECTS = graphics/rect.o graphics/caret.o graphics/text.o graphics/syscol.o graphics/fill.o\
graphics/draw.o
RESOURCE_OBJECTS = resources/sysres.o
OBJECTS = $(MISC_OBJECTS) $(INTERNAL_OBJECTS) $(GRAPHICS_OBJECTS) $(RESOURCE_OBJECTS) $(WINDOWS_OBJECTS)
user32.exe: $(OBJECTS)
$(LD) $(OBJECTS) F:/gnu/cygnus/cygwin-b20/H-i586-cygwin32/i586-cygwin32/lib/crt1.o F:/gnu/cygnus/cygwin-b20/H-i586-cygwin32/i586-cygwin32/lib/libgdi32.a F:/gnu/cygnus/cygwin-b20/H-i586-cygwin32/i586-cygwin32/lib/libkernel32.a F:/gnu/cygnus/cygwin-b20/H-i586-cygwin32/i586-cygwin32/lib/libcrtdll.a -o user32.exe
dummy:
include ../../Rules.mak

View File

@@ -0,0 +1,80 @@
#include <windows.h>
HBITMAP BITMAP_LoadBitmapW(HINSTANCE instance,LPCWSTR name, UINT loadflags);
HBITMAP LoadBitmapW(HINSTANCE hInstance, LPCWSTR lpBitmapName)
{
return BITMAP_LoadBitmapW(hInstance, lpBitmapName, 0);
}
HBITMAP LoadBitmapA(HINSTANCE hInstance, LPCSTR lpBitmapName)
{
return NULL;
// return BITMAP_LoadBitmap32W(hInstance, lpBitmapName, 0);
}
HBITMAP BITMAP_LoadBitmapW(HINSTANCE instance,LPCWSTR name,
UINT loadflags)
{
#if 0
HBITMAP hbitmap = 0;
HDC hdc;
HRSRC hRsrc;
HGLOBAL handle;
char *ptr = NULL;
BITMAPINFO *info, *fix_info=NULL;
HGLOBAL hFix;
int size;
if (!(loadflags & LR_LOADFROMFILE)) {
if (!instance) /* OEM bitmap */
{
HDC hdc;
DC *dc;
if (HIWORD((int)name)) return 0;
hdc = CreateDCA( "DISPLAY", NULL, NULL, NULL );
dc = DC_GetDCPtr( hdc );
if(dc->funcs->pLoadOEMResource)
hbitmap = dc->funcs->pLoadOEMResource( LOWORD((int)name),
OEM_BITMAP );
GDI_HEAP_UNLOCK( hdc );
DeleteDC( hdc );
return hbitmap;
}
if (!(hRsrc = FindResourceW( instance, name, RT_BITMAPW ))) return 0;
if (!(handle = LoadResource( instance, hRsrc ))) return 0;
if ((info = (BITMAPINFO *)LockResource( handle )) == NULL) return 0;
}
else
{
if (!(ptr = (char *)VIRTUAL_MapFileW( name ))) return 0;
info = (BITMAPINFO *)(ptr + sizeof(BITMAPFILEHEADER));
}
size = DIB_BitmapInfoSize(info, DIB_RGB_COLORS);
if ((hFix = GlobalAlloc(0, size))) fix_info=GlobalLock(hFix);
if (fix_info) {
BYTE pix;
memcpy(fix_info, info, size);
pix = *((LPBYTE)info+DIB_BitmapInfoSize(info, DIB_RGB_COLORS));
DIB_FixColorsToLoadflags(fix_info, loadflags, pix);
if ((hdc = GetDC(0)) != 0) {
if (loadflags & LR_CREATEDIBSECTION)
hbitmap = CreateDIBSection(hdc, fix_info, DIB_RGB_COLORS, NULL, 0, 0);
else {
char *bits = (char *)info + size;;
hbitmap = CreateDIBitmap( hdc, &fix_info->bmiHeader, CBM_INIT,
bits, fix_info, DIB_RGB_COLORS );
}
ReleaseDC( 0, hdc );
}
GlobalUnlock(hFix);
GlobalFree(hFix);
}
if (loadflags & LR_LOADFROMFILE) UnmapViewOfFile( ptr );
return hbitmap;
#endif
}

View File

@@ -0,0 +1,34 @@
#include <windows.h>
/***********************************************************************
* SetCursor (USER32.472)
* RETURNS:
* A handle to the previous cursor shape.
*/
HCURSOR STDCALL SetCursor( HCURSOR hCursor )
{
}
int STDCALL ShowCursor(WINBOOL bShow )
{
}
WINBOOL STDCALL SetCursorPos(int x, int y )
{
}
HCURSOR STDCALL LoadCursorA(HINSTANCE hInstance, LPCSTR lpCursorName )
{
}
HCURSOR STDCALL LoadCursorW(HINSTANCE hInstance, LPCWSTR lpCursorName )
{
}
WINBOOL
STDCALL
DestroyCursor(
HCURSOR hCursor)
{
}

View File

@@ -0,0 +1,72 @@
#include <windows.h>
LRESULT CALLBACK WindowFunc(HWND,UINT,WPARAM, LPARAM);
char szName[] = "Hallo";
int _CRT_fmode = 0;
int _CRT_glob = 0;
int __main(int argc, char **argv)
{
}
int main(int argc, char **argv)
{
HWND hwnd;
MSG msg;
WNDCLASSEX wc1;
HINSTANCE hInst = 0;
int nWinMode = 0;
wc1.hInstance = hInst;
wc1.lpszClassName = szName;
wc1.lpfnWndProc = WindowFunc;
wc1.style = 0;
wc1.cbSize = sizeof(WNDCLASSEX);
wc1.hIcon = NULL;
wc1.hIconSm = NULL;
wc1.hCursor = NULL;
wc1.lpszMenuName = NULL;
wc1.cbClsExtra = 0;
wc1.cbWndExtra = 0;
wc1.hbrBackground = NULL;
if ( !RegisterClassEx(&wc1)) return 0;
hwnd = CreateWindowEx(0, szName, "test", WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT,CW_USEDEFAULT,CW_USEDEFAULT,CW_USEDEFAULT,
NULL,NULL,hInst, NULL);
ShowWindow(hwnd,nWinMode);
UpdateWindow(hwnd);
while(GetMessage(&msg,NULL, 0, 0))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
return msg.wParam;
}
//printf("hallo\n");
LRESULT CALLBACK WindowFunc(HWND hwnd,UINT message,WPARAM wParam, LPARAM lParam)
{
switch(message)
{
case WM_DESTROY:
PostQuitMessage(0);
break;
default:
return DefWindowProc(hwnd, message, wParam, lParam);
}
return 0;
}

View File

@@ -0,0 +1,813 @@
/*
* String functions
*
* Copyright 1993 Yngvi Sigurjonsson (yngvi@hafro.is)
* Copyright 1996 Marcus Meissner
*/
#include <windows.h>
#include <string.h>
#include <stdarg.h>
#include <wchar.h>
#include <ddk/ntddk.h>
/* Funny to divide them between user and kernel. */
/* be careful: always use functions from wctype.h if character > 255 */
/*
* Unicode case conversion routines ... these should be used where
* toupper/tolower are used for ASCII.
*/
// bugfix: mutual exclusiveness of
// FORMAT_MESSAGE_FROM_STRING, FORMAT_MESSAGE_FROM_SYSTEM and FORMAT_MESSAGE_FROM_HMODULE
// in FormatMessage
#define IsDBCSLeadByte(c) FALSE
#define IsDBCSLeadByteEx(c,n) FALSE
#define CopyMemory memcpy
#define lstrlenA strlen
#define lstrlenW wcslen
DWORD LoadMessageA(HMODULE hModule,DWORD dwMessageId,
DWORD dwLanguageId,LPSTR Buffer,UINT BufSize);
DWORD LoadMessageW(HMODULE hModule,DWORD dwMessageId,
DWORD dwLanguageId,LPWSTR Buffer,UINT BufSize);
LPWSTR lstrchrW(LPCWSTR s, INT c);
LPSTR lstrchrA(LPCSTR s, INT c);
LPSTR STDCALL CharNextA(LPCSTR lpsz)
{
LPSTR next = (LPSTR)lpsz;
if (!*lpsz)
return next;
if (IsDBCSLeadByte( *next ))
next++;
next++;
return next;
}
/***********************************************************************
* CharNextExA (USER.30)
*/
LPSTR STDCALL CharNextExA( WORD codepage, LPCSTR ptr, DWORD flags )
{
LPSTR next = (LPSTR)ptr;
if (!*ptr)
return next;
if (IsDBCSLeadByteEx( codepage, *next ))
return next++;
next++;
return next;
}
LPWSTR
STDCALL
CharNextW(LPCWSTR lpsz)
{
LPWSTR next = (LPWSTR)lpsz;
if (!*lpsz)
return next;
next++;
return next;
}
LPSTR STDCALL CharPrevA( LPCSTR start, LPCSTR ptr )
{
LPCSTR next;
while (*start && (start < ptr))
{
next = CharNextA( start );
if (next >= ptr)
break;
start = next;
}
return (LPSTR)start;
}
LPSTR STDCALL CharPrevExA( WORD codepage, LPCSTR start, LPCSTR ptr, DWORD flags )
{
LPCSTR next;
while (*start && (start < ptr))
{
next = CharNextExA( codepage, start, flags );
if (next > ptr)
break;
start = next;
}
return (LPSTR)start;
}
LPWSTR STDCALL CharPrevW(LPCWSTR start,LPCWSTR x)
{
LPWSTR prev = (LPWSTR)x;
if (x<=start)
return prev;
prev--;
return prev;
}
LPSTR STDCALL CharLowerA(LPSTR x)
{
LPSTR s;
UINT s2;
if (!HIWORD(x)) {
s2 = (UINT)x;
if (!IsDBCSLeadByte( s2 )) {
if (!IsCharLowerA(s2))
s2 = s2 - ( 'A' - 'a' );
return (LPSTR)s2;
}
else {
// should do a multibyte toupper
if (s2 >= 'A' && s2 <= 'Z')
s2 = s2 - ( 'A' - 'a' );
return (LPSTR)s2;
}
return (LPSTR)x;
}
s=x;
while (*s)
{
if (!IsDBCSLeadByte( *s )) {
if (!IsCharLowerA(*s))
*s = *s - ( 'A' - 'a' );
}
else {
// should do a multibyte toupper
s++;
}
s++;
}
return x;
}
DWORD STDCALL CharLowerBuffA(LPSTR s,DWORD buflen)
{
DWORD done=0;
if (!s)
return 0; /* YES */
while (*s && (buflen--))
{
if (!IsDBCSLeadByte( *s )) {
if (!IsCharLowerA(*s))
*s = *s - ( 'A' - 'a' );
}
else {
// should do a multibyte toupper
s++;
}
s++;
done++;
}
return done;
}
DWORD STDCALL CharLowerBuffW(LPWSTR s,DWORD buflen)
{
DWORD done=0;
if (!s)
return 0; /* YES */
while (*s && (buflen--))
{
if (!IsCharLowerW(*s))
*s = *s - ( L'A' - L'a' );
s++;
done++;
}
return done;
}
LPWSTR STDCALL CharLowerW(LPWSTR x)
{
LPWSTR s;
UINT s2;
if (!HIWORD(x)) {
s2 = (UINT)x;
if (!IsCharLowerW(s2))
s2 = s2 - ( L'A' - L'a' );
return (LPWSTR)s2;
}
s = x;
while (*s)
{
if (!IsCharLowerW(*s))
*s = *s - ( L'A' - L'a' );
s++;
}
return x;
}
LPSTR STDCALL CharUpperA(LPSTR x)
{
LPSTR s;
UINT s2;
if (!HIWORD(x)) {
s2 = (UINT)x;
if (!IsDBCSLeadByte( s2 )) {
if (!IsCharUpperW(s2))
s2 = s2 + ( 'A' - 'a' );
return (LPSTR)s2;
}
else {
// should do a multibyte toupper
if (s2 >= 'a' && s2 <= 'z')
s2 = s2 + ( 'A' - 'a' );
return (LPSTR)s2;
}
return x;
}
s=x;
while (*s)
{
if (!IsDBCSLeadByte( *s )) {
if (!IsCharUpperW(*s))
*s = *s + ( 'A' - 'a' );
}
else {
// should do a multibyte toupper
s++;
}
s++;
}
return x;
}
DWORD STDCALL CharUpperBuffA(LPSTR s,DWORD buflen)
{
DWORD done=0;
if (!s)
return 0; /* YES */
while (*s && (buflen--))
{
if (!IsDBCSLeadByte( *s )) {
if (!IsCharUpperW(*s))
*s = *s + ( 'A' - 'a' );
}
else {
// should do a multibyte toupper
s++;
}
s++;
done++;
}
return done;
}
DWORD STDCALL CharUpperBuffW(LPWSTR s,DWORD buflen)
{
DWORD done=0;
if (!s)
return 0; /* YES */
while (*s && (buflen--))
{
if (!IsCharUpperW(*s))
*s = *s + ( L'A' - L'a' );
s++;
done++;
}
return done;
}
LPWSTR STDCALL CharUpperW(LPWSTR x)
{
LPWSTR s;
UINT s2;
if (!HIWORD(x)) {
s2 = (UINT)x;
if (!IsCharUpperW(s2))
s2 = s2 + ( L'A' - L'a' );
return (LPWSTR)s2;
}
s = x;
while (*s)
{
if (!IsCharUpperW(*s))
*s = *s + ( L'A' - L'a' );
s++;
}
return x;
}
WINBOOL STDCALL IsCharAlphaNumericA(CHAR c)
{
return ((c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z') || (c >= '0' && c <= '9'));
}
WINBOOL STDCALL IsCharAlphaNumericW(WCHAR c)
{
return ((c >= L'A' && c <= L'Z') || (c >= L'a' && c <= L'z') || (c >= L'0' && c <= L'9'));
}
WINBOOL STDCALL IsCharAlphaA(CHAR c)
{
return (c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z');
}
WINBOOL STDCALL IsCharAlphaW(WCHAR c)
{
return (c >= L'A' && c <= L'Z') || (c >= L'a' && c <= L'z');
}
WINBOOL STDCALL IsCharLowerA(CHAR c)
{
return (c >= 'a' && c <= 'z');
}
WINBOOL STDCALL IsCharLowerW(WCHAR c)
{
return (c >= L'a' && c <= L'z');
}
WINBOOL STDCALL IsCharUpperA(CHAR c)
{
return (c >= 'A' && c <= 'Z' );
}
WINBOOL STDCALL IsCharUpperW(WCHAR c)
{
return (c >= L'A' && c <= L'Z' );
}
DWORD STDCALL FormatMessageA(
DWORD dwFlags,
LPCVOID lpSource,
DWORD dwMessageId,
DWORD dwLanguageId,
LPSTR lpBuffer,
DWORD nSize,
va_list *Arguments
) {
LPSTR target,t;
DWORD talloced;
LPSTR from,f;
//DWORD width = dwFlags & FORMAT_MESSAGE_MAX_WIDTH_MASK;
DWORD nolinefeed = 0;
DWORD len;
////TRACE(resource, "(0x%lx,%p,%ld,0x%lx,%p,%ld,%p)\n",
// dwFlags,lpSource,dwMessageId,dwLanguageId,lpBuffer,nSize,Arguments);
//if (width)
// FIXME(resource,"line wrapping not supported.\n");
from = NULL;
if (dwFlags & FORMAT_MESSAGE_FROM_STRING) {
len = lstrlenA((LPSTR)lpSource);
from = HeapAlloc( GetProcessHeap(),0, len+1 );
CopyMemory(from,lpSource,len+1);
}
else if (dwFlags & FORMAT_MESSAGE_FROM_SYSTEM) {
len = 200;
from = HeapAlloc( GetProcessHeap(),0,200 );
wsprintfA(from,"Systemmessage, messageid = 0x%08lx\n",dwMessageId);
}
else if (dwFlags & FORMAT_MESSAGE_FROM_HMODULE) {
INT bufsize;
dwMessageId &= 0xFFFF;
bufsize=LoadMessageA((HMODULE)lpSource,dwMessageId,dwLanguageId,NULL,100);
if (bufsize) {
from = HeapAlloc( GetProcessHeap(), 0, bufsize + 1 );
LoadMessageA((HMODULE)lpSource,dwMessageId,dwLanguageId,from,bufsize+1);
}
}
target = HeapAlloc( GetProcessHeap(), HEAP_ZERO_MEMORY, 100);
t = target;
talloced= 100;
#define ADD_TO_T(c) \
*t++=c;\
if (t-target == talloced) {\
target = (char*)HeapReAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,target,talloced*2);\
t = target+talloced;\
talloced*=2;\
}
if (from) {
f=from;
while (*f && !nolinefeed) {
if (*f=='%') {
int insertnr;
char *fmtstr,*sprintfbuf,*x,*lastf;
DWORD *argliststart;
fmtstr = NULL;
lastf = f;
f++;
if (!*f) {
ADD_TO_T('%');
continue;
}
switch (*f) {
case '1':case '2':case '3':case '4':case '5':
case '6':case '7':case '8':case '9':
insertnr=*f-'0';
switch (f[1]) {
case '0':case '1':case '2':case '3':
case '4':case '5':case '6':case '7':
case '8':case '9':
f++;
insertnr=insertnr*10+*f-'0';
f++;
break;
default:
f++;
break;
}
if (*f=='!') {
f++;
if (NULL!=(x=lstrchrA(f,'!'))) {
*x='\0';
fmtstr=HeapAlloc(GetProcessHeap(),0,lstrlenA(f)+2);
wsprintfA(fmtstr,"%%%s",f);
f=x+1;
} else {
len = lstrlenA(f);
fmtstr=HeapAlloc(GetProcessHeap(),0,len + 1);
wsprintfA(fmtstr,"%%%s",f);
f+=lstrlenA(f); /*at \0*/
}
} else
if(!Arguments)
break;
else {
fmtstr = HeapAlloc( GetProcessHeap(),0, 3 );
fmtstr[0] = '%';
fmtstr[1] = 's';
fmtstr[2] = 0;
}
if (Arguments) {
if (dwFlags & FORMAT_MESSAGE_ARGUMENT_ARRAY)
argliststart=Arguments+insertnr-1;
else
argliststart=(*(DWORD**)Arguments)+insertnr-1;
if (fmtstr[lstrlenA(fmtstr)-1]=='s')
sprintfbuf=HeapAlloc(GetProcessHeap(),0,lstrlenA((LPSTR)argliststart[0])+1);
else
sprintfbuf=HeapAlloc(GetProcessHeap(),0,100);
/* CMF - This makes a BIG assumption about va_list */
wvsprintfA(sprintfbuf, fmtstr, (va_list) argliststart);
x=sprintfbuf;
while (*x) {
ADD_TO_T(*x++);
}
HeapFree(GetProcessHeap(),0,sprintfbuf);
} else {
/* NULL Arguments - copy formatstr
* (probably wrong)
*/
while ((lastf<f)&&(*lastf)) {
ADD_TO_T(*lastf++);
}
}
HeapFree(GetProcessHeap(),0,fmtstr);
break;
case 'n':
/* FIXME: perhaps add \r too? */
ADD_TO_T('\n');
f++;
break;
case '0':
nolinefeed=1;
f++;
break;
default:ADD_TO_T(*f++)
break;
}
} else {
ADD_TO_T(*f++)
}
}
*t='\0';
}
if (!nolinefeed) {
/* add linefeed */
if(t==target || t[-1]!='\n')
ADD_TO_T('\n'); /* FIXME: perhaps add \r too? */
}
talloced = lstrlenA(target)+1;
if (nSize && talloced<nSize) {
target = (char*)HeapReAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,target,nSize);
}
// //TRACE(resource,"-- %s\n",debugstr_a(target));
if (dwFlags & FORMAT_MESSAGE_ALLOCATE_BUFFER) {
/* nSize is the MINIMUM size */
*((LPVOID*)lpBuffer) = (LPVOID)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,talloced);
CopyMemory(*(LPSTR*)lpBuffer,target,talloced);
} else
strncpy(lpBuffer,target,nSize);
HeapFree(GetProcessHeap(),0,target);
if (from) HeapFree(GetProcessHeap(),0,from);
return (dwFlags & FORMAT_MESSAGE_ALLOCATE_BUFFER) ?
lstrlenA(*(LPSTR*)lpBuffer):
lstrlenA(lpBuffer);
}
#undef ADD_TO_T
DWORD STDCALL FormatMessageW(
DWORD dwFlags,
LPCVOID lpSource,
DWORD dwMessageId,
DWORD dwLanguageId,
LPWSTR lpBuffer,
DWORD nSize,
va_list *Arguments
) {
LPWSTR target,t;
DWORD talloced;
LPWSTR from,f;
//DWORD width = dwFlags & FORMAT_MESSAGE_MAX_WIDTH_MASK;
DWORD nolinefeed = 0;
DWORD len;
////TRACE(resource, "(0x%lx,%p,%ld,0x%lx,%p,%ld,%p)\n",
// dwFlags,lpSource,dwMessageId,dwLanguageId,lpBuffer,nSize,Arguments);
//if (width)
// FIXME(resource,"line wrapping not supported.\n");
from = NULL;
if (dwFlags & FORMAT_MESSAGE_FROM_STRING) {
len = lstrlenW((LPWSTR)lpSource);
from = HeapAlloc( GetProcessHeap(),0, (len+1)*2 );
CopyMemory(from,lpSource,(len+1)*2);
}
else if (dwFlags & FORMAT_MESSAGE_FROM_SYSTEM) {
from = HeapAlloc( GetProcessHeap(),0,200 );
wsprintfW(from,L"Systemmessage, messageid = 0x%08lx\n",dwMessageId);
}
else if (dwFlags & FORMAT_MESSAGE_FROM_HMODULE) {
INT bufsize;
dwMessageId &= 0xFFFF;
bufsize=LoadMessageW((HMODULE)lpSource,dwMessageId,dwLanguageId,NULL,100);
if (bufsize) {
from = HeapAlloc( GetProcessHeap(), 0, (bufsize + 1)*sizeof(WCHAR) );
LoadMessageW((HMODULE)lpSource,dwMessageId,dwLanguageId,from,(bufsize + 1)*sizeof(WCHAR));
}
}
target = HeapAlloc( GetProcessHeap(), HEAP_ZERO_MEMORY, 100);
t = target;
talloced= 100;
#define ADD_TO_T(c) \
*t++=c;\
if (t-target == talloced) {\
target = (WCHAR *)HeapReAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,target,talloced*2);\
t = target+talloced;\
talloced*=2;\
}
if (from) {
f=from;
while (*f && !nolinefeed) {
if (*f=='%') {
int insertnr;
wchar_t *fmtstr,*sprintfbuf,*x,*lastf;
DWORD *argliststart;
fmtstr = NULL;
lastf = f;
f++;
if (!*f) {
ADD_TO_T('%');
continue;
}
switch (*f) {
case '1':case '2':case '3':case '4':case '5':
case '6':case '7':case '8':case '9':
insertnr=*f-'0';
switch (f[1]) {
case '0':case '1':case '2':case '3':
case '4':case '5':case '6':case '7':
case '8':case '9':
f++;
insertnr=insertnr*10+*f-'0';
f++;
break;
default:
f++;
break;
}
if (*f=='!') {
f++;
if (NULL!=(x=lstrchrW(f,'!'))) {
*x='\0';
len = lstrlenW(f);
fmtstr=HeapAlloc(GetProcessHeap(),0,(len+1)*2);
wsprintfW(fmtstr,L"%%%s",f);
f=x+1;
} else {
len = lstrlenW(f);
fmtstr=HeapAlloc(GetProcessHeap(),0,(len+1)*2);
wsprintfW(fmtstr,L"%%%s",f);
f+=len; /*at \0*/
}
} else
if(!Arguments)
break;
else {
fmtstr = HeapAlloc( GetProcessHeap(),0, 6 );
fmtstr[0] = '%';
fmtstr[1] = 's';
fmtstr[2] = 0;
}
if (Arguments) {
if (dwFlags & FORMAT_MESSAGE_ARGUMENT_ARRAY)
argliststart=Arguments+insertnr-1;
else
argliststart=(*(DWORD**)Arguments)+insertnr-1;
if (fmtstr[lstrlenW(fmtstr)-1]=='s')
sprintfbuf=HeapAlloc(GetProcessHeap(),0,lstrlenW((LPWSTR)argliststart[0])+1);
else
sprintfbuf=HeapAlloc(GetProcessHeap(),0,100);
/* CMF - This makes a BIG assumption about va_list */
wvsprintfW(sprintfbuf, fmtstr, (va_list) argliststart);
x=sprintfbuf;
while (*x) {
ADD_TO_T(*x++);
}
HeapFree(GetProcessHeap(),0,sprintfbuf);
} else {
/* NULL Arguments - copy formatstr
* (probably wrong)
*/
while ((lastf<f)&&(*lastf)) {
ADD_TO_T(*lastf++);
}
}
HeapFree(GetProcessHeap(),0,fmtstr);
break;
case 'n':
/* FIXME: perhaps add \r too? */
ADD_TO_T('\n');
f++;
break;
case '0':
nolinefeed=1;
f++;
break;
default:ADD_TO_T(*f++)
break;
}
} else {
ADD_TO_T(*f++)
}
}
*t='\0';
}
if (!nolinefeed) {
/* add linefeed */
if(t==target || t[-1]!='\n')
ADD_TO_T('\n'); /* FIXME: perhaps add \r too? */
}
talloced = (lstrlenW(target)+1)*sizeof(WCHAR);
if (nSize && talloced<nSize) {
target = (LPWSTR)HeapReAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,target,nSize);
}
////TRACE(resource,"-- %s\n",debugstr_a(target));
if (dwFlags & FORMAT_MESSAGE_ALLOCATE_BUFFER) {
/* nSize is the MINIMUM size */
*((LPVOID*)lpBuffer) = (LPVOID)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,talloced);
CopyMemory(*(LPSTR*)lpBuffer,target,talloced);
} else
wcsncpy(lpBuffer,target,nSize);
HeapFree(GetProcessHeap(),0,target);
if (from) HeapFree(GetProcessHeap(),0,from);
return (dwFlags & FORMAT_MESSAGE_ALLOCATE_BUFFER) ?
lstrlenW(*(LPWSTR*)lpBuffer):
lstrlenW(lpBuffer);
}
#undef ADD_TO_T
DWORD LoadMessageA(HMODULE hModule,DWORD dwMessageId,DWORD dwLanguageId,LPSTR Buffer,UINT BufSize)
{
return 0;
}
DWORD LoadMessageW(HMODULE hModule,DWORD dwMessageId,DWORD dwLanguageId,LPWSTR Buffer,UINT BufSize)
{
return 0;
}
LPSTR lstrchrA(LPCSTR s, INT c)
{
char cc = c;
while (*s)
{
if (*s == cc)
return (char *)s;
s++;
}
if (cc == 0)
return (char *)s;
return 0;
}
LPWSTR lstrchrW(LPCWSTR s, int c)
{
WCHAR cc = c;
while (*s)
{
if (*s == cc)
return (LPWSTR)s;
s++;
}
if (cc == 0)
return (LPWSTR)s;
return 0;
}
#if 0
VOID STDCALL OutputDebugStringA(LPCSTR lpOutputString)
{
WCHAR DebugStringW[161];
int i,j;
i = 0;
j = 0;
while ( lpOutputString[i] != 0 )
{
while ( j < 160 && lpOutputString[i] != 0 )
{
DebugStringW[j] = (WCHAR)lpOutputString[i];
i++;
j++;
}
DebugStringW[j] = 0;
OutputDebugStringW(DebugStringW);
j = 0;
}
return;
}
VOID
STDCALL
OutputDebugStringW(
LPCWSTR lpOutputString
)
{
UNICODE_STRING UnicodeOutput;
UnicodeOutput.Buffer = (WCHAR *)lpOutputString;
UnicodeOutput.Length = lstrlenW(lpOutputString)*sizeof(WCHAR);
UnicodeOutput.MaximumLength = UnicodeOutput.Length;
NtDisplayString(&UnicodeOutput);
}
#endif

View File

@@ -0,0 +1,274 @@
/*
* System metrics functions
*
* Copyright 1994 Alexandre Julliard
*
*/
#include <stdio.h>
#include <windows.h>
#include <user32/sysmetr.h>
#undef SM_CMETRICS
#define SM_CMETRICS (83)
short sysMetrics[SM_CMETRICS+1] = {
800, // [SM_CXSCREEN] /* 0 */
600, // [SM_CYSCREEN] /* 1 */
19, // [SM_CXVSCROLL] /* 2 */
17, // [SM_CYHSCROLL] /* 3 */
19, // [SM_CYCAPTION] /* 4 */
1, // [SM_CXBORDER] /* 5 */
1, // [SM_CYBORDER] /* 6 */
3, // [SM_CXDLGFRAME] /* 7 */
3, // [SM_CYDLGFRAME] /* 8 */
17, // [SM_CYVTHUMB] /* 9 */ sysMetrics[SM_CXVSCROLL] - 1;
17, // [SM_CXHTHUMB] /* 10 */ sysMetrics[SM_CXVSCROLL] - 1;
32, // [SM_CXICON] /* 11 */
32, // [SM_CYICON] /* 12 */
32, // [SM_CXCURSOR] /* 13 */
32, // [SM_CYCURSOR] /* 14 */
19, // [SM_CYMENU] /* 15 */
800, // [SM_CXFULLSCREEN] /* 16 */
0, // [SM_CYFULLSCREEN] /* 17 */
0, // [SM_CYKANJIWINDOW] /* 18 */
0, // [SM_MOUSEPRESENT] /* 19 */
0, // [SM_CYVSCROLL] /* 20 */
0, // [SM_CXHSCROLL] /* 21 */
0, // [SM_DEBUG] /* 22 */
0, // [SM_SWAPBUTTON] /* 23 */
0, // [SM_RESERVED1] /* 24 */
0, // [SM_RESERVED2] /* 25 */
0, // [SM_RESERVED3] /* 26 */
0, // [SM_RESERVED4] /* 27 */
0, // [SM_CXMIN] /* 28 */
0, // [SM_CYMIN] /* 29 */
0, // [SM_CXSIZE] /* 30 */
0, // [SM_CYSIZE] /* 31 */
0, // [SM_CXFRAME] /* 32 */
0, // [SM_CYFRAME] /* 33 */
0, // [SM_CXMINTRACK] /* 34 */
0, // [SM_CYMINTRACK] /* 35 */
0, // [SM_CXDOUBLECLK] /* 36 */
0, // [SM_CYDOUBLECLK] /* 37 */
0, // [SM_CXICONSPACING] /* 38 */
0, // [SM_CYICONSPACING] /* 39 */
0, // [SM_MENUDROPALIGNMENT] /* 40 */
0, // [SM_PENWINDOWS] /* 41 */
0, // [SM_DBCSENABLED] /* 42 */
0, // [SM_CMOUSEBUTTONS] /* 43 */
// [SM_CXDLGFRAME] /* win40 name change */
// [SM_CYDLGFRAME] /* win40 name change */
// [SM_CXFRAME] /* win40 name change */
// [SM_CYFRAME] /* win40 name change */
0, // [SM_SECURE] /* 44 */
0, // [SM_CXEDGE] /* 45 */
0, // [SM_CYEDGE] /* 46 */
0, // [SM_CXMINSPACING] /* 47 */
0, // [SM_CYMINSPACING] /* 48 */
0, // [SM_CXSMICON] /* 49 */
0, // [SM_CYSMICON] /* 50 */
0, // [SM_CYSMCAPTION] /* 51 */
0, // [SM_CXSMSIZE] /* 52 */
0, // [SM_CYSMSIZE] /* 53 */
0, // [SM_CXMENUSIZE] /* 54 */
0, // [SM_CYMENUSIZE] /* 55 */
8, // [SM_ARRANGE] /* 56 */
160, // [SM_CXMINIMIZED] /* 57 */
24, // [SM_CYMINIMIZED] /* 58 */
0, // [SM_CXMAXTRACK] /* 59 */
0, // [SM_CYMAXTRACK] /* 60 */
0, // [SM_CXMAXIMIZED] /* 61 */
0, // [SM_CYMAXIMIZED] /* 62 */
3, // [SM_NETWORK] /* 63 */
0, // [SM_CLEANBOOT] /* 67 */
2, // [SM_CXDRAG] /* 68 */
2, // [SM_CYDRAG] /* 69 */
0, // [SM_SHOWSOUNDS] /* 70 */
2, // [SM_CXMENUCHECK] /* 71 */
2, // [SM_CYMENUCHECK] /* 72 */
0, // [SM_SLOWMACHINE] /* 73 */
0, // [SM_MIDEASTENABLED] /* 74 */
0, // [SM_MOUSEWHEELPRESENT] /* 75 */
800, // [SM_CXVIRTUALSCREEN] /* 76 */
600, // [SM_CYVIRTUALSCREEN] /* 77 */
0, // [SM_YVIRTUALSCREEN] /* 78 */
0, // [SM_XVIRTUALSCREEN] /* 79 */
1, // [SM_CMONITORS] /* 81 */
1 // [SM_SAMEDISPLAYFORMAT] /* 82 */
};
int STDCALL GetSystemMetrics(int nIndex)
{
if ( nIndex >= 0 && nIndex <= SM_CMETRICS+1 )
return sysMetrics[nIndex];
return 0;
}
WINBOOL STDCALL SystemParametersInfo(UINT uiAction,
UINT uiParam, PVOID pvParam, UINT fWinIni )
{
return FALSE;
}
#if 0
/***********************************************************************
* SYSMETRICS_Init
*
* Initialisation of the system metrics array.
*
* Differences in return values between 3.1 and 95 apps under Win95 (FIXME ?):
* SM_CXVSCROLL x+1 x
* SM_CYHSCROLL x+1 x
* SM_CXDLGFRAME x-1 x
* SM_CYDLGFRAME x-1 x
* SM_CYCAPTION x+1 x
* SM_CYMENU x-1 x
* SM_CYFULLSCREEN x-1 x
*
* (collides with TWEAK_WineLook sometimes,
* so changing anything might be difficult)
*/
void SYSMETRICS_Init(void)
{
sysMetrics[SM_CXCURSOR] = 32;
sysMetrics[SM_CYCURSOR] = 32;
sysMetrics[SM_CXSCREEN] = screenWidth;
sysMetrics[SM_CYSCREEN] = screenHeight;
sysMetrics[SM_CXVSCROLL] =
PROFILE_GetWineIniInt("Tweak.Layout", "ScrollBarWidth", 16) + 1;
sysMetrics[SM_CYHSCROLL] = sysMetrics[SM_CXVSCROLL];
if (TWEAK_WineLook > WIN31_LOOK)
sysMetrics[SM_CYCAPTION] =
PROFILE_GetWineIniInt("Tweak.Layout", "CaptionHeight", 19);
else
sysMetrics[SM_CYCAPTION] = 2 +
PROFILE_GetWineIniInt("Tweak.Layout", "CaptionHeight", 18);
sysMetrics[SM_CXBORDER] = 1;
sysMetrics[SM_CYBORDER] = sysMetrics[SM_CXBORDER];
sysMetrics[SM_CXDLGFRAME] =
PROFILE_GetWineIniInt("Tweak.Layout", "DialogFrameWidth",
(TWEAK_WineLook > WIN31_LOOK) ? 3 : 4);
sysMetrics[SM_CYDLGFRAME] = sysMetrics[SM_CXDLGFRAME];
*/ sysMetrics[SM_CYVTHUMB] = sysMetrics[SM_CXVSCROLL] - 1;
*/ sysMetrics[SM_CXHTHUMB] = sysMetrics[SM_CYVTHUMB];
*/ sysMetrics[SM_CXICON] = 32;
*/ sysMetrics[SM_CYICON] = 32;
if (TWEAK_WineLook > WIN31_LOOK)
sysMetrics[SM_CYMENU] =
PROFILE_GetWineIniInt("Tweak.Layout", "MenuHeight", 19);
else
sysMetrics[SM_CYMENU] =
PROFILE_GetWineIniInt("Tweak.Layout", "MenuHeight", 18);
sysMetrics[SM_CXFULLSCREEN] = sysMetrics[SM_CXSCREEN];
sysMetrics[SM_CYFULLSCREEN] =
sysMetrics[SM_CYSCREEN] - sysMetrics[SM_CYCAPTION];
sysMetrics[SM_CYKANJIWINDOW] = 0;
sysMetrics[SM_MOUSEPRESENT] = 1;
sysMetrics[SM_CYVSCROLL] = sysMetrics[SM_CYVTHUMB];
sysMetrics[SM_CXHSCROLL] = sysMetrics[SM_CXHTHUMB];
sysMetrics[SM_DEBUG] = 0;
/* FIXME: The following should look for the registry key to see if the
buttons should be swapped. */
sysMetrics[SM_SWAPBUTTON] = 0;
sysMetrics[SM_RESERVED1] = 0;
sysMetrics[SM_RESERVED2] = 0;
sysMetrics[SM_RESERVED3] = 0;
sysMetrics[SM_RESERVED4] = 0;
/* FIXME: The following two are calculated, but how? */
sysMetrics[SM_CXMIN] = (TWEAK_WineLook > WIN31_LOOK) ? 112 : 100;
sysMetrics[SM_CYMIN] = (TWEAK_WineLook > WIN31_LOOK) ? 27 : 28;
sysMetrics[SM_CXSIZE] = sysMetrics[SM_CYCAPTION] - 2;
sysMetrics[SM_CYSIZE] = sysMetrics[SM_CXSIZE];
sysMetrics[SM_CXFRAME] = GetProfileInt32A("Windows", "BorderWidth", 4);
sysMetrics[SM_CYFRAME] = sysMetrics[SM_CXFRAME];
sysMetrics[SM_CXMINTRACK] = sysMetrics[SM_CXMIN];
sysMetrics[SM_CYMINTRACK] = sysMetrics[SM_CYMIN];
sysMetrics[SM_CXDOUBLECLK] =
(GetProfileInt32A("Windows", "DoubleClickWidth", 4) + 1) & ~1;
sysMetrics[SM_CYDOUBLECLK] =
(GetProfileInt32A("Windows","DoubleClickHeight", 4) + 1) & ~1;
sysMetrics[SM_CXICONSPACING] =
GetProfileInt32A("Desktop","IconSpacing", 75);
sysMetrics[SM_CYICONSPACING] =
GetProfileInt32A("Desktop", "IconVerticalSpacing", 75);
sysMetrics[SM_MENUDROPALIGNMENT] =
GetProfileInt32A("Windows", "MenuDropAlignment", 0);
sysMetrics[SM_PENWINDOWS] = 0;
sysMetrics[SM_DBCSENABLED] = 0;
/* FIXME: Need to query X for the following */
sysMetrics[SM_CMOUSEBUTTONS] = 3;
sysMetrics[SM_SECURE] = 0;
sysMetrics[SM_CXEDGE] = sysMetrics[SM_CXBORDER] + 1;
sysMetrics[SM_CYEDGE] = sysMetrics[SM_CXEDGE];
sysMetrics[SM_CXMINSPACING] = 160;
sysMetrics[SM_CYMINSPACING] = 24;
sysMetrics[SM_CXSMICON] =
sysMetrics[SM_CYSIZE] - (sysMetrics[SM_CYSIZE] % 2) - 2;
sysMetrics[SM_CYSMICON] = sysMetrics[SM_CXSMICON];
sysMetrics[SM_CYSMCAPTION] = 16;
sysMetrics[SM_CXSMSIZE] = 15;
sysMetrics[SM_CYSMSIZE] = sysMetrics[SM_CXSMSIZE];
sysMetrics[SM_CXMENUSIZE] = sysMetrics[SM_CYMENU];
sysMetrics[SM_CYMENUSIZE] = sysMetrics[SM_CXMENUSIZE];
/* FIXME: What do these mean? */
sysMetrics[SM_ARRANGE] = 8;
sysMetrics[SM_CXMINIMIZED] = 160;
sysMetrics[SM_CYMINIMIZED] = 24;
/* FIXME: How do I calculate these? */
sysMetrics[SM_CXMAXTRACK] =
sysMetrics[SM_CXSCREEN] + 4 + 2 * sysMetrics[SM_CXFRAME];
sysMetrics[SM_CYMAXTRACK] =
sysMetrics[SM_CYSCREEN] + 4 + 2 * sysMetrics[SM_CYFRAME];
sysMetrics[SM_CXMAXIMIZED] =
sysMetrics[SM_CXSCREEN] + 2 * sysMetrics[SM_CXFRAME];
sysMetrics[SM_CYMAXIMIZED] =
sysMetrics[SM_CYSCREEN] - 45;
sysMetrics[SM_NETWORK] = 3;
/* For the following: 0 = ok, 1 = failsafe, 2 = failsafe + network */
sysMetrics[SM_CLEANBOOT] = 0;
sysMetrics[SM_CXDRAG] = 2;
sysMetrics[SM_CYDRAG] = 2;
sysMetrics[SM_SHOWSOUNDS] = 0;
sysMetrics[SM_CXMENUCHECK] = 2;
sysMetrics[SM_CYMENUCHECK] = 2;
/* FIXME: Should check the type of processor for the following */
sysMetrics[SM_SLOWMACHINE] = 0;
/* FIXME: Should perform a check */
sysMetrics[SM_MIDEASTENABLED] = 0;
sysMetrics[SM_MOUSEWHEELPRESENT] = 0;
sysMetrics[SM_CXVIRTUALSCREEN] = sysMetrics[SM_CXSCREEN];
sysMetrics[SM_CYVIRTUALSCREEN] = sysMetrics[SM_CYSCREEN];
sysMetrics[SM_XVIRTUALSCREEN] = 0;
sysMetrics[SM_YVIRTUALSCREEN] = 0;
sysMetrics[SM_CMONITORS] = 1;
sysMetrics[SM_SAMEDISPLAYFORMAT] = 1;
sysMetrics[SM_CMETRICS] = SM_CMETRICS;
}
#endif

View File

@@ -0,0 +1,26 @@
#include <windows.h>
int
STDCALL
ToAscii(
UINT uVirtKey,
UINT uScanCode,
PBYTE lpKeyState,
LPWORD lpChar,
UINT uFlags)
{
return ToAsciiEx(uVirtKey,uScanCode, lpKeyState, lpChar, uFlags, NULL);
}
int
STDCALL
ToAsciiEx(
UINT uVirtKey,
UINT uScanCode,
PBYTE lpKeyState,
LPWORD lpChar,
UINT uFlags,
HKL dwhkl)
{
}

View File

@@ -0,0 +1,13 @@
#include <windows.h>
/***********************************************************************
* SYSRES_GetResourcePtr
*
* Return a pointer to a system resource.
*/
LPCVOID SYSRES_GetResPtr( int id )
{
// return SYSRES_Resources[Options.language][id]->data;
return NULL;
}

View File

@@ -0,0 +1,467 @@
#include <windows.h>
#include <user32/class.h>
#include <user32/win.h>
#include <user32/heapdup.h>
CLASS *rootClass;
ATOM STDCALL RegisterClassA(const WNDCLASS* wc)
{
WNDCLASSEX wcex;
wcex.cbSize = sizeof(WNDCLASSEX);
wcex.style = wc->style;
wcex.lpfnWndProc = wc->lpfnWndProc;
wcex.cbClsExtra = wc->cbClsExtra;
wcex.cbWndExtra = wc->cbWndExtra;
wcex.hInstance = wc->hInstance;
wcex.hIcon = wc->hIcon;
wcex.hCursor = wc->hCursor;
wcex.hbrBackground = wc->hbrBackground;
wcex.lpszMenuName = wc->lpszMenuName;
wcex.lpszClassName = wc->lpszClassName;
wcex.hIconSm = NULL;
return RegisterClassExA(&wcex);
}
ATOM STDCALL RegisterClassW(const WNDCLASS* wc)
{
WNDCLASSEX wcex;
wcex.cbSize = sizeof(WNDCLASSEX);
wcex.style = wc->style;
wcex.lpfnWndProc = wc->lpfnWndProc;
wcex.cbClsExtra = wc->cbClsExtra;
wcex.cbWndExtra = wc->cbWndExtra;
wcex.hInstance = wc->hInstance;
wcex.hIcon = wc->hIcon;
wcex.hCursor = wc->hCursor;
wcex.hbrBackground = wc->hbrBackground;
wcex.lpszMenuName = wc->lpszMenuName;
wcex.lpszClassName = wc->lpszClassName;
wcex.hIconSm = NULL;
return RegisterClassExW(&wcex);
}
ATOM STDCALL RegisterClassExA(const WNDCLASSEX* wc)
{
ATOM atom;
CLASS *classPtr;
INT classExtra, winExtra;
int len;
if ( wc == NULL || wc->cbSize != sizeof(WNDCLASSEX)) {
SetLastError(ERROR_INVALID_DATA);
return FALSE;
}
atom = GlobalAddAtomA( wc->lpszClassName );
if (!atom)
{
SetLastError(ERROR_CLASS_ALREADY_EXISTS);
return FALSE;
}
classExtra = wc->cbClsExtra;
if (classExtra < 0)
classExtra = 0;
else if (classExtra > 40)
classExtra = 40;
winExtra = wc->cbClsExtra;
if (winExtra < 0)
winExtra = 0;
else if (winExtra > 40)
winExtra = 40;
classPtr = (CLASS *)HeapAlloc( GetProcessHeap(), 0, sizeof(CLASS) +
classExtra - sizeof(classPtr->wExtra) );
if (classExtra)
memset( classPtr->wExtra, 0, classExtra );
if (!classPtr) {
SetLastError(ERROR_NOT_ENOUGH_MEMORY);
GlobalDeleteAtom( atom );
return FALSE;
}
classPtr->magic = CLASS_MAGIC;
classPtr->cWindows = 0;
classPtr->style = wc->style;
classPtr->winproc = wc->lpfnWndProc;
classPtr->cbWndExtra = winExtra;
classPtr->cbClsExtra = classExtra;
classPtr->hInstance = wc->hInstance;
classPtr->atomName = atom;
classPtr->hIcon = (HICON)wc->hIcon;
classPtr->hIconSm = (HICON)wc->hIconSm;
classPtr->hCursor = (HCURSOR)wc->hCursor;
classPtr->hbrBackground = (HBRUSH)wc->hbrBackground;
classPtr->bUnicode = FALSE;
classPtr->dce = (wc->style & CS_CLASSDC) ?
CreateDC( "DISPLAY", NULL,NULL,NULL ) : NULL;
if ( wc->lpszMenuName != NULL ) {
len = lstrlenA(wc->lpszMenuName);
classPtr->menuName = HeapAlloc(GetProcessHeap(),0,len+1);
lstrcpyA(classPtr->menuName,wc->lpszMenuName);
}
else
classPtr->menuName = NULL;
len = lstrlenA(wc->lpszClassName);
classPtr->className = HeapAlloc(GetProcessHeap(),0,len+1);
lstrcpyA(classPtr->className,wc->lpszClassName);
classPtr->next = rootClass;
rootClass = classPtr;
return atom;
}
ATOM STDCALL RegisterClassExW( const WNDCLASSEX* wc )
{
ATOM atom;
CLASS *classPtr;
INT classExtra, winExtra;
int i, len;
if ( wc == NULL || wc->cbSize != sizeof(WNDCLASSEX)) {
SetLastError(ERROR_INVALID_DATA);
return FALSE;
}
if (!(atom = GlobalAddAtomW( (LPWSTR)wc->lpszClassName )))
{
SetLastError(ERROR_CLASS_ALREADY_EXISTS);
return FALSE;
}
classExtra = wc->cbClsExtra;
if (classExtra < 0)
classExtra = 0;
else if (classExtra > 40)
classExtra = 40;
winExtra = wc->cbClsExtra;
if (winExtra < 0)
winExtra = 0;
else if (winExtra > 40)
winExtra = 40;
classPtr = (CLASS *)HeapAlloc( GetProcessHeap(), 0, sizeof(CLASS) +
classExtra - sizeof(classPtr->wExtra) );
if (classExtra)
memset( classPtr->wExtra, 0, classExtra );
if (!classPtr) {
SetLastError(ERROR_NOT_ENOUGH_MEMORY);
GlobalDeleteAtom( atom );
return FALSE;
}
classPtr->magic = CLASS_MAGIC;
classPtr->cWindows = 0;
classPtr->style = wc->style;
classPtr->winproc = wc->lpfnWndProc;
classPtr->cbWndExtra = winExtra;
classPtr->cbClsExtra = classExtra;
classPtr->hInstance = wc->hInstance;
classPtr->atomName = atom;
classPtr->hIcon = (HICON)wc->hIcon;
classPtr->hIconSm = (HICON)wc->hIconSm;
classPtr->hCursor = (HCURSOR)wc->hCursor;
classPtr->hbrBackground = (HBRUSH)wc->hbrBackground;
classPtr->bUnicode = FALSE;
classPtr->dce = (wc->style & CS_CLASSDC) ?
CreateDC( "DISPLAY", NULL,NULL,NULL ) : NULL;
len = lstrlenW((LPWSTR)wc->lpszMenuName);
classPtr->menuName = HeapAlloc(GetProcessHeap(),0,(len+1)*2);
lstrcpyW((LPWSTR)classPtr->menuName, (LPWSTR)wc->lpszMenuName);
len = lstrlenW((LPWSTR)wc->lpszClassName);
classPtr->className = HeapAlloc(GetProcessHeap(),0,(len+1)*2);
lstrcpyW((LPWSTR)classPtr->className,(LPWSTR) wc->lpszClassName );
classPtr->next = rootClass;
rootClass = classPtr;
return atom;
}
WINBOOL UnregisterClassA(LPCSTR lpClassName, HINSTANCE hInstance )
{
CLASS *classPtr;
classPtr = CLASS_FindClassByAtom( STRING2ATOMA(lpClassName), hInstance );
if ( classPtr == NULL )
return FALSE;
if ( CLASS_FreeClass(classPtr) == TRUE )
GlobalDeleteAtom( classPtr->atomName );
return TRUE;
}
WINBOOL UnregisterClassW(LPCWSTR lpClassName, HINSTANCE hInstance )
{
CLASS *classPtr;
classPtr = CLASS_FindClassByAtom( STRING2ATOMW(lpClassName), hInstance );
if ( classPtr == NULL )
return FALSE;
if ( CLASS_FreeClass(classPtr) == TRUE )
GlobalDeleteAtom( classPtr->atomName );
return TRUE;
}
WINBOOL GetClassInfoA( HINSTANCE hInstance, LPCSTR lpClassName, LPWNDCLASS lpWndClass )
{
return FALSE;
}
WINBOOL GetClassInfoW( HINSTANCE hInstance, LPCWSTR lpClassName, LPWNDCLASS lpWndClass )
{
CLASS *classPtr;
ATOM a;
if ( HIWORD(lpClassName) != 0 )
a = FindAtomW(lpClassName);
else
a = lpClassName;
classPtr = CLASS_FindClassByAtom( a, hInstance );
if ( classPtr == NULL )
return FALSE;
lpWndClass->style = classPtr->style;
lpWndClass->lpfnWndProc = classPtr->winproc;
lpWndClass->cbClsExtra = classPtr->cbWndExtra;
lpWndClass->cbClsExtra = classPtr->cbClsExtra;
lpWndClass->hInstance = classPtr->hInstance;
lpWndClass->hIcon = classPtr->hIcon;
lpWndClass->hCursor = classPtr->hCursor;
lpWndClass->hbrBackground = classPtr->hbrBackground;
return TRUE;
}
WINBOOL GetClassInfoExA( HINSTANCE hInstance, LPCSTR lpClassName, LPWNDCLASSEX lpWndClass )
{
return FALSE;
}
WINBOOL GetClassInfoExW( HINSTANCE hInstance, LPCWSTR lpClassName, LPWNDCLASSEX lpWndClassEx )
{
CLASS *classPtr;
ATOM a;
if ( HIWORD(lpClassName) != 0 )
a = FindAtomW(lpClassName);
else
a = lpClassName;
classPtr = CLASS_FindClassByAtom( a, hInstance );
if ( classPtr == NULL )
return FALSE;
if ( lpWndClassEx ->cbSize != sizeof(WNDCLASSEX) )
return FALSE;
lpWndClassEx->style = classPtr->style;
lpWndClassEx->lpfnWndProc = classPtr->winproc;
lpWndClassEx->cbClsExtra = classPtr->cbWndExtra;
lpWndClassEx->cbClsExtra = classPtr->cbClsExtra;
lpWndClassEx->hInstance = classPtr->hInstance;
lpWndClassEx->hIcon = classPtr->hIcon;
lpWndClassEx->hCursor = classPtr->hCursor;
lpWndClassEx->hbrBackground = classPtr->hbrBackground;
return TRUE;
}
int GetClassNameA(HWND hWnd, LPSTR lpClassName, int nMaxCount )
{
WND *wndPtr = WIN_FindWndPtr(hWnd);
if ( wndPtr == NULL )
return 0;
if ( wndPtr->class->bUnicode == TRUE )
return 0;
return lpstrncpyA(lpClassName,wndPtr->class->className, nMaxCount);
}
int GetClassNameW(HWND hWnd, LPWSTR lpClassName, int nMaxCount )
{
WND *wndPtr = WIN_FindWndPtr(hWnd);
if ( wndPtr == NULL )
return 0;
if ( wndPtr->class->bUnicode == FALSE )
return 0;
return lpstrncpyW(lpClassName,wndPtr->class->className, nMaxCount);
}
DWORD GetClassLongA(HWND hWnd, int nIndex )
{
WND * wndPtr;
if (!(wndPtr = WIN_FindWndPtr( hWnd ))) return 0;
if (nIndex >= 0)
{
if (nIndex <= wndPtr->class->cbClsExtra - sizeof(LONG))
return (DWORD)((char *)wndPtr->class->wExtra) + nIndex;
}
switch(nIndex)
{
case GCL_STYLE: return (LONG)wndPtr->class->style;
case GCL_CBWNDEXTRA: return (LONG)wndPtr->class->cbWndExtra;
case GCL_CBCLSEXTRA: return (LONG)wndPtr->class->cbClsExtra;
case GCL_HMODULE: return (LONG)wndPtr->class->hInstance;
case GCL_WNDPROC: return (LONG)wndPtr->class->winproc;
case GCL_MENUNAME: return (LONG)wndPtr->class->menuName;
case GCW_ATOM:
case GCL_HBRBACKGROUND:
case GCL_HCURSOR:
case GCL_HICON:
case GCL_HICONSM:
return GetClassWord( hWnd, nIndex );
default:
return -1;
}
return 0;
}
DWORD GetClassLongW(HWND hWnd, int nIndex )
{
WND * wndPtr;
if (!(wndPtr = WIN_FindWndPtr( hWnd ))) return 0;
if (nIndex >= 0)
{
if (nIndex <= wndPtr->class->cbClsExtra - sizeof(LONG))
return (DWORD)((char *)wndPtr->class->wExtra) + nIndex;
}
switch(nIndex)
{
case GCL_STYLE: return (LONG)wndPtr->class->style;
case GCL_CBWNDEXTRA: return (LONG)wndPtr->class->cbWndExtra;
case GCL_CBCLSEXTRA: return (LONG)wndPtr->class->cbClsExtra;
case GCL_HMODULE: return (LONG)wndPtr->class->hInstance;
case GCL_WNDPROC: return (LONG)wndPtr->class->winproc;
case GCL_MENUNAME: return (LONG)wndPtr->class->menuName;
case GCW_ATOM:
case GCL_HBRBACKGROUND:
case GCL_HCURSOR:
case GCL_HICON:
case GCL_HICONSM:
return GetClassWord( hWnd, nIndex );
default:
return -1;
}
return 0;
}
WORD STDCALL GetClassWord( HWND hWnd, INT nIndex )
{
WND * wndPtr;
if (!(wndPtr = WIN_FindWndPtr( hWnd ))) return 0;
if (nIndex >= 0)
{
if (nIndex <= wndPtr->class->cbClsExtra - sizeof(WORD))
return (WORD)((char *)wndPtr->class->wExtra) + nIndex;
}
else switch(nIndex)
{
//case GCW_HBRBACKGROUND: return wndPtr->class->hbrBackground;
//case GCW_HCURSOR: return wndPtr->class->hCursor;
//case GCW_HICON: return wndPtr->class->hIcon;
// case GCW_HICONSM: return wndPtr->class->hIconSm;
case GCW_ATOM: return wndPtr->class->atomName;
//case GCW_STYLE:
//case GCW_CBWNDEXTRA:
//case GCW_CBCLSEXTRA:
//case GCW_HMODULE:
return (WORD)GetClassLongA( hWnd, nIndex );
default:
return -1;
}
return 0;
}
CLASS *CLASS_FindClassByAtom( ATOM classAtom, HINSTANCE hInstance )
{
CLASS *p = rootClass;
while(p != NULL ) {
if ( p->atomName == classAtom )
return p;
p = p->next;
}
return NULL;
}
WINBOOL CLASS_FreeClass(CLASS *classPtr)
{
CLASS *p = rootClass;
if( classPtr->cWindows > 0 )
return FALSE;
if (classPtr->dce)
DeleteDC( classPtr->dce );
if (classPtr->hbrBackground)
DeleteObject( classPtr->hbrBackground );
classPtr->atomName = 0;
HeapFree(GetProcessHeap(),0,classPtr->className);
while(p != NULL && p->next != classPtr )
p = p->next;
if ( p != NULL )
p->next = classPtr->next;
HeapFree(GetProcessHeap(),0,classPtr);
return TRUE;
}

View File

@@ -0,0 +1,505 @@
/*
* USER DCE functions
*
* Copyright 1993 Alexandre Julliard
* 1996,1997 Alex Korobka
*
*
* Note: Visible regions of CS_OWNDC/CS_CLASSDC window DCs
* have to be updated dynamically.
*
* Internal DCX flags:
*
* DCX_DCEEMPTY - dce is uninitialized
* DCX_DCEBUSY - dce is in use
* DCX_DCEDIRTY - ReleaseDC() should wipe instead of caching
* DCX_KEEPCLIPRGN - ReleaseDC() should not delete the clipping region
* DCX_WINDOWPAINT - BeginPaint() is in effect
*/
/* GetDCEx flags */
#define DCX_USESTYLE 0x00010000
#include <windows.h>
#include <user32/win.h>
#include <user32/dce.h>
#include <user32/sysmetr.h>
#include <user32/debug.h>
extern DCE *firstDCE;
INT SelectVisRgn(HDC hdc,HRGN hrgn);
INT ExcludeVisRect(HDC hDC,INT nLeftRect,INT nTopRect,INT nRightRect,INT nBottomRect);
INT RestoreVisRgn(HDC hdc);
HDC STDCALL GetDC( HWND hWnd )
{
if (!hWnd)
return GetDCEx( GetDesktopWindow(), 0, DCX_CACHE | DCX_WINDOW );
return GetDCEx( hWnd, 0, DCX_USESTYLE );
}
/***********************************************************************
* GetDCEx
*
* Unimplemented flags: DCX_LOCKWINDOWUPDATE
*
* FIXME: Full support for hrgnClip == 1 (alias for entire window).
*/
HDC WINAPI GetDCEx( HWND hwnd, HRGN hrgnClip, DWORD flags )
{
HRGN hrgnVisible = 0;
HDC hdc = 0;
DCE * dce;
//HDC dc;
WND * wndPtr;
DWORD dcxFlags = 0;
BOOL bUpdateVisRgn = TRUE;
BOOL bUpdateClipOrigin = FALSE;
DPRINT("hwnd %04x, hrgnClip %04x, flags %08x\n",
hwnd, hrgnClip, (unsigned)flags);
if (!(wndPtr = WIN_FindWndPtr( hwnd ))) return 0;
/* fixup flags */
if (!(wndPtr->class->style & (CS_OWNDC | CS_CLASSDC))) flags |= DCX_CACHE;
if (flags & DCX_USESTYLE)
{
flags &= ~( DCX_CLIPCHILDREN | DCX_CLIPSIBLINGS | DCX_PARENTCLIP);
if( wndPtr->dwStyle & WS_CLIPSIBLINGS )
flags |= DCX_CLIPSIBLINGS;
if ( !(flags & DCX_WINDOW) )
{
if (wndPtr->class->style & CS_PARENTDC) flags |= DCX_PARENTCLIP;
if (wndPtr->dwStyle & WS_CLIPCHILDREN &&
!(wndPtr->dwStyle & WS_MINIMIZE) ) flags |= DCX_CLIPCHILDREN;
}
else flags |= DCX_CACHE;
}
if( flags & DCX_NOCLIPCHILDREN )
{
flags |= DCX_CACHE;
flags &= ~(DCX_PARENTCLIP | DCX_CLIPCHILDREN);
}
if (flags & DCX_WINDOW)
flags = (flags & ~DCX_CLIPCHILDREN) | DCX_CACHE;
if (!(wndPtr->dwStyle & WS_CHILD) || !wndPtr->parent )
flags &= ~DCX_PARENTCLIP;
else if( flags & DCX_PARENTCLIP )
{
flags |= DCX_CACHE;
if( !(flags & (DCX_CLIPSIBLINGS | DCX_CLIPCHILDREN)) )
if( (wndPtr->dwStyle & WS_VISIBLE) && (wndPtr->parent->dwStyle & WS_VISIBLE) )
{
flags &= ~DCX_CLIPCHILDREN;
if( wndPtr->parent->dwStyle & WS_CLIPSIBLINGS )
flags |= DCX_CLIPSIBLINGS;
}
}
/* find a suitable DCE */
dcxFlags = flags & (DCX_PARENTCLIP | DCX_CLIPSIBLINGS | DCX_CLIPCHILDREN |
DCX_CACHE | DCX_WINDOW);
if (flags & DCX_CACHE)
{
DCE* dceEmpty;
DCE* dceUnused;
dceEmpty = dceUnused = NULL;
/* Strategy: First, we attempt to find a non-empty but unused DCE with
* compatible flags. Next, we look for an empty entry. If the cache is
* full we have to purge one of the unused entries.
*/
for (dce = firstDCE; (dce); dce = dce->next)
{
if ((dce->DCXflags & (DCX_CACHE | DCX_DCEBUSY)) == DCX_CACHE )
{
dceUnused = dce;
if (dce->DCXflags & DCX_DCEEMPTY)
dceEmpty = dce;
else
if ((dce->hwndCurrent == hwnd) &&
((dce->DCXflags & (DCX_CLIPSIBLINGS | DCX_CLIPCHILDREN |
DCX_CACHE | DCX_WINDOW | DCX_PARENTCLIP)) == dcxFlags))
{
DPRINT("\tfound valid %08x dce [%04x], flags %08x\n",
(unsigned)dce, hwnd, (unsigned)dcxFlags );
bUpdateVisRgn = FALSE;
bUpdateClipOrigin = TRUE;
break;
}
}
}
if (!dce) dce = (dceEmpty) ? dceEmpty : dceUnused;
}
else
{
dce = (wndPtr->class->style & CS_OWNDC) ? wndPtr->dce : wndPtr->class->dce;
if( dce->hwndCurrent == hwnd )
{
DPRINT("\tskipping hVisRgn update\n");
bUpdateVisRgn = FALSE; /* updated automatically, via DCHook() */
if( (dce->DCXflags & (DCX_EXCLUDERGN | DCX_INTERSECTRGN)) &&
(flags & (DCX_EXCLUDERGN | DCX_INTERSECTRGN)) )
{
/* This is likely to be a nested BeginPaint(). */
if( dce->hClipRgn != hrgnClip )
{
DPRINT("fixme new hrgnClip[%04x] smashes the previous[%04x]\n",
hrgnClip, dce->hClipRgn );
DCE_DeleteClipRgn( dce );
}
else
RestoreVisRgn(dce->hDC);
}
}
}
if (!dce) return 0;
dce->hwndCurrent = hwnd;
dce->hClipRgn = 0;
dce->DCXflags = dcxFlags | (flags & DCX_WINDOWPAINT) | DCX_DCEBUSY;
hdc = dce->hDC;
//if (!(dc = (DC *) GDI_GetObjPtr( hdc, DC_MAGIC ))) return 0;
//bUpdateVisRgn = bUpdateVisRgn || (dc->w.flags & DC_DIRTY);
/* recompute visible region */
//wndPtr->pDriver->pSetDrawable( wndPtr, dc, flags, bUpdateClipOrigin );
if( bUpdateVisRgn )
{
DPRINT("updating visrgn for %08x dce, hwnd [%04x]\n", (unsigned)dce, hwnd);
if (flags & DCX_PARENTCLIP)
{
WND *parentPtr = wndPtr->parent;
if( wndPtr->dwStyle & WS_VISIBLE && !(parentPtr->dwStyle & WS_MINIMIZE) )
{
if( parentPtr->dwStyle & WS_CLIPSIBLINGS )
dcxFlags = DCX_CLIPSIBLINGS | (flags & ~(DCX_CLIPCHILDREN | DCX_WINDOW));
else
dcxFlags = flags & ~(DCX_CLIPSIBLINGS | DCX_CLIPCHILDREN | DCX_WINDOW);
hrgnVisible = DCE_GetVisRgn( parentPtr->hwndSelf, dcxFlags );
if( flags & DCX_WINDOW )
OffsetRgn( hrgnVisible, -wndPtr->rectWindow.left,
-wndPtr->rectWindow.top );
else
OffsetRgn( hrgnVisible, -wndPtr->rectClient.left,
-wndPtr->rectClient.top );
DCE_OffsetVisRgn( hdc, hrgnVisible );
}
else
hrgnVisible = CreateRectRgn( 0, 0, 0, 0 );
}
else
if ((hwnd == GetDesktopWindow())) {
hrgnVisible = CreateRectRgn( 0, 0, SYSMETRICS_CXSCREEN,
SYSMETRICS_CYSCREEN );
// (rootWindow == DefaultRootWindow(display))
}
else
{
hrgnVisible = DCE_GetVisRgn( hwnd, flags );
DCE_OffsetVisRgn( hdc, hrgnVisible );
}
//dc->w.flags &= ~DC_DIRTY;
dce->DCXflags &= ~DCX_DCEDIRTY;
SelectVisRgn( hdc, hrgnVisible );
}
else
DPRINT("no visrgn update %08x dce, hwnd [%04x]\n", (unsigned)dce, hwnd);
/* apply additional region operation (if any) */
if( flags & (DCX_EXCLUDERGN | DCX_INTERSECTRGN) )
{
if( !hrgnVisible ) hrgnVisible = CreateRectRgn( 0, 0, 0, 0 );
dce->DCXflags |= flags & (DCX_KEEPCLIPRGN | DCX_INTERSECTRGN | DCX_EXCLUDERGN);
dce->hClipRgn = hrgnClip;
DPRINT( "\tsaved VisRgn, clipRgn = %04x\n", hrgnClip);
SaveVisRgn( hdc );
CombineRgn( hrgnVisible, hrgnClip, 0, RGN_COPY );
DCE_OffsetVisRgn( hdc, hrgnVisible );
CombineRgn( hrgnVisible, InquireVisRgn( hdc ), hrgnVisible,
(flags & DCX_INTERSECTRGN) ? RGN_AND : RGN_DIFF );
SelectVisRgn( hdc, hrgnVisible );
}
if( hrgnVisible ) DeleteObject( hrgnVisible );
DPRINT( "(%04x,%04x,0x%lx): returning %04x\n",
hwnd, hrgnClip, flags, hdc);
return hdc;
}
int STDCALL ReleaseDC(HWND hWnd,HDC hDC )
{
return 0;
}
HDC GetWindowDC(HWND hWnd )
{
if (!hWnd) hWnd = GetDesktopWindow();
return GetDCEx( hWnd, 0, DCX_USESTYLE | DCX_WINDOW );
}
/***********************************************************************
* BeginPaint (USER.10)
*/
HDC
STDCALL
BeginPaint(
HWND hWnd,
LPPAINTSTRUCT lpPaint)
{
WINBOOL bIcon;
HRGN hrgnUpdate;
WND *wndPtr = WIN_FindWndPtr( hWnd );
if (!wndPtr) return 0;
bIcon = (wndPtr->dwStyle & WS_MINIMIZE && wndPtr->class->hIcon);
wndPtr->flags &= ~WIN_NEEDS_BEGINPAINT;
if (wndPtr->flags & WIN_NEEDS_NCPAINT) WIN_UpdateNCArea( wndPtr, TRUE );
if (((hrgnUpdate = wndPtr->hrgnUpdate) != 0) ||
(wndPtr->flags & WIN_INTERNAL_PAINT))
QUEUE_DecPaintCount( wndPtr->hmemTaskQ );
wndPtr->hrgnUpdate = 0;
wndPtr->flags &= ~WIN_INTERNAL_PAINT;
HideCaret( hWnd );
DPRINT("hrgnUpdate = %04x, \n", hrgnUpdate);
/* When bIcon is TRUE hrgnUpdate is automatically in window coordinates
* (because rectClient == rectWindow for WS_MINIMIZE windows).
*/
if (wndPtr->class->style & CS_PARENTDC)
{
/* Don't clip the output to the update region for CS_PARENTDC window */
if(hrgnUpdate > 1)
DeleteObject(hrgnUpdate);
lpPaint->hdc = GetDCEx( hWnd, 0, DCX_WINDOWPAINT | DCX_USESTYLE |
(bIcon ? DCX_WINDOW : 0) );
}
else
{
lpPaint->hdc = GetDCEx(hWnd, hrgnUpdate, DCX_INTERSECTRGN |
DCX_WINDOWPAINT | DCX_USESTYLE |
(bIcon ? DCX_WINDOW : 0) );
}
DPRINT("hdc = %04x\n", lpPaint->hdc);
if (!lpPaint->hdc)
{
//WARN(win, "GetDCEx() failed in BeginPaint(), hWnd=%04x\n", hWnd);
return 0;
}
GetClipBox( lpPaint->hdc, &lpPaint->rcPaint );
DPRINT("box = (%i,%i - %i,%i)\n", lpPaint->rcPaint.left, lpPaint->rcPaint.top,
lpPaint->rcPaint.right, lpPaint->rcPaint.bottom );
if (wndPtr->flags & WIN_NEEDS_ERASEBKGND)
{
wndPtr->flags &= ~WIN_NEEDS_ERASEBKGND;
lpPaint->fErase = !SendMessageA(hWnd, (bIcon) ? WM_ICONERASEBKGND
: WM_ERASEBKGND,
(WPARAM)lpPaint->hdc, 0 );
}
else lpPaint->fErase = TRUE;
return lpPaint->hdc;
}
WINBOOL STDCALL EndPaint( HWND hWnd, const PAINTSTRUCT *lpPaint )
{
ReleaseDC( hWnd, lpPaint->hdc );
ShowCaret( hWnd );
return TRUE;
}
/***********************************************************************
* RedrawWindow (USER32.426)
*/
WINBOOL STDCALL RedrawWindow( HWND hwnd, const RECT *rectUpdate,
HRGN hrgnUpdate, UINT flags )
{
return PAINT_RedrawWindow( hwnd, rectUpdate, hrgnUpdate, flags, 0 );
}
/***********************************************************************
* UpdateWindow (USER32.567)
*/
WINBOOL
STDCALL
UpdateWindow(
HWND hWnd)
{
return PAINT_RedrawWindow( hWnd, NULL, 0, RDW_UPDATENOW | RDW_NOCHILDREN, 0 );
}
/***********************************************************************
* InvalidateRgn (USER32.9)
*/
WINBOOL
STDCALL
InvalidateRgn(
HWND hWnd,
HRGN hRgn,
WINBOOL bErase)
{
return PAINT_RedrawWindow(hWnd, NULL, hRgn, RDW_INVALIDATE | (bErase ? RDW_ERASE : 0), 0 );
}
/***********************************************************************
* InvalidateRect (USER32.8)
*/
WINBOOL
STDCALL
InvalidateRect(
HWND hWnd ,
CONST RECT *lpRect,
WINBOOL bErase)
{
return PAINT_RedrawWindow( hWnd, lpRect, 0,
RDW_INVALIDATE | (bErase ? RDW_ERASE : 0), 0 );
}
/***********************************************************************
* ValidateRgn (USER32.572)
*/
WINBOOL
STDCALL
ValidateRgn(
HWND hWnd,
HRGN hRgn)
{
return PAINT_RedrawWindow( hWnd, NULL, hRgn, RDW_VALIDATE | RDW_NOCHILDREN, 0 );
}
/***********************************************************************
* ValidateRect (USER32.571)
*/
WINBOOL
STDCALL
ValidateRect(
HWND hWnd ,
CONST RECT *lpRect)
{
return PAINT_RedrawWindow( hWnd, lpRect, 0, RDW_VALIDATE | RDW_NOCHILDREN, 0 );
}
/***********************************************************************
* GetUpdateRect (USER32.297)
*/
WINBOOL STDCALL GetUpdateRect( HWND hwnd, LPRECT rect, WINBOOL erase )
{
WND * wndPtr = WIN_FindWndPtr( hwnd );
if (!wndPtr) return FALSE;
if (rect)
{
if (wndPtr->hrgnUpdate > 1)
{
HRGN hrgn = CreateRectRgn( 0, 0, 0, 0 );
if (GetUpdateRgn( hwnd, hrgn, erase ) == ERROR) return FALSE;
GetRgnBox( hrgn, rect );
DeleteObject( hrgn );
}
else SetRectEmpty( rect );
}
return ((UINT)wndPtr->hrgnUpdate > 1);
}
/***********************************************************************
* GetUpdateRgn (USER32.298)
*/
INT STDCALL GetUpdateRgn( HWND hwnd, HRGN hrgn, WINBOOL erase )
{
INT retval;
WND * wndPtr = WIN_FindWndPtr( hwnd );
if (!wndPtr) return ERROR;
if ((UINT)wndPtr->hrgnUpdate <= 1)
{
SetRectRgn( hrgn, 0, 0, 0, 0 );
return NULLREGION;
}
retval = CombineRgn( hrgn, wndPtr->hrgnUpdate, 0, RGN_COPY );
if (erase) RedrawWindow( hwnd, NULL, 0, RDW_ERASENOW | RDW_NOCHILDREN );
return retval;
}
/***********************************************************************
* ExcludeUpdateRgn (USER32.195)
*/
INT STDCALL ExcludeUpdateRgn( HDC hdc, HWND hwnd )
{
RECT rect;
WND * wndPtr;
if (!(wndPtr = WIN_FindWndPtr( hwnd ))) return ERROR;
if (wndPtr->hrgnUpdate)
{
INT ret;
HRGN hrgn = CreateRectRgn(wndPtr->rectWindow.left - wndPtr->rectClient.left,
wndPtr->rectWindow.top - wndPtr->rectClient.top,
wndPtr->rectClient.right - wndPtr->rectClient.left,
wndPtr->rectClient.bottom - wndPtr->rectClient.top);
if( wndPtr->hrgnUpdate > 1 )
CombineRgn(hrgn, wndPtr->hrgnUpdate, 0, RGN_COPY);
/* do ugly coordinate translations in dce.c */
ret = DCE_ExcludeRgn( hdc, wndPtr, hrgn );
DeleteObject( hrgn );
return ret;
}
return GetClipBox( hdc, &rect );
}
WINBOOL PAINT_RedrawWindow( HWND hwnd, const RECT *rectUpdate,
HRGN hrgnUpdate, UINT flags, UINT control )
{
}

View File

@@ -0,0 +1,86 @@
#include <windows.h>
#include <user32/win.h>
HWND hwndFocus;
//FIXME this a shared api by all procedures
HWND STDCALL SetFocus( HWND hwnd )
{
HWND hWndPrevFocus, hwndTop = hwnd;
WND *wndPtr = WIN_FindWndPtr( hwnd );
if (wndPtr)
{
/* Check if we can set the focus to this window */
while ( (wndPtr->dwStyle & (WS_CHILD | WS_POPUP)) == WS_CHILD )
{
if ( wndPtr->dwStyle & ( WS_MINIMIZE | WS_DISABLED) )
return 0;
if (!(wndPtr = wndPtr->parent)) return 0;
hwndTop = wndPtr->hwndSelf;
}
if( hwnd == hwndFocus ) return hwnd;
/* call hooks */
if( HOOK_CallHooksA( WH_CBT, HCBT_SETFOCUS, (WPARAM)hwnd,
(LPARAM)hwndFocus) )
return 0;
/* activate hwndTop if needed. */
if (hwndTop != GetActiveWindow())
{
if (!WINPOS_SetActiveWindow(hwndTop, 0, 0)) return 0;
if (!IsWindow( hwnd )) return 0; /* Abort if window destroyed */
}
}
else if( HOOK_CallHooksA( WH_CBT, HCBT_SETFOCUS, 0, (LPARAM)hwndFocus ) )
return 0;
/* Change focus and send messages */
hWndPrevFocus = hwndFocus;
FOCUS_SwitchFocus( hwndFocus , hwnd );
return hWndPrevFocus;
}
HWND STDCALL GetFocus(void)
{
return hwndFocus;
}
/*****************************************************************
* FOCUS_SwitchFocus
*/
void FOCUS_SwitchFocus( HWND hFocusFrom, HWND hFocusTo )
{
WND *pFocusTo = WIN_FindWndPtr( hFocusTo );
hwndFocus = hFocusTo;
#if 0
if (hFocusFrom) SendMessageA( hFocusFrom, WM_KILLFOCUS, hFocusTo, 0 );
#else
/* FIXME: must be SendMessage16() because 32A doesn't do
* intertask at this time */
if (hFocusFrom) SendMessage( hFocusFrom, WM_KILLFOCUS, hFocusTo, 0 );
#endif
if( !pFocusTo || hFocusTo != hwndFocus )
return;
/* According to API docs, the WM_SETFOCUS message is sent AFTER the window
has received the keyboard focus. */
// pFocusTo->pDriver->pSetFocus(pFocusTo);
#if 0
SendMessageA( hFocusTo, WM_SETFOCUS, hFocusFrom, 0 );
#else
SendMessageA( hFocusTo, WM_SETFOCUS, hFocusFrom, 0 );
#endif
}

View File

@@ -7,24 +7,453 @@
* Based on investigations by Alex Korobka
*/
#include <windows.h>
#include <user32/hook.h>
#define GetThreadQueue(x) NULL
HANDLE HOOK_systemHooks[WH_NB_HOOKS] = { NULL, };
/***********************************************************************
* HOOK_CallHooks32W
* SetWindowsHookA
*
* FIXME: I don't know if this is correct
*/
HHOOK SetWindowsHookExA(int idHook, HOOKPROC lpfn, HINSTANCE hMod, DWORD dwThreadId )
{
return HOOK_SetHook( idHook, lpfn, HOOK_WINA, hMod, dwThreadId );
}
/***********************************************************************
* SetWindowsHookExW
*
* FIXME: I don't know if this is correct
*/
HHOOK SetWindowsHookExW(int idHook, HOOKPROC lpfn, HINSTANCE hMod, DWORD dwThreadId )
{
return HOOK_SetHook( idHook, lpfn, HOOK_WIN32W, hMod, dwThreadId );
}
/***********************************************************************
* UnhookWindowsHook
*/
WINBOOL STDCALL UnhookWindowsHook( INT id, HOOKPROC proc )
{
return FALSE;
}
/***********************************************************************
* UnhookWindowHookEx (USER.558)
*/
WINBOOL STDCALL UnhookWindowsHookEx( HHOOK hhook )
{
return HOOK_RemoveHook( hhook );
}
/***********************************************************************
* CallNextHookEx
*
* There aren't ANSI and UNICODE versions of this.
*/
LRESULT STDCALL CallNextHookEx( HHOOK hhook, INT code, WPARAM wParam,
LPARAM lParam )
{
HHOOK next;
INT fromtype; /* figure out Ansi/Unicode */
HOOKDATA *oldhook;
if (!(next = HOOK_GetNextHook(hhook ))) return 0;
oldhook = (HOOKDATA *)hhook ;
fromtype = oldhook->flags & HOOK_MAPTYPE;
return HOOK_CallHook( next, fromtype, code, wParam, lParam );
}
/***********************************************************************
* CallMsgFilterA (USER.15)
*/
/*
* FIXME: There are ANSI and UNICODE versions of this, plus an unspecified
* version, plus USER (the bit one) has a CallMsgFilter function.
*/
WINBOOL STDCALL CallMsgFilterA( LPMSG msg, INT code )
{
if (HOOK_CallHooksA( WH_SYSMSGFILTER, code, 0, (LPARAM)msg ))
return TRUE;
return HOOK_CallHooksA( WH_MSGFILTER, code, 0, (LPARAM)msg );
}
/***********************************************************************
* CallMsgFilterW (USER.)
*/
WINBOOL STDCALL CallMsgFilterW( LPMSG msg, INT code )
{
if (HOOK_CallHooksW( WH_SYSMSGFILTER, code, 0, (LPARAM)msg ))
return TRUE;
return HOOK_CallHooksW( WH_MSGFILTER, code, 0, (LPARAM)msg );
}
/***********************************************************************
* Internal Functions
*/
/***********************************************************************
* HOOK_GetNextHook
*
* Get the next hook of a given hook.
*/
HANDLE HOOK_GetNextHook( HHOOK hhook )
{
HOOKDATA *hook;
if (!hhook) return 0;
hook = (HOOKDATA *)hhook;
if (hook->next) return hook->next;
if (!hook->ownerQueue) return 0; /* Already system hook */
/* Now start enumerating the system hooks */
return HOOK_systemHooks[hook->id - WH_MINHOOK];
}
/***********************************************************************
* HOOK_GetHook
*
* Get the first hook for a given type.
*/
HANDLE HOOK_GetHook( INT id, HQUEUE hQueue )
{
// MESSAGEQUEUE *queue;
HHOOK hook = 0;
// if ((queue = (MESSAGEQUEUE *)GlobalLock( hQueue )) != NULL)
// hook = queue->hooks[id - WH_MINHOOK];
if (!hook) hook = HOOK_systemHooks[id - WH_MINHOOK];
return hook;
}
/***********************************************************************
* HOOK_SetHook
*
* Install a given hook.
*/
HANDLE HOOK_SetHook( INT id, LPVOID proc, INT type,
HINSTANCE hInst, DWORD dwThreadId )
{
HOOKDATA *data;
//HANDLE handle;
HQUEUE hQueue = 0;
if ((id < WH_MINHOOK) || (id > WH_MAXHOOK)) return 0;
//if (id == WH_JOURNALPLAYBACK) EnableHardwareInput(FALSE);
#if 0
if (hTask) /* Task-specific hook */
{
if ((id == WH_JOURNALRECORD) || (id == WH_JOURNALPLAYBACK) ||
(id == WH_SYSMSGFILTER)) return 0; /* System-only hooks */
if (!(hQueue = GetTaskQueue( hTask )))
{
/* FIXME: shouldn't this be done somewhere else? */
if (hTask != GetCurrentTask()) return 0;
if (!(hQueue = GetFastQueue())) return 0;
}
}
#endif
/* Create the hook structure */
if (!(data = HeapAlloc(GetProcessHeap(),0, sizeof(HOOKDATA) ))) return 0;
data->proc = proc;
data->id = id;
data->ownerQueue = hQueue;
data->ownerModule = hInst;
data->flags = type;
/* Insert it in the correct linked list */
#if 0
if (hQueue)
{
MESSAGEQUEUE *queue = (MESSAGEQUEUE *)GlobalLock16( hQueue );
data->next = queue->hooks[id - WH_MINHOOK];
queue->hooks[id - WH_MINHOOK] = data;
return data;
}
#endif
data->next = HOOK_systemHooks[id - WH_MINHOOK];
HOOK_systemHooks[id - WH_MINHOOK] = data;
return data;
}
/***********************************************************************
* HOOK_RemoveHook
*
* Remove a hook from the list.
*/
WINBOOL HOOK_RemoveHook( HANDLE hook )
{
HOOKDATA *data;
HANDLE *prevHook;
if (!(data = (HOOKDATA *)(hook))) return FALSE;
if (data->flags & HOOK_INUSE)
{
/* Mark it for deletion later on */
//WARN(hook, "Hook still running, deletion delayed\n" );
data->proc = (HOOKPROC)0;
return TRUE;
}
// if (data->id == WH_JOURNALPLAYBACK) EnableHardwareInput(TRUE);
/* Remove it from the linked list */
if (data->ownerQueue)
{
#if 0
MESSAGEQUEUE *queue = (MESSAGEQUEUE *)GlobalLock( data->ownerQueue );
if (!queue) return FALSE;
prevHook = &queue->hooks[data->id - WH_MINHOOK];
#endif
}
else
prevHook = &HOOK_systemHooks[data->id - WH_MINHOOK];
while (*prevHook && *prevHook != hook)
prevHook = &((HOOKDATA *)(*prevHook))->next;
if (!*prevHook) return FALSE;
*prevHook = data->next;
HeapFree(GetProcessHeap(),0, hook );
return TRUE;
}
/***********************************************************************
* HOOK_FindValidHook
*/
static HANDLE HOOK_FindValidHook( HANDLE hook )
{
HOOKDATA *data;
for (;;)
{
if (!(data = (HOOKDATA *)(hook))) return 0;
if (data->proc) return hook;
hook = data->next;
}
}
/***********************************************************************
* HOOK_CallHook
*
* Call a hook procedure.
*/
LRESULT HOOK_CallHook( HHOOK hook, INT fromtype, INT code,
WPARAM wParam, LPARAM lParam )
{
// MESSAGEQUEUE *queue;
HANDLE prevHook;
HOOKDATA *data = (HOOKDATA *)(hook);
LRESULT ret;
WPARAM wParamOrig = wParam;
LPARAM lParamOrig = lParam;
// HOOK_MapFunc MapFunc;
// HOOK_UnMapFunc UnMapFunc;
// MapFunc = HOOK_MapFuncs[fromtype][data->flags & HOOK_MAPTYPE];
// UnMapFunc = HOOK_UnMapFuncs[fromtype][data->flags & HOOK_MAPTYPE];
//if (MapFunc)
// MapFunc( data->id, code, &wParam, &lParam );
/* Now call it */
#if 0
if (!(queue = (MESSAGEQUEUE *)GlobalLock( GetThreadQueue(0) ))) return 0;
prevHook = queue->hCurHook;
queue->hCurHook = hook;
data->flags |= HOOK_INUSE;
#endif
//TRACE(hook, "Calling hook %04x: %d %08x %08lx\n",
// hook, code, wParam, lParam );
ret = data->proc(code, wParam, lParam);
//TRACE(hook, "Ret hook %04x = %08lx\n", hook, ret );
data->flags &= ~HOOK_INUSE;
//queue->hCurHook = prevHook;
//if (UnMapFunc)
// UnMapFunc( data->id, code, wParamOrig, lParamOrig, wParam, lParam );
if (!data->proc) HOOK_RemoveHook( hook );
return ret;
}
/***********************************************************************
* HOOK_IsHooked
*
* Replacement for calling HOOK_GetHook from other modules.
*/
WINBOOL HOOK_IsHooked( INT id )
{
return HOOK_GetHook( id, GetThreadQueue(0) ) != 0;
}
/***********************************************************************
* HOOK_CallHooksA
*
* Call a hook chain.
*/
#include <windows.h>
LRESULT HOOK_CallHooksA( INT id, INT code, WPARAM wParam,
LPARAM lParam )
{
HANDLE hook;
if (!(hook = HOOK_GetHook( id , GetThreadQueue(0) ))) return 0;
if (!(hook = HOOK_FindValidHook(hook))) return 0;
return HOOK_CallHook( hook, HOOK_WINA, code, wParam, lParam );
}
/***********************************************************************
* HOOK_CallHooksW
*
* Call a hook chain.
*/
LRESULT HOOK_CallHooksW( INT id, INT code, WPARAM wParam,
LPARAM lParam )
{
HANDLE hook;
if (!(hook = HOOK_GetHook( id , GetThreadQueue(0) ))) return 0;
if (!(hook = HOOK_FindValidHook(hook))) return 0;
return HOOK_CallHook( hook, HOOK_WINW, code, wParam,
lParam );
}
WINBOOL HOOK_IsHooked( INT id )
/***********************************************************************
* HOOK_ResetQueueHooks
*/
void HOOK_ResetQueueHooks( HQUEUE hQueue )
{
return FALSE;
}
#if 0
MESSAGEQUEUE *queue;
if ((queue = (MESSAGEQUEUE *)GlobalLock( hQueue )) != NULL)
{
HOOKDATA* data;
HHOOK hook;
int id;
for( id = WH_MINHOOK; id <= WH_MAXHOOK; id++ )
{
hook = queue->hooks[id - WH_MINHOOK];
while( hook )
{
if( (data = (HOOKDATA *)(hook)) )
{
data->ownerQueue = hQueue;
hook = data->next;
} else break;
}
}
}
#endif
}
/***********************************************************************
* HOOK_FreeModuleHooks
*/
void HOOK_FreeModuleHooks( HMODULE hModule )
{
/* remove all system hooks registered by this module */
HOOKDATA* hptr;
HHOOK hook, next;
int id;
for( id = WH_MINHOOK; id <= WH_MAXHOOK; id++ )
{
hook = HOOK_systemHooks[id - WH_MINHOOK];
while( hook )
if( (hptr = (HOOKDATA *)(hook)) )
{
next = hptr->next;
if( hptr->ownerModule == hModule )
{
hptr->flags &= HOOK_MAPTYPE;
HOOK_RemoveHook(hook);
}
hook = next;
}
else hook = 0;
}
}
/***********************************************************************
* HOOK_FreeQueueHooks
*/
void HOOK_FreeQueueHooks( HQUEUE hQueue )
{
/* remove all hooks registered by this queue */
HOOKDATA* hptr = NULL;
HHOOK hook, next;
int id;
for( id = WH_MINHOOK; id <= WH_MAXHOOK; id++ )
{
hook = HOOK_GetHook( id, hQueue );
while( hook )
{
next = HOOK_GetNextHook(hook);
hptr = (HOOKDATA *)(hook);
if( hptr && hptr->ownerQueue == hQueue )
{
hptr->flags &= HOOK_MAPTYPE;
HOOK_RemoveHook(hook);
}
hook = next;
}
}
}

View File

@@ -0,0 +1,64 @@
#include <windows.h>
#include <user32/debug.h>
static INT captureHT = HTCLIENT;
static HWND captureWnd = 0;
WINBOOL MouseButtonsStates[3];
WINBOOL AsyncMouseButtonsStates[3];
BYTE InputKeyStateTable[256];
BYTE QueueKeyStateTable[256];
BYTE AsyncKeyStateTable[256];
HWND EVENT_Capture(HWND hwnd, INT ht);
HWND STDCALL SetCapture( HWND hwnd )
{
return EVENT_Capture( hwnd, HTCLIENT );
}
WINBOOL STDCALL ReleaseCapture(void)
{
if( captureWnd ) EVENT_Capture( 0, 0 );
}
HWND STDCALL GetCapture(void)
{
return captureWnd;
}
/**********************************************************************
* EVENT_Capture
*
* We need this to be able to generate double click messages
* when menu code captures mouse in the window without CS_DBLCLK style.
*/
HWND EVENT_Capture(HWND hwnd, INT ht)
{
HWND capturePrev = captureWnd;
if (!hwnd)
{
captureWnd = 0L;
captureHT = 0;
}
else
{
if( IsWindow(hwnd) )
{
DPRINT("(0x%04x)\n", hwnd );
captureWnd = hwnd;
captureHT = ht;
}
}
if( capturePrev && capturePrev != captureWnd )
{
if( IsWindow(capturePrev) )
SendMessageA( capturePrev, WM_CAPTURECHANGED, 0L, hwnd);
}
return capturePrev;
}

File diff suppressed because it is too large Load Diff

View File

@@ -26,106 +26,22 @@
* ECMA-234, Win
*/
#if 0
LRESULT STDCALL SendMessageA( HWND hwnd, UINT msg, WPARAM wParam,
LPARAM lParam )
{
WND * wndPtr;
WND **list, **ppWnd;
LRESULT ret;
if (hwnd == HWND_BROADCAST || hwnd == HWND_TOPMOST)
{
if (!(list = WIN_BuildWinArray( WIN_GetDesktop(), 0, NULL )))
return TRUE;
for (ppWnd = list; *ppWnd; ppWnd++)
{
wndPtr = *ppWnd;
if (!IsWindow(wndPtr->hwndSelf)) continue;
if (wndPtr->dwStyle & WS_POPUP || wndPtr->dwStyle & WS_CAPTION)
SendMessageA( wndPtr->hwndSelf, msg, wParam, lParam );
}
HeapFree( GetProcessHeap(), 0, list );
return TRUE;
}
if (HOOK_IsHooked( WH_CALLWNDPROC ))
MSG_CallWndProcHook( (LPMSG)&hwnd, FALSE);
if (!(wndPtr = WIN_FindWndPtr( hwnd )))
{
//WARN(msg, "invalid hwnd %08x\n", hwnd );
return 0;
}
#if 0
if (QUEUE_IsExitingQueue(wndPtr->hmemTaskQ))
return 0; /* Don't send anything if the task is dying */
#endif
SPY_EnterMessage( SPY_SENDMESSAGE, hwnd, msg, wParam, lParam );
if (wndPtr->hmemTaskQ != GetFastQueue())
ret = MSG_SendMessage( wndPtr->hmemTaskQ, hwnd, msg, wParam, lParam,
QUEUE_SM_ASCII );
else
ret = CallWindowProcA( (WNDPROC)wndPtr->winproc,
hwnd, msg, wParam, lParam );
SPY_ExitMessage( SPY_RESULT_OK, hwnd, msg, ret );
return ret;
return MSG_SendMessage( hwnd, msg, wParam, lParam, FALSE );
}
LRESULT STDCALL SendMessageW(
HWND hwnd, /* Window to send message to. If HWND_BROADCAST,
the message will be sent to all top-level windows. */
UINT msg, /* message */
WPARAM wParam, /* message parameter */
LPARAM lParam /* additional message parameter */
) {
WND * wndPtr;
WND **list, **ppWnd;
LRESULT ret;
if (hwnd == HWND_BROADCAST || hwnd == HWND_TOPMOST)
{
if (!(list = WIN_BuildWinArray( WIN_GetDesktop(), 0, NULL )))
return TRUE;
for (ppWnd = list; *ppWnd; ppWnd++)
{
wndPtr = *ppWnd;
if (!IsWindow(wndPtr->hwndSelf)) continue;
if (wndPtr->dwStyle & WS_POPUP || wndPtr->dwStyle & WS_CAPTION)
SendMessageW( wndPtr->hwndSelf, msg, wParam, lParam );
}
HeapFree( GetProcessHeap(), 0, list );
return TRUE;
}
if (HOOK_IsHooked( WH_CALLWNDPROC ))
MSG_CallWndProcHook( (LPMSG)&hwnd, TRUE);
if (!(wndPtr = WIN_FindWndPtr( hwnd )))
{
//WARN(msg, "invalid hwnd %08x\n", hwnd );
return 0;
}
#if 0
if (QUEUE_IsExitingQueue(wndPtr->hmemTaskQ))
return 0; /* Don't send anything if the task is dying */
#endif
SPY_EnterMessage( SPY_SENDMESSAGE, hwnd, msg, wParam, lParam );
if (wndPtr->hmemTaskQ != GetFastQueue())
ret = MSG_SendMessage( wndPtr->hmemTaskQ, hwnd, msg, wParam, lParam,
QUEUE_SM_ASCII | QUEUE_SM_UNICODE );
else
ret = CallWindowProcW( (WNDPROC)wndPtr->winproc,
hwnd, msg, wParam, lParam );
SPY_ExitMessage( SPY_RESULT_OK, hwnd, msg, ret );
return ret;
LRESULT STDCALL SendMessageW( HWND hwnd, UINT msg, WPARAM wParam,
LPARAM lParam )
{
return MSG_SendMessage( hwnd, msg, wParam, lParam, TRUE );
}
#endif
/***********************************************************************
@@ -133,11 +49,57 @@ LRESULT STDCALL SendMessageW(
*
* Implementation of an inter-task SendMessage.
*/
LRESULT MSG_SendMessage( HQUEUE hDestQueue, HWND hwnd, UINT msg,
WPARAM wParam, LPARAM lParam, WORD flags )
LRESULT MSG_SendMessage( HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam, WINBOOL bUnicode )
{
return 0;
WND * wndPtr;
LRESULT ret;
MSG msg;
// SPY_EnterMessage( SPY_SENDMESSAGE, hwnd, msg, wParam, lParam );
#if 0
WND **list, **ppWnd;
if (hwnd == HWND_BROADCAST || hwnd == HWND_TOPMOST)
{
if (!(list = WIN_BuildWinArray( WIN_GetDesktop(), 0, NULL )))
return TRUE;
for (ppWnd = list; *ppWnd; ppWnd++)
{
wndPtr = *ppWnd;
if (!WIN_IsWindow(wndPtr->hwndSelf))
continue;
if (wndPtr->dwStyle & WS_POPUP || wndPtr->dwStyle & WS_CAPTION)
MSG_SendMessage( wndPtr->hwndSelf, message, wParam, lParam, bUnicode );
}
WIN_DestroyList( list );
return TRUE;
}
#endif
if (HOOK_IsHooked( WH_CALLWNDPROC ))
MSG_CallWndProcHook( (LPMSG)&hwnd, FALSE);
if (!(wndPtr = WIN_FindWndPtr( hwnd )))
{
return 0;
}
msg.hwnd = hwnd;
msg.message = message;
msg.wParam = wParam;
msg.lParam = lParam;
msg.time = 0;
msg.pt.x = 0;
msg.pt.y = 0;
// SPY_ExitMessage( SPY_RESULT_OK, hwnd, msg, ret );
return ret;
}
/************************************************************************
* MSG_CallWndProcHook
*/
@@ -160,3 +122,17 @@ void MSG_CallWndProcHook( LPMSG pmsg, WINBOOL bUnicode )
pmsg->message = cwp.message;
pmsg->hwnd = cwp.hwnd;
}
/***********************************************************************
* MSG_InternalGetMessage
*
* GetMessage() function for internal use. Behave like GetMessage(),
* but also call message filters and optionally send WM_ENTERIDLE messages.
* 'hwnd' must be the handle of the dialog or menu window.
* 'code' is the message filter value (MSGF_??? codes).
*/
WINBOOL MSG_InternalGetMessage( MSG *msg, HWND hwnd, HWND hwndOwner,
WPARAM code, WORD flags, WINBOOL sendIdle )
{
}

View File

@@ -0,0 +1,925 @@
#include <windows.h>
#include <user32/msg.h>
#include <user32/hook.h>
#include <user32/queue.h>
#include <user32/spy.h>
#include <user32/msg.h>
#include <user32/debug.h>
extern int doubleClickSpeed;
HQUEUE hFirstQueue;
HQUEUE hNewQueue;
/**********************************************************************
* SetDoubleClickTime (USER.480)
*/
WINBOOL STDCALL SetDoubleClickTime( UINT interval )
{
doubleClickSpeed = interval ? interval : 500;
return TRUE;
}
/**********************************************************************
* GetDoubleClickTime (USER.239)
*/
UINT STDCALL GetDoubleClickTime(void)
{
return doubleClickSpeed;
}
/***********************************************************************
* PeekMessageW Check queue for messages
*
* Checks for a message in the thread's queue, filtered as for
* GetMessage(). Returns immediately whether a message is available
* or not.
*
* Whether a retrieved message is removed from the queue is set by the
* _wRemoveMsg_ flags, which should be one of the following values:
*
* PM_NOREMOVE Do not remove the message from the queue.
*
* PM_REMOVE Remove the message from the queue.
*
* In addition, PM_NOYIELD may be combined into _wRemoveMsg_ to
* request that the system not yield control during PeekMessage();
* however applications may not rely on scheduling behavior.
*
* RETURNS
*
* Nonzero if a message is available and is retrieved, zero otherwise.
*
* CONFORMANCE
*
* ECMA-234, Win
*
*/
WINBOOL STDCALL PeekMessageA( LPMSG msg, HWND hwnd, UINT first,
UINT last, UINT flags )
{
return MSG_PeekMessage( msg, hwnd, first, last, flags, FALSE );
}
WINBOOL STDCALL PeekMessageW( LPMSG msg, HWND hwnd, UINT first,
UINT last, UINT flags )
{
return MSG_PeekMessage( msg, hwnd, first, last, flags, TRUE );
}
/***********************************************************************
* GetMessageW (USER.274) Retrieve next message
*
* GetMessage retrieves the next event from the calling thread's
* queue and deposits it in *lpmsg.
*
* If _hwnd_ is not NULL, only messages for window _hwnd_ and its
* children as specified by IsChild() are retrieved. If _hwnd_ is NULL
* all application messages are retrieved.
*
* _min_ and _max_ specify the range of messages of interest. If
* min==max==0, no filtering is performed. Useful examples are
* WM_KEYFIRST and WM_KEYLAST to retrieve keyboard input, and
* WM_MOUSEFIRST and WM_MOUSELAST to retrieve mouse input.
*
* WM_PAINT messages are not removed from the queue; they remain until
* processed. Other messages are removed from the queue.
*
* RETURNS
*
* -1 on error, 0 if message is WM_QUIT, nonzero otherwise.
*
* CONFORMANCE
*
* ECMA-234, Win
*
*/
WINBOOL
STDCALL
GetMessageA(LPMSG lpMsg, HWND hWnd ,
UINT wMsgFilterMin, UINT wMsgFilterMax)
{
MSG_PeekMessage( lpMsg, hWnd, wMsgFilterMin, wMsgFilterMax, PM_REMOVE, FALSE );
HOOK_CallHooksA( WH_GETMESSAGE, HC_ACTION, 0, (LPARAM)lpMsg );
return (lpMsg->message != WM_QUIT);
}
WINBOOL
STDCALL
GetMessageW(
LPMSG lpMsg,
HWND hWnd ,
UINT wMsgFilterMin,
UINT wMsgFilterMax)
{
MSG_PeekMessage( lpMsg, hWnd, wMsgFilterMin, wMsgFilterMax, PM_REMOVE, FALSE );
HOOK_CallHooksW( WH_GETMESSAGE, HC_ACTION, 0, (LPARAM)lpMsg );
return (lpMsg->message != WM_QUIT);
}
/***********************************************************************
* PostMessageA (USER.419)
*/
WINBOOL STDCALL PostMessageA( HWND hwnd, UINT message, WPARAM wParam,
LPARAM lParam )
{
MSG msg;
WND *wndPtr;
msg.hwnd = hwnd;
msg.message = message;
msg.wParam = wParam;
msg.lParam = lParam;
msg.time = GetTickCount();
msg.pt.x = 0;
msg.pt.y = 0;
#ifdef CONFIG_IPC
if (DDE_PostMessage(&msg))
return TRUE;
#endif /* CONFIG_IPC */
if (hwnd == HWND_BROADCAST)
{
DPRINT("HWND_BROADCAST !\n");
for (wndPtr = WIN_GetDesktop()->child; wndPtr; wndPtr = wndPtr->next)
{
if (wndPtr->dwStyle & WS_POPUP || wndPtr->dwStyle & WS_CAPTION)
{
DPRINT("BROADCAST Message to hWnd=%04x m=%04X w=%04X l=%08lX !\n",
wndPtr->hwndSelf, message, wParam, lParam);
PostMessageA( wndPtr->hwndSelf, message, wParam, lParam );
}
}
DPRINT("End of HWND_BROADCAST !\n");
return TRUE;
}
wndPtr = WIN_FindWndPtr( hwnd );
if (!wndPtr || !wndPtr->hmemTaskQ) return FALSE;
return QUEUE_AddMsg( wndPtr->hmemTaskQ, &msg, 0 );
}
/***********************************************************************
* PostMessageW (USER.420)
*/
WINBOOL STDCALL PostMessageW( HWND hwnd, UINT message, WPARAM wParam,
LPARAM lParam )
{
MSG msg;
WND *wndPtr;
msg.hwnd = hwnd;
msg.message = message;
msg.wParam = wParam;
msg.lParam = lParam;
msg.time = GetTickCount();
msg.pt.x = 0;
msg.pt.y = 0;
#ifdef CONFIG_IPC
if (DDE_PostMessage(&msg))
return TRUE;
#endif /* CONFIG_IPC */
if (hwnd == HWND_BROADCAST)
{
DPRINT("HWND_BROADCAST !\n");
for (wndPtr = WIN_GetDesktop()->child; wndPtr; wndPtr = wndPtr->next)
{
if (wndPtr->dwStyle & WS_POPUP || wndPtr->dwStyle & WS_CAPTION)
{
DPRINT("BROADCAST Message to hWnd=%04x m=%04X w=%04X l=%08lX !\n",
wndPtr->hwndSelf, message, wParam, lParam);
PostMessageA( wndPtr->hwndSelf, message, wParam, lParam );
}
}
DPRINT("End of HWND_BROADCAST !\n");
return TRUE;
}
wndPtr = WIN_FindWndPtr( hwnd );
if (!wndPtr || !wndPtr->hmemTaskQ) return FALSE;
return QUEUE_AddMsg( wndPtr->hmemTaskQ, &msg, 0 );
}
/***********************************************************************
* SendMessageW (USER.459) Send Window Message
*
* Sends a message to the window procedure of the specified window.
* SendMessage() will not return until the called window procedure
* either returns or calls ReplyMessage().
*
* Use PostMessage() to send message and return immediately. A window
* procedure may use InSendMessage() to detect
* SendMessage()-originated messages.
*
* Applications which communicate via HWND_BROADCAST may use
* RegisterWindowMessage() to obtain a unique message to avoid conflicts
* with other applications.
*
* CONFORMANCE
*
* ECMA-234, Win
*/
LRESULT STDCALL SendMessageA( HWND hwnd, UINT msg, WPARAM wParam,
LPARAM lParam )
{
WND * wndPtr;
WND **list, **ppWnd;
LRESULT ret;
if (hwnd == HWND_BROADCAST || hwnd == HWND_TOPMOST)
{
if (!(list = WIN_BuildWinArray( WIN_GetDesktop(), 0, NULL )))
return TRUE;
for (ppWnd = list; *ppWnd; ppWnd++)
{
wndPtr = *ppWnd;
if (!IsWindow(wndPtr->hwndSelf)) continue;
if (wndPtr->dwStyle & WS_POPUP || wndPtr->dwStyle & WS_CAPTION)
SendMessageA( wndPtr->hwndSelf, msg, wParam, lParam );
}
HeapFree( GetProcessHeap(), 0, list );
return TRUE;
}
if (HOOK_IsHooked( WH_CALLWNDPROC ))
MSG_CallWndProcHook( (LPMSG)&hwnd, FALSE);
if (!(wndPtr = WIN_FindWndPtr( hwnd )))
{
DPRINT( "invalid hwnd %08x\n", hwnd );
return 0;
}
if (QUEUE_IsExitingQueue(wndPtr->hmemTaskQ))
return 0; /* Don't send anything if the task is dying */
SPY_EnterMessage( SPY_SENDMESSAGE, hwnd, msg, wParam, lParam );
if (wndPtr->hmemTaskQ != GetFastQueue())
ret = MSG_SendMessage( wndPtr->hmemTaskQ, hwnd, msg, wParam, lParam,
QUEUE_SM_ASCII );
else
ret = CallWindowProcA( (WNDPROC)wndPtr->winproc,
hwnd, msg, wParam, lParam );
SPY_ExitMessage( SPY_RESULT_OK, hwnd, msg, ret );
return ret;
}
LRESULT STDCALL SendMessageW(
HWND hwnd, /* Window to send message to. If HWND_BROADCAST,
the message will be sent to all top-level windows. */
UINT msg, /* message */
WPARAM wParam, /* message parameter */
LPARAM lParam /* additional message parameter */
) {
WND * wndPtr;
WND **list, **ppWnd;
LRESULT ret;
if (hwnd == HWND_BROADCAST || hwnd == HWND_TOPMOST)
{
if (!(list = WIN_BuildWinArray( WIN_GetDesktop(), 0, NULL )))
return TRUE;
for (ppWnd = list; *ppWnd; ppWnd++)
{
wndPtr = *ppWnd;
if (!IsWindow(wndPtr->hwndSelf)) continue;
if (wndPtr->dwStyle & WS_POPUP || wndPtr->dwStyle & WS_CAPTION)
SendMessageW( wndPtr->hwndSelf, msg, wParam, lParam );
}
HeapFree( GetProcessHeap(), 0, list );
return TRUE;
}
if (HOOK_IsHooked( WH_CALLWNDPROC ))
MSG_CallWndProcHook( (LPMSG)&hwnd, TRUE);
if (!(wndPtr = WIN_FindWndPtr( hwnd )))
{
DPRINT( "invalid hwnd %08x\n", hwnd );
return 0;
}
if (QUEUE_IsExitingQueue(wndPtr->hmemTaskQ))
return 0; /* Don't send anything if the task is dying */
SPY_EnterMessage( SPY_SENDMESSAGE, hwnd, msg, wParam, lParam );
if (wndPtr->hmemTaskQ != GetFastQueue())
ret = MSG_SendMessage( wndPtr->hmemTaskQ, hwnd, msg, wParam, lParam,
QUEUE_SM_ASCII | QUEUE_SM_UNICODE );
else
ret = CallWindowProcW( (WNDPROC)wndPtr->winproc,
hwnd, msg, wParam, lParam );
SPY_ExitMessage( SPY_RESULT_OK, hwnd, msg, ret );
return ret;
}
/***********************************************************************
* TranslateMessage (USER.556)
*/
WINBOOL STDCALL TranslateMessage( const MSG *msg )
{
return MSG_DoTranslateMessage( msg->message, msg->hwnd,
msg->wParam, msg->lParam );
}
/***********************************************************************
* DispatchMessageA (USER.141)
*/
LONG STDCALL DispatchMessageA( const MSG* msg )
{
WND * wndPtr;
LONG retval;
int painting;
/* Process timer messages */
if ((msg->message == WM_TIMER) || (msg->message == WM_SYSTIMER))
{
if (msg->lParam)
{
/* HOOK_CallHooksA( WH_CALLWNDPROC, HC_ACTION, 0, FIXME ); */
return CallWindowProcA( (WNDPROC)msg->lParam, msg->hwnd,
msg->message, msg->wParam, GetTickCount() );
}
}
if (!msg->hwnd) return 0;
if (!(wndPtr = WIN_FindWndPtr( msg->hwnd ))) return 0;
if (!wndPtr->winproc) return 0;
painting = (msg->message == WM_PAINT);
if (painting) wndPtr->flags |= WIN_NEEDS_BEGINPAINT;
/* HOOK_CallHooksA( WH_CALLWNDPROC, HC_ACTION, 0, FIXME ); */
SPY_EnterMessage( SPY_DISPATCHMESSAGE, msg->hwnd, msg->message,
msg->wParam, msg->lParam );
retval = CallWindowProcA( (WNDPROC)wndPtr->winproc,
msg->hwnd, msg->message,
msg->wParam, msg->lParam );
SPY_ExitMessage( SPY_RESULT_OK, msg->hwnd, msg->message, retval );
if (painting && (wndPtr = WIN_FindWndPtr( msg->hwnd )) &&
(wndPtr->flags & WIN_NEEDS_BEGINPAINT) && wndPtr->hrgnUpdate)
{
//ERR(msg, "BeginPaint not called on WM_PAINT for hwnd %04x!\n",
// msg->hwnd);
wndPtr->flags &= ~WIN_NEEDS_BEGINPAINT;
/* Validate the update region to avoid infinite WM_PAINT loop */
ValidateRect( msg->hwnd, NULL );
}
return retval;
}
/***********************************************************************
* DispatchMessageW (USER.142) Process Message
*
* Process the message specified in the structure *_msg_.
*
* If the lpMsg parameter points to a WM_TIMER message and the
* parameter of the WM_TIMER message is not NULL, the lParam parameter
* points to the function that is called instead of the window
* procedure.
*
* The message must be valid.
*
* RETURNS
*
* DispatchMessage() returns the result of the window procedure invoked.
*
* CONFORMANCE
*
* ECMA-234, Win
*
*/
LONG STDCALL DispatchMessageW( const MSG* msg )
{
WND * wndPtr;
LONG retval;
int painting;
/* Process timer messages */
if ((msg->message == WM_TIMER) || (msg->message == WM_SYSTIMER))
{
if (msg->lParam)
{
/* HOOK_CallHooksW( WH_CALLWNDPROC, HC_ACTION, 0, FIXME ); */
return CallWindowProcW( (WNDPROC)msg->lParam, msg->hwnd,
msg->message, msg->wParam, GetTickCount() );
}
}
if (!msg->hwnd) return 0;
if (!(wndPtr = WIN_FindWndPtr( msg->hwnd ))) return 0;
if (!wndPtr->winproc) return 0;
painting = (msg->message == WM_PAINT);
if (painting) wndPtr->flags |= WIN_NEEDS_BEGINPAINT;
/* HOOK_CallHooksW( WH_CALLWNDPROC, HC_ACTION, 0, FIXME ); */
SPY_EnterMessage( SPY_DISPATCHMESSAGE, msg->hwnd, msg->message,
msg->wParam, msg->lParam );
retval = CallWindowProcW( (WNDPROC)wndPtr->winproc,
msg->hwnd, msg->message,
msg->wParam, msg->lParam );
SPY_ExitMessage( SPY_RESULT_OK, msg->hwnd, msg->message, retval );
if (painting && (wndPtr = WIN_FindWndPtr( msg->hwnd )) &&
(wndPtr->flags & WIN_NEEDS_BEGINPAINT) && wndPtr->hrgnUpdate)
{
//ERR(msg, "BeginPaint not called on WM_PAINT for hwnd %04x!\n",
// msg->hwnd);
wndPtr->flags &= ~WIN_NEEDS_BEGINPAINT;
/* Validate the update region to avoid infinite WM_PAINT loop */
ValidateRect( msg->hwnd, NULL );
}
return retval;
}
/**********************************************************************
* PostThreadMessageA (USER.422)
*
* BUGS
*
* Thread-local message queues are not supported.
*
*/
WINBOOL STDCALL PostThreadMessageA(DWORD idThread , UINT message,
WPARAM wParam, LPARAM lParam )
{
return FALSE;
}
/**********************************************************************
* PostThreadMessageW (USER.423)
*
* BUGS
*
* Thread-local message queues are not supported.
*
*/
WINBOOL STDCALL PostThreadMessageW(DWORD idThread , UINT message,
WPARAM wParam, LPARAM lParam )
{
return FALSE;
}
/***********************************************************************
* SendMessageTimeoutA (USER.457)
*/
LRESULT STDCALL SendMessageTimeoutA( HWND hwnd, UINT msg, WPARAM wParam,
LPARAM lParam, UINT flags,
UINT timeout, LPDWORD resultp)
{
// DPRINT( "(...): semistub\n");
return SendMessageA (hwnd, msg, wParam, lParam);
}
/***********************************************************************
* SendMessageTimeoutW (USER.458)
*/
LRESULT STDCALL SendMessageTimeoutW( HWND hwnd, UINT msg, WPARAM wParam,
LPARAM lParam, UINT flags,
UINT timeout, LPDWORD resultp)
{
// DPRINT( "(...): semistub\n");
return SendMessageW (hwnd, msg, wParam, lParam);
}
/***********************************************************************
* WaitMessage (USER.112) (USER.578) Suspend thread pending messages
*
* WaitMessage() suspends a thread until events appear in the thread's
* queue.
*
* BUGS
*
* Is supposed to return WINBOOL under Win.
*
* Thread-local message queues are not supported.
*
* CONFORMANCE
*
* ECMA-234, Win
*
*/
WINBOOL
STDCALL
WaitMessage(VOID)
{
QUEUE_WaitBits( QS_ALLINPUT );
return TRUE;
}
/***********************************************************************
* MsgWaitForMultipleObjects (USER.400)
*/
DWORD STDCALL MsgWaitForMultipleObjects( DWORD nCount, HANDLE *pHandles,
WINBOOL fWaitAll, DWORD dwMilliseconds,
DWORD dwWakeMask )
{
}
/***********************************************************************
* RegisterWindowMessageA (USER.437)
*/
UINT
STDCALL
RegisterWindowMessageA(
LPCSTR lpString)
{
return GlobalAddAtomA( lpString );
}
/***********************************************************************
* RegisterWindowMessageW (USER.438)
*/
UINT
STDCALL
RegisterWindowMessageW(
LPCWSTR lpString)
{
return GlobalAddAtomW( lpString );
}
/***********************************************************************
* InSendMessage (USER.0)
*/
WINBOOL STDCALL InSendMessage(void)
{
MESSAGEQUEUE *queue;
if (!(queue = (MESSAGEQUEUE *)GlobalLock( GetFastQueue() )))
return 0;
return (WINBOOL)queue->InSendMessageHandle;
}
/***********************************************************************
* BroadcastSystemMessage (USER.12)
*/
LONG STDCALL BroadcastSystemMessage(
DWORD dwFlags,LPDWORD recipients,UINT uMessage,WPARAM wParam,
LPARAM lParam
) {
DPRINT("(%08lx,%08lx,%08x,%08x,%08lx): stub!\n",
dwFlags,*recipients,uMessage,wParam,lParam
);
return 0;
}
/***********************************************************************
* SendNotifyMessageA (USER.460)
* FIXME
* The message sended with PostMessage has to be put in the queue
* with a higher priority as the other "Posted" messages.
* QUEUE_AddMsg has to be modifyed.
*/
WINBOOL STDCALL SendNotifyMessageA(HWND hwnd,UINT msg,WPARAM wParam,LPARAM lParam)
{ WINBOOL ret = TRUE;
DPRINT("(%04x,%08x,%08x,%08lx) not complete\n",
hwnd, msg, wParam, lParam);
if ( GetCurrentThreadId() == GetWindowThreadProcessId ( hwnd, NULL))
{ ret=SendMessageA ( hwnd, msg, wParam, lParam );
}
else
{ PostMessageA ( hwnd, msg, wParam, lParam );
}
return ret;
}
/***********************************************************************
* SendNotifyMessageW (USER.461)
* FIXME
* The message sended with PostMessage has to be put in the queue
* with a higher priority as the other "Posted" messages.
* QUEUE_AddMsg has to be modifyed.
*/
WINBOOL STDCALL SendNotifyMessageW(HWND hwnd,UINT msg,WPARAM wParam,LPARAM lParam)
{ WINBOOL ret = TRUE;
DPRINT("(%04x,%08x,%08x,%08lx) not complete\n",
hwnd, msg, wParam, lParam);
if ( GetCurrentThreadId() == GetWindowThreadProcessId ( hwnd, NULL))
{ ret=SendMessageW ( hwnd, msg, wParam, lParam );
}
else
{ PostMessageW ( hwnd, msg, wParam, lParam );
}
return ret;
}
/***********************************************************************
* SendMessageCallBackA
* FIXME: It's like PostMessage. The callback gets called when the message
* is processed. We have to modify the message processing for a exact
* implementation...
*/
WINBOOL
STDCALL
SendMessageCallbackA(
HWND hWnd,
UINT Msg,
WPARAM wParam,
LPARAM lParam,
SENDASYNCPROC lpResultCallBack,
DWORD dwData)
{
if ( hWnd == HWND_BROADCAST)
{ PostMessageA( hWnd, Msg, wParam, lParam);
// DPRINT("Broadcast: Callback will not be called!\n");
return TRUE;
}
(lpResultCallBack)( hWnd, Msg, dwData, SendMessageA ( hWnd, Msg, wParam, lParam ));
return TRUE;
}
/***********************************************************************
* ReplyMessage (USER.115)
*/
WINBOOL STDCALL ReplyMessage( LRESULT result )
{
MESSAGEQUEUE *senderQ;
MESSAGEQUEUE *queue;
if (!(queue = (MESSAGEQUEUE*)GlobalLock( GetFastQueue() ))) return;
DPRINT("ReplyMessage, queue %04x\n", queue->self);
while( (senderQ = (MESSAGEQUEUE*)GlobalLock( queue->InSendMessageHandle)))
{
DPRINT("\trpm: replying to %04x (%04x -> %04x)\n",
queue->msg, queue->self, senderQ->self);
if( queue->wakeBits & QS_SENDMESSAGE )
{
QUEUE_ReceiveMessage( queue );
continue; /* ReceiveMessage() already called us */
}
if(!(senderQ->wakeBits & QS_SMRESULT) ) break;
// if (THREAD_IsWinA(THREAD_Current())) OldYield();
}
if( !senderQ ) { DPRINT("\trpm: done\n"); return; }
senderQ->SendMessageReturn = result;
DPRINT("\trpm: smResult = %08x, result = %08lx\n",
(unsigned)queue->smResultCurrent, result );
senderQ->smResult = queue->smResultCurrent;
queue->InSendMessageHandle = 0;
QUEUE_SetWakeBit( senderQ, QS_SMRESULT );
// if (THREAD_IsWinA(THREAD_Current())) DirectedYield( senderQ->hTask );
}
/***********************************************************************
* PostQuitMessage (USER.421)
*
* PostQuitMessage() posts a message to the system requesting an
* application to terminate execution. As a result of this function,
* the WM_QUIT message is posted to the application, and
* PostQuitMessage() returns immediately. The exitCode parameter
* specifies an application-defined exit code, which appears in the
* _wParam_ parameter of the WM_QUIT message posted to the application.
*
* CONFORMANCE
*
* ECMA-234, Win
*/
void STDCALL PostQuitMessage( INT exitCode )
{
MESSAGEQUEUE *queue;
if (!(queue = (MESSAGEQUEUE *)GlobalLock( GetFastQueue() ))) return;
queue->wPostQMsg = TRUE;
queue->wExitCode = (WORD)exitCode;
}
/***********************************************************************
* GetWindowThreadProcessId (USER.313)
*/
DWORD STDCALL GetWindowThreadProcessId( HWND hwnd, LPDWORD process )
{
return 0;
}
/***********************************************************************
* SetMessageQueue (USER.494)
*/
WINBOOL STDCALL SetMessageQueue( INT size )
{
HQUEUE hQueue, hNewQueue;
MESSAGEQUEUE *queuePtr;
DPRINT("task %04x size %i\n", GetCurrentTask(), size);
if ((size > MAX_QUEUE_SIZE) || (size <= 0)) return FALSE;
if( !(hNewQueue = QUEUE_CreateMsgQueue( size )))
{
DPRINT( "failed!\n");
return FALSE;
}
queuePtr = (MESSAGEQUEUE *)GlobalLock( hNewQueue );
SIGNAL_MaskAsyncEvents( TRUE );
/* Copy data and free the old message queue */
if ((hQueue = GetThreadQueue(0)) != 0)
{
MESSAGEQUEUE *oldQ = (MESSAGEQUEUE *)GlobalLock( hQueue );
memcpy( &queuePtr->wParamHigh, &oldQ->wParamHigh,
(int)oldQ->messages - (int)(&oldQ->wParamHigh) );
HOOK_ResetQueueHooks( hNewQueue );
if( WIN_GetDesktop()->hmemTaskQ == hQueue )
WIN_GetDesktop()->hmemTaskQ = hNewQueue;
WIN_ResetQueueWindows( WIN_GetDesktop(), hQueue, hNewQueue );
// CLIPBOARD_ResetLock( hQueue, hNewQueue );
QUEUE_DeleteMsgQueue( hQueue );
}
/* Link new queue into list */
queuePtr->hTask = GetCurrentTask();
queuePtr->next = hFirstQueue;
hFirstQueue = hNewQueue;
if( !queuePtr->next ) pCursorQueue = queuePtr;
SetThreadQueue( 0, hNewQueue );
SIGNAL_MaskAsyncEvents( FALSE );
return TRUE;
// win32 dynamically expands the message queue
}
/***********************************************************************
* GetQueueStatus (USER.283)
*/
DWORD STDCALL GetQueueStatus( UINT flags )
{
MESSAGEQUEUE *queue;
DWORD ret;
if (!(queue = (MESSAGEQUEUE *)GlobalLock( GetFastQueue() ))) return 0;
ret = MAKELONG( queue->changeBits, queue->wakeBits );
queue->changeBits = 0;
return ret & MAKELONG( flags, flags );
}
/***********************************************************************
* WaitForInputIdle (USER.577)
*/
DWORD STDCALL WaitForInputIdle (HANDLE hProcess, DWORD dwTimeOut)
{
// FIXME (msg, "(hProcess=%d, dwTimeOut=%ld): stub\n", hProcess, dwTimeOut);
return WAIT_TIMEOUT;
}
/***********************************************************************
* GetInputState (USER.244)
*/
WINBOOL STDCALL GetInputState(void)
{
MESSAGEQUEUE *queue;
if (!(queue = (MESSAGEQUEUE *)GlobalLock( GetFastQueue() )))
return FALSE;
return queue->wakeBits & (QS_KEY | QS_MOUSEBUTTON);
}
/***********************************************************************
* GetMessagePos (USER.272)
*
* The GetMessagePos() function returns a long value representing a
* cursor position, in screen coordinates, when the last message
* retrieved by the GetMessage() function occurs. The x-coordinate is
* in the low-order word of the return value, the y-coordinate is in
* the high-order word. The application can use the MAKEPOINT()
* macro to obtain a POINT structure from the return value.
*
* For the current cursor position, use GetCursorPos().
*
* RETURNS
*
* Cursor position of last message on success, zero on failure.
*
* CONFORMANCE
*
* ECMA-234, Win
*
*/
DWORD STDCALL GetMessagePos(void)
{
MESSAGEQUEUE *queue;
if (!(queue = (MESSAGEQUEUE *)GlobalLock( GetFastQueue() ))) return 0;
return queue->GetMessagePosVal;
}
/***********************************************************************
* GetMessageTime (USER.273)
*
* GetMessageTime() returns the message time for the last message
* retrieved by the function. The time is measured in milliseconds with
* the same offset as GetTickCount().
*
* Since the tick count wraps, this is only useful for moderately short
* relative time comparisons.
*
* RETURNS
*
* Time of last message on success, zero on failure.
*
* CONFORMANCE
*
* ECMA-234, Win
*
*/
LONG STDCALL GetMessageTime(void)
{
MESSAGEQUEUE *queue;
if (!(queue = (MESSAGEQUEUE *)GlobalLock( GetFastQueue() ))) return 0;
return queue->GetMessageTimeVal;
}
/***********************************************************************
* GetMessageExtraInfo (USER.271)
*/
LONG STDCALL GetMessageExtraInfo(void)
{
MESSAGEQUEUE *queue;
if (!(queue = (MESSAGEQUEUE *)GlobalLock( GetFastQueue() ))) return 0;
return queue->GetMessageExtraInfoVal;
}
WINBOOL STDCALL MessageBeep( UINT uType )
{
return Beep(uType ,0);
}

View File

@@ -0,0 +1,200 @@
#include <windows.h>
#include <user32/property.h>
#include <user32/win.h>
/***********************************************************************
* GetPropA (USER.281)
*/
HANDLE STDCALL GetPropA( HWND hWnd, LPCSTR str )
{
PROPERTY *prop;
prop = PROPERTY_FindProp(hWnd,STRING2ATOMA(str));
return prop ? prop->handle : NULL;
}
/***********************************************************************
* GetPropW (USER.282)
*/
HANDLE STDCALL GetPropW( HWND hWnd, LPCWSTR str)
{
PROPERTY *prop;
prop = PROPERTY_FindProp(hWnd,STRING2ATOMW(str));
return prop ? prop->handle : NULL;
}
/***********************************************************************
* SetPropA (USER.497)
*/
WINBOOL STDCALL SetPropA( HWND hwnd, LPCSTR str, HANDLE hdata )
{
return PROPERTY_SetProp( hwnd,STRING2ATOMA(str),hdata);
}
/***********************************************************************
* SetPropW (USER.498)
*/
WINBOOL STDCALL SetPropW( HWND hwnd, LPCWSTR str, HANDLE hdata )
{
return PROPERTY_SetProp(hwnd,STRING2ATOMW(str),hdata);
}
/***********************************************************************
* RemovePropA (USER.442)
*/
HANDLE STDCALL RemovePropA( HWND hwnd, LPCSTR str )
{
return PROPERTY_RemoveProp(hwnd, STRING2ATOMA(str));
}
/***********************************************************************
* RemovePropW (USER.443)
*/
HANDLE STDCALL RemovePropW( HWND hwnd, LPCWSTR str )
{
return PROPERTY_RemoveProp(hwnd, STRING2ATOMW(str));
}
#if 0
/***********************************************************************
* EnumPropsA (USER.186)
*/
INT STDCALL EnumPropsA( HWND hwnd, PROPENUMPROCA func )
{
int size;
int i;
INT ret = -1;
LPWSTR string[MAX_PATH];
PROPVALUE pv;
pv = malloc(100*sizeof(PROPVALUE));
PROPERTY_EnumPropEx(hwnd, pv ,100, &size );
for (i=0;i<size;i++)
{
/* Already get the next in case the callback */
/* function removes the current property. */
next = prop->next;
GlobalFindAtomNameA(pv[i]->atom,string,MAX_PATH-1);
ret = func( hwnd, string, pv[i]->handle);
if (!ret)
break;
}
free(pv);
return ret;
}
/***********************************************************************
* EnumPropsW (USER.189)
*/
INT STDCALL EnumPropsW( HWND hwnd, PROPENUMPROCW func )
{
int size;
int i;
INT ret = -1;
LPWSTR string[MAX_PATH];
PROPVALUE *pv;
pv = malloc(100*sizeof(PROPVALUE));
PROPERTY_EnumPropEx(hwnd, pv ,100, &size );
for (i=0;i<size;i++)
{
/* Already get the next in case the callback */
/* function removes the current property. */
next = prop->next;
GlobalFindAtomNameW(pv[i]->atom,string,MAX_PATH-1);
ret = func( hwnd, string, pv[i]->handle);
if (!ret)
break;
}
free(pv);
return ret;
}
/***********************************************************************
* EnumPropsExA (USER.187)
*/
INT STDCALL EnumPropsExA(HWND hwnd, PROPENUMPROCEXA func, LPARAM lParam)
{
int size;
int i;
INT ret = -1;
LPWSTR string[MAX_PATH];
PROPVALUE *pv;
pv = malloc(100*sizeof(PROPVALUE));
PROPERTY_EnumPropEx(hwnd, pv ,100, &size );
for (i=0;i<size;i++)
{
/* Already get the next in case the callback */
/* function removes the current property. */
next = prop->next;
GlobalFindAtomNameW(pv[i]->atom,string,MAX_PATH-1);
ret = func( hwnd, string, pv[i]->handle, lParam);
if (!ret)
break;
}
free(pv);
return ret;
}
/***********************************************************************
* EnumPropsExW (USER.188)
*/
INT STDCALL EnumPropsExW(HWND hwnd, PROPENUMPROCEXW func, LPARAM lParam)
{
int size;
int i;
INT ret = -1;
LPWSTR string[MAX_PATH];
PROPVALUE *pv;
pv = malloc(100*sizeof(PROPVALUE));
PROPERTY_EnumPropEx(hwnd, pv ,100, &size );
for (i=0;i<size;i++)
{
/* Already get the next in case the callback */
/* function removes the current property. */
next = prop->next;
GlobalFindAtomNameW(pv[i]->atom,string,MAX_PATH-1);
ret = func( hwnd, string, pv[i]->handle, lParam);
if (!ret)
break;
}
free(pv);
return ret;
}
#endif

View File

@@ -0,0 +1,5 @@
#include <windows.h>
#include <user32/queue.h>

View File

@@ -0,0 +1,63 @@
#include <windows.h>
#include <user32/nc.h>
WINBOOL
STDCALL
AdjustWindowRect( LPRECT lpRect, DWORD dwStyle, WINBOOL bMenu )
{
return AdjustWindowRectEx( lpRect, dwStyle, bMenu, 0 );
}
WINBOOL
STDCALL AdjustWindowRectEx(LPRECT lpRect, DWORD dwStyle, WINBOOL bMenu, DWORD dwExStyle)
{
/* Correct the window style */
if (!(dwStyle & (WS_POPUP | WS_CHILD))) /* Overlapped window */
dwStyle |= WS_CAPTION;
dwStyle &= (WS_DLGFRAME | WS_BORDER | WS_THICKFRAME | WS_CHILD);
dwExStyle &= (WS_EX_DLGMODALFRAME | WS_EX_CLIENTEDGE |
WS_EX_STATICEDGE | WS_EX_TOOLWINDOW);
if (dwExStyle & WS_EX_DLGMODALFRAME) dwStyle &= ~WS_THICKFRAME;
if (TWEAK_WineLook == WIN31_LOOK)
NC_AdjustRect( lpRect, dwStyle, bMenu, dwExStyle );
else {
NC_AdjustRectOuter95( lpRect, dwStyle, bMenu, dwExStyle );
NC_AdjustRectInner95( lpRect, dwStyle, dwExStyle );
}
return TRUE;
}
WINBOOL STDCALL GetWindowRect( HWND hwnd, LPRECT rect )
{
WND * wndPtr = WIN_FindWndPtr( hwnd );
if (!wndPtr) return FALSE;
*rect = wndPtr->rectWindow;
if (wndPtr->dwStyle & WS_CHILD)
MapWindowPoints( wndPtr->parent->hwndSelf, 0, (POINT *)rect, 2 );
return TRUE;
}
WINBOOL
STDCALL
GetClientRect(HWND hWnd, LPRECT lpRect)
{
WND * wndPtr = WIN_FindWndPtr( hWnd );
if ( wndPtr == NULL || lpRect == NULL )
return FALSE;
lpRect->left = lpRect->top = lpRect->right = lpRect->bottom = 0;
if (wndPtr)
{
lpRect->right = wndPtr->rectClient.right - wndPtr->rectClient.left;
lpRect->bottom = wndPtr->rectClient.bottom - wndPtr->rectClient.top;
}
return TRUE;
}

View File

@@ -6,4 +6,8 @@ int SPY_EnterMessage( UINT id, HWND hwnd, UINT msg, WPARAM wParam,LPARAM lParam
int SPY_ExitMessage( UINT id, HWND hwnd, UINT msg, LRESULT res )
{
}
const char *SPY_GetMsgName( UINT msg )
{
}

View File

@@ -0,0 +1,13 @@
#include <windows.h>
UINT SetTimer( HWND hWnd,UINT nIDEvent,
UINT uElapse, TIMERPROC lpTimerFunc
)
{
return 0;
}
WINBOOL STDCALL KillTimer(HWND hWnd, UINT uIDEvent )
{
return FALSE;
}

View File

@@ -1,22 +1,681 @@
#include <windows.h>
#include <user32/win.h>
#include <user32/class.h>
#include <user32/menu.h>
#include <user32/winpos.h>
#include <user32/hook.h>
#include <user32/property.h>
#include <user32/debug.h>
#undef CreateWindowA
HWND STDCALL CreateWindowA(LPCSTR lpClassName, LPCSTR lpWindowName,
DWORD dwStyle,int x, int y,
int nWidth, int nHeight, HWND hWndParent,
HMENU hMenu, HANDLE hInstance,
LPVOID lpParam )
{
return CreateWindowExA( 0, lpClassName, lpWindowName, dwStyle,x, y, nWidth, nHeight, hWndParent, hMenu, hInstance, lpParam );
}
#undef CreateWindowW
HWND STDCALL CreateWindowW(LPCWSTR lpClassName, LPCWSTR lpWindowName,
DWORD dwStyle,int x, int y,
int nWidth, int nHeight, HWND hWndParent,
HMENU hMenu, HANDLE hInstance,
LPVOID lpParam )
{
return CreateWindowExW( 0, lpClassName, lpWindowName, dwStyle, x, y, nWidth, nHeight, hWndParent, hMenu, hInstance, lpParam );
}
HWND STDCALL CreateWindowExA( DWORD exStyle, LPCSTR lpClassName,
LPCSTR lpWindowName, DWORD style, INT x,
INT y, INT width, INT height,
HWND parent, HMENU menu,
HINSTANCE hInstance, LPVOID data )
{
CREATESTRUCTW cs;
CLASS *p;
DWORD status;
// int i;
p = CLASS_FindClassByAtom( STRING2ATOMA(lpClassName), hInstance );
if ( p == NULL )
return NULL;
//if(exStyle & WS_EX_MDICHILD)
// return MDI_CreateMDIWindowA(className, windowName, style, x, y, width, height, parent, instance, data);
#if 0
while ((*lpWindowName)!=0 && i < MAX_PATH)
{
WindowNameW[i] = *lpWindowName;
lpWindowName++;
i++;
}
WindowNameW[i] = 0;
#endif
/* Create the window */
cs.lpCreateParams = data;
cs.hInstance = hInstance;
cs.hMenu = menu;
cs.hWndParent = parent;
cs.x = x;
cs.y = y;
cs.cx = width;
cs.cy = height;
cs.style = style;
cs.lpszName = (LPWSTR)lpWindowName;
cs.dwExStyle = exStyle;
return WIN_CreateWindowEx( &cs, p->atomName );
}
HWND STDCALL CreateWindowExW( DWORD exStyle, LPCWSTR lpClassName,
LPCWSTR windowName, DWORD style, INT x,
INT y, INT width, INT height,
HWND parent, HMENU menu,
HINSTANCE hInstance, LPVOID data )
{
// WCHAR WindowNameW[MAX_PATH];
// WCHAR ClassNameW[MAX_PATH];
CLASS *p;
DWORD status;
CREATESTRUCTW cs;
p = CLASS_FindClassByAtom( STRING2ATOMW(lpClassName), hInstance );
if ( p == NULL )
return NULL;
/* Create the window */
cs.lpCreateParams = data;
cs.hInstance = hInstance;
cs.hMenu = menu;
cs.hWndParent = parent;
cs.x = x;
cs.y = y;
cs.cx = width;
cs.cy = height;
cs.style = style;
cs.lpszName = windowName;
cs.lpszClass = p->className;
cs.dwExStyle = exStyle;
return WIN_CreateWindowEx( &cs, p->atomName );
}
/***********************************************************************
* DestroyWindow (USER.135)
*/
WINBOOL STDCALL DestroyWindow( HWND hwnd )
{
WND * wndPtr;
DPRINT( "(%04x)\n", hwnd);
/* Initialization */
if (!(wndPtr = WIN_FindWndPtr( hwnd ))) return FALSE;
//if (wndPtr == pWndDesktop) return FALSE; /* Can't destroy desktop */
/* Call hooks */
if( HOOK_CallHooksA( WH_CBT, HCBT_DESTROYWND, hwnd, 0L) )
return FALSE;
if (!(wndPtr->dwStyle & WS_CHILD) && !wndPtr->owner)
{
HOOK_CallHooksA( WH_SHELL, HSHELL_WINDOWDESTROYED, hwnd, 0L );
/* FIXME: clean up palette - see "Internals" p.352 */
}
if( !QUEUE_IsExitingQueue(wndPtr->hmemTaskQ) )
if( wndPtr->dwStyle & WS_CHILD && !(wndPtr->dwExStyle & WS_EX_NOPARENTNOTIFY) )
{
/* Notify the parent window only */
SendMessageA( wndPtr->parent->hwndSelf, WM_PARENTNOTIFY,
MAKEWPARAM(WM_DESTROY, wndPtr->wIDmenu), (LPARAM)hwnd );
if( !IsWindow(hwnd) ) return TRUE;
}
// CLIPBOARD_GetDriver()->pResetOwner( wndPtr, FALSE ); /* before the window is unmapped */
/* Hide the window */
if (wndPtr->dwStyle & WS_VISIBLE)
{
SetWindowPos( hwnd, 0, 0, 0, 0, 0, SWP_HIDEWINDOW |
SWP_NOACTIVATE|SWP_NOZORDER|SWP_NOMOVE|SWP_NOSIZE|
((QUEUE_IsExitingQueue(wndPtr->hmemTaskQ))?SWP_DEFERERASE:0) );
if (!IsWindow(hwnd)) return TRUE;
}
/* Recursively destroy owned windows */
if( !(wndPtr->dwStyle & WS_CHILD) )
{
/* make sure top menu popup doesn't get destroyed */
MENU_PatchResidentPopup( (HQUEUE)0xFFFF, wndPtr );
for (;;)
{
WND *siblingPtr = wndPtr->parent->child; /* First sibling */
while (siblingPtr)
{
if (siblingPtr->owner == wndPtr)
{
if (siblingPtr->hmemTaskQ == wndPtr->hmemTaskQ)
break;
else
siblingPtr->owner = NULL;
}
siblingPtr = siblingPtr->next;
}
if (siblingPtr) DestroyWindow( siblingPtr->hwndSelf );
else break;
}
// !Options.managed ||
if( EVENT_CheckFocus() )
WINPOS_ActivateOtherWindow(wndPtr);
if( wndPtr->owner &&
wndPtr->owner->hwndLastActive == wndPtr->hwndSelf )
wndPtr->owner->hwndLastActive = wndPtr->owner->hwndSelf;
}
/* Send destroy messages */
WIN_SendDestroyMsg( wndPtr );
if (!IsWindow(hwnd)) return TRUE;
/* Unlink now so we won't bother with the children later on */
if( wndPtr->parent ) WIN_UnlinkWindow(hwnd);
/* Destroy the window storage */
WIN_DestroyWindow( wndPtr );
return TRUE;
}
/*******************************************************************
* EnableWindow
*/
WINBOOL STDCALL EnableWindow( HWND hWnd, WINBOOL enable )
{
WND *wndPtr;
if (!(wndPtr = WIN_FindWndPtr( hWnd ))) return FALSE;
if (enable && (wndPtr->dwStyle & WS_DISABLED))
{
/* Enable window */
wndPtr->dwStyle &= ~WS_DISABLED;
SendMessageA( hWnd, WM_ENABLE, TRUE, 0 );
return TRUE;
}
else if (!enable && !(wndPtr->dwStyle & WS_DISABLED))
{
/* Disable window */
wndPtr->dwStyle |= WS_DISABLED;
if ((hWnd == GetFocus()) || IsChild( hWnd, GetFocus() ))
SetFocus( 0 ); /* A disabled window can't have the focus */
if ((hWnd == GetCapture()) || IsChild( hWnd, GetCapture() ))
ReleaseCapture(); /* A disabled window can't capture the mouse */
SendMessageA( hWnd, WM_ENABLE, FALSE, 0 );
return FALSE;
}
return ((wndPtr->dwStyle & WS_DISABLED) != 0);
}
HWND STDCALL GetDesktopWindow(VOID)
{
return NULL;
}
HWND STDCALL GetWindow( HWND hwnd, UINT rel )
{
WND * wndPtr = WIN_FindWndPtr( hwnd );
if (!wndPtr) return 0;
switch(rel)
{
case GW_HWNDFIRST:
if (wndPtr->parent) return wndPtr->parent->child->hwndSelf;
else return 0;
case GW_HWNDLAST:
if (!wndPtr->parent) return 0; /* Desktop window */
while (wndPtr->next) wndPtr = wndPtr->next;
return wndPtr->hwndSelf;
case GW_HWNDNEXT:
if (!wndPtr->next) return 0;
return wndPtr->next->hwndSelf;
case GW_HWNDPREV:
if (!wndPtr->parent) return 0; /* Desktop window */
wndPtr = wndPtr->parent->child; /* First sibling */
if (wndPtr->hwndSelf == hwnd) return 0; /* First in list */
while (wndPtr->next)
{
if (wndPtr->next->hwndSelf == hwnd) return wndPtr->hwndSelf;
wndPtr = wndPtr->next;
}
return 0;
case GW_OWNER:
return wndPtr->owner ? wndPtr->owner->hwndSelf : 0;
case GW_CHILD:
return wndPtr->child ? wndPtr->child->hwndSelf : 0;
}
return 0;
}
WORD STDCALL SetWindowWord( HWND hwnd, INT offset, WORD newval )
{
WORD *ptr, retval;
WND * wndPtr = WIN_FindWndPtr( hwnd );
if (!wndPtr) return 0;
if (offset >= 0)
{
if (offset + sizeof(WORD) > wndPtr->class->cbWndExtra)
{
DPRINT( "Invalid offset %d\n", offset );
return 0;
}
ptr = (WORD *)(((char *)wndPtr->wExtra) + offset);
}
else switch(offset)
{
case GWW_ID: ptr = (WORD *)&wndPtr->wIDmenu; break;
case GWW_HINSTANCE: ptr = (WORD *)&wndPtr->hInstance; break;
case GWW_HWNDPARENT: return SetParent( hwnd, newval );
default:
DPRINT("Invalid offset %d\n", offset );
return 0;
}
retval = *ptr;
*ptr = newval;
return retval;
}
LONG STDCALL GetWindowLongA( HWND hwnd, INT offset )
{
return WIN_GetWindowLong( hwnd, offset );
}
LONG STDCALL GetWindowLongW( HWND hwnd, INT offset )
{
return WIN_GetWindowLong( hwnd, offset );
}
/**********************************************************************
* SetWindowLongW (USER.518) Set window attribute
*
* SetWindowLong() alters one of a window's attributes or sets a -bit (long)
* value in a window's extra memory.
*
* The _hwnd_ parameter specifies the window. is the handle to a
* window that has extra memory. The _newval_ parameter contains the
* new attribute or extra memory value. If positive, the _offset_
* parameter is the byte-addressed location in the window's extra
* memory to set. If negative, _offset_ specifies the window
* attribute to set, and should be one of the following values:
*
* GWL_EXSTYLE The window's extended window style
*
* GWL_STYLE The window's window style.
*
* GWL_WNDPROC Pointer to the window's window procedure.
*
* GWL_HINSTANCE The window's pplication instance handle.
*
* GWL_ID The window's identifier.
*
* GWL_USERDATA The window's user-specified data.
*
* If the window is a dialog box, the _offset_ parameter can be one of
* the following values:
*
* DWL_DLGPROC The address of the window's dialog box procedure.
*
* DWL_MSGRESULT The return value of a message
* that the dialog box procedure processed.
*
* DWL_USER Application specific information.
*
* RETURNS
*
* If successful, returns the previous value located at _offset_. Otherwise,
* returns 0.
*
* NOTES
*
* Extra memory for a window class is specified by a nonzero cbWndExtra
* parameter of the WNDCLASS structure passed to RegisterClass() at the
* time of class creation.
*
* Using GWL_WNDPROC to set a new window procedure effectively creates
* a window subclass. Use CallWindowProc() in the new windows procedure
* to pass messages to the superclass's window procedure.
*
* The user data is reserved for use by the application which created
* the window.
*
* Do not use GWL_STYLE to change the window's WS_DISABLE style;
* instead, call the EnableWindow() function to change the window's
* disabled state.
*
* Do not use GWL_HWNDPARENT to reset the window's parent, use
* SetParent() instead.
*
* Win95:
* When offset is GWL_STYLE and the calling app's ver is 4.0,
* it sends WM_STYLECHANGING before changing the settings
* and WM_STYLECHANGED afterwards.
* App ver 4.0 can't use SetWindowLong to change WS_EX_TOPMOST.
*
* BUGS
*
* GWL_STYLE does not dispatch WM_STYLE... messages.
*
* CONFORMANCE
*
* ECMA-234, Win
*
*/
LONG STDCALL SetWindowLongA( HWND hwnd, INT offset, LONG newval )
{
return WIN_SetWindowLong( hwnd, offset, newval );
}
LONG STDCALL SetWindowLongW(
HWND hwnd,
INT offset,
LONG newval
) {
return WIN_SetWindowLong( hwnd, offset, newval );
}
HWND STDCALL GetTopWindow( HWND hwnd )
{
WND * wndPtr = WIN_FindWndPtr( hwnd );
if (wndPtr && wndPtr->child) return wndPtr->child->hwndSelf;
else return 0;
}
HWND STDCALL GetNextWindow( HWND hwnd, UINT flag )
{
if ((flag != GW_HWNDNEXT) && (flag != GW_HWNDPREV)) return 0;
return GetWindow( hwnd, flag );
}
/*****************************************************************
* GetParent (USER.278)
*/
HWND STDCALL GetParent( HWND hwnd )
{
WND *wndPtr = WIN_FindWndPtr(hwnd);
if ((!wndPtr) || (!(wndPtr->dwStyle & (WS_POPUP|WS_CHILD)))) return 0;
wndPtr = (wndPtr->dwStyle & WS_CHILD) ? wndPtr->parent : wndPtr->owner;
return wndPtr ? wndPtr->hwndSelf : NULL;
}
/*****************************************************************
* SetParent (USER.495)
*/
HWND STDCALL SetParent( HWND hWndChild, HWND hWndNewParent )
{
WND *wndPtr = WIN_FindWndPtr( hWndChild );
WND *pWndNewParent =
(hWndNewParent) ? WIN_FindWndPtr( hWndNewParent ) : WIN_FindWndPtr(GetDesktopWindow());
WND *pWndOldParent;
// (wndPtr)?(*wndPtr->pDriver->pSetParent)(wndPtr, pWndNewParent):NULL;
return pWndOldParent?pWndOldParent->hwndSelf:NULL;
}
/*******************************************************************
* GetWindowTextA (USER.309)
*/
INT STDCALL GetWindowTextA( HWND hwnd, LPSTR lpString, INT nMaxCount )
{
return (INT)SendMessageA( hwnd, WM_GETTEXT, nMaxCount,
(LPARAM)lpString );
}
/*******************************************************************
* GetWindowTextW (USER.312)
*/
INT STDCALL GetWindowTextW( HWND hwnd, LPWSTR lpString, INT nMaxCount )
{
return (INT)SendMessageW( hwnd, WM_GETTEXT, nMaxCount,
(LPARAM)lpString );
}
WINBOOL STDCALL SetWindowTextA( HWND hwnd, LPCSTR lpString )
{
return (WINBOOL)SendMessageA( hwnd, WM_SETTEXT, 0, (LPARAM)lpString );
}
WINBOOL STDCALL SetWindowTextW( HWND hwnd, LPCWSTR lpString )
{
return (WINBOOL)SendMessageW( hwnd, WM_SETTEXT, 0, (LPARAM)lpString );
}
INT STDCALL GetWindowTextLengthA( HWND hwnd )
{
return SendMessageA( hwnd, WM_GETTEXTLENGTH, 0, 0 );
}
INT STDCALL GetWindowTextLengthW( HWND hwnd )
{
return SendMessageW( hwnd, WM_GETTEXTLENGTH, 0, 0 );
}
WINBOOL STDCALL IsChild( HWND parent, HWND child )
{
WND * wndPtr = WIN_FindWndPtr( child );
while (wndPtr && (wndPtr->dwStyle & WS_CHILD))
{
wndPtr = wndPtr->parent;
if (wndPtr->hwndSelf == parent) return TRUE;
}
return FALSE;
}
WINBOOL IsWindow(HANDLE hWnd)
{
{
if (WIN_FindWndPtr( hWnd ) == NULL) return FALSE;
return TRUE;
}
WND * WIN_FindWndPtr( HWND hwnd )
/***********************************************************************
* IsWindowEnabled
*/
WINBOOL STDCALL IsWindowEnabled(HWND hWnd)
{
return NULL;
WND * wndPtr;
if (!(wndPtr = WIN_FindWndPtr(hWnd))) return FALSE;
return !(wndPtr->dwStyle & WS_DISABLED);
}
WND* WIN_GetDesktop(void)
/***********************************************************************
* IsWindowUnicode
*/
WINBOOL STDCALL IsWindowUnicode( HWND hWnd )
{
return NULL;
WND * wndPtr;
// What if handle is invalid ??
if (!(wndPtr = WIN_FindWndPtr(hWnd)))
return FALSE;
return wndPtr->class->bUnicode;
}
WND **WIN_BuildWinArray( WND *wndPtr, UINT bwaFlags, UINT* pTotal )
WINBOOL STDCALL IsWindowVisible( HWND hwnd )
{
return NULL;
}
WND *wndPtr = WIN_FindWndPtr( hwnd );
while (wndPtr && (wndPtr->dwStyle & WS_CHILD))
{
if (!(wndPtr->dwStyle & WS_VISIBLE)) return FALSE;
wndPtr = wndPtr->parent;
}
return (wndPtr && (wndPtr->dwStyle & WS_VISIBLE));
}
/***********************************************************************
* ShowWindow32 (USER32.534)
*/
WINBOOL STDCALL ShowWindow( HWND hwnd, INT cmd )
{
WND* wndPtr = WIN_FindWndPtr( hwnd );
WINBOOL wasVisible, showFlag;
RECT newPos = {0, 0, 0, 0};
int swp = 0;
if (!wndPtr) return FALSE;
// DPRINT("hwnd=%04x, cmd=%d\n", hwnd, cmd);
wasVisible = (wndPtr->dwStyle & WS_VISIBLE) != 0;
switch(cmd)
{
case SW_HIDE:
if (!wasVisible) return FALSE;
swp |= SWP_HIDEWINDOW | SWP_NOSIZE | SWP_NOMOVE |
SWP_NOACTIVATE | SWP_NOZORDER;
break;
case SW_SHOWMINNOACTIVE:
swp |= SWP_NOACTIVATE | SWP_NOZORDER;
/* fall through */
case SW_SHOWMINIMIZED:
swp |= SWP_SHOWWINDOW;
/* fall through */
case SW_MINIMIZE:
swp |= SWP_FRAMECHANGED;
if( !(wndPtr->dwStyle & WS_MINIMIZE) )
swp |= WINPOS_MinMaximize( wndPtr, SW_MINIMIZE, &newPos );
else swp |= SWP_NOSIZE | SWP_NOMOVE;
break;
case SW_SHOWMAXIMIZED: /* same as SW_MAXIMIZE */
swp |= SWP_SHOWWINDOW | SWP_FRAMECHANGED;
if( !(wndPtr->dwStyle & WS_MAXIMIZE) )
swp |= WINPOS_MinMaximize( wndPtr, SW_MAXIMIZE, &newPos );
else swp |= SWP_NOSIZE | SWP_NOMOVE;
break;
case SW_SHOWNA:
swp |= SWP_NOACTIVATE | SWP_NOZORDER;
/* fall through */
case SW_SHOW:
swp |= SWP_SHOWWINDOW | SWP_NOSIZE | SWP_NOMOVE;
break;
case SW_SHOWNOACTIVATE:
swp |= SWP_NOZORDER;
if (GetActiveWindow()) swp |= SWP_NOACTIVATE;
/* fall through */
case SW_SHOWNORMAL: /* same as SW_NORMAL: */
case SW_SHOWDEFAULT: /* FIXME: should have its own handler */
case SW_RESTORE:
swp |= SWP_SHOWWINDOW | SWP_FRAMECHANGED;
if( wndPtr->dwStyle & (WS_MINIMIZE | WS_MAXIMIZE) )
swp |= WINPOS_MinMaximize( wndPtr, SW_RESTORE, &newPos );
else swp |= SWP_NOSIZE | SWP_NOMOVE;
break;
}
showFlag = (cmd != SW_HIDE);
if (showFlag != wasVisible)
{
SendMessageW( hwnd, WM_SHOWWINDOW, showFlag, 0 );
if (!IsWindow( hwnd )) return wasVisible;
}
if ((wndPtr->dwStyle & WS_CHILD) &&
!IsWindowVisible( wndPtr->parent->hwndSelf ) &&
(swp & (SWP_NOSIZE | SWP_NOMOVE)) == (SWP_NOSIZE | SWP_NOMOVE) )
{
/* Don't call SetWindowPos() on invisible child windows */
if (cmd == SW_HIDE) wndPtr->dwStyle &= ~WS_VISIBLE;
else wndPtr->dwStyle |= WS_VISIBLE;
}
else
{
/* We can't activate a child window */
if (wndPtr->dwStyle & WS_CHILD) swp |= SWP_NOACTIVATE | SWP_NOZORDER;
SetWindowPos( hwnd, HWND_TOP,
newPos.left, newPos.top, newPos.right, newPos.bottom, swp );
if (!IsWindow( hwnd )) return wasVisible;
else if( wndPtr->dwStyle & WS_MINIMIZE ) WINPOS_ShowIconTitle( wndPtr, TRUE );
}
if (wndPtr->flags & WIN_NEED_SIZE)
{
/* should happen only in CreateWindowEx() */
int wParam = SIZE_RESTORED;
wndPtr->flags &= ~WIN_NEED_SIZE;
if (wndPtr->dwStyle & WS_MAXIMIZE) wParam = SIZE_MAXIMIZED;
else if (wndPtr->dwStyle & WS_MINIMIZE) wParam = SIZE_MINIMIZED;
SendMessageW( hwnd, WM_SIZE, wParam,
MAKELONG(wndPtr->rectClient.right-wndPtr->rectClient.left,
wndPtr->rectClient.bottom-wndPtr->rectClient.top));
SendMessageW( hwnd, WM_MOVE, 0,
MAKELONG(wndPtr->rectClient.left, wndPtr->rectClient.top) );
}
return wasVisible;
}

File diff suppressed because it is too large Load Diff

View File

@@ -1,5 +1,10 @@
#include <windows.h>
#include <user32/win.h>
#include <user32/winproc.h>
//#include <user32/heapdup.h>
#define MDICREATESTRUCTA MDICREATESTRUCT
#define MDICREATESTRUCTW MDICREATESTRUCT
/**********************************************************************
@@ -34,6 +39,29 @@ LRESULT WINAPI CallWindowProcA(
LPARAM lParam
)
{
INT ret;
WND *w;
LRESULT l;
w = WIN_FindWndPtr( hwnd );
if ( w == NULL )
return 0;
if ( w->class->bUnicode == FALSE )
return func(hwnd,msg,wParam,lParam);
//convert message
ret = WINPROC_MapMsg32WTo32A( hwnd, msg, wParam, &lParam );
if ( ret == -1 )
return 0;
l = func(hwnd,msg,wParam,lParam);
if ( ret == 1 )
WINPROC_UnmapMsg32WTo32A( hwnd, msg, wParam, lParam );
return l;
}
LRESULT WINAPI CallWindowProcW(
@@ -44,6 +72,25 @@ LRESULT WINAPI CallWindowProcW(
LPARAM lParam
)
{
INT ret;
WND *w;
LRESULT l;
w = WIN_FindWndPtr( hwnd );
if ( w == NULL )
return 0;
if ( w->class->bUnicode == TRUE )
return func(hwnd,msg,wParam,lParam);
//convert message
ret = WINPROC_MapMsg32ATo32W( hwnd, msg, wParam, &lParam );
if ( ret == -1 )
return 0;
l = func(hwnd,msg,wParam,lParam);
if ( ret == 1 )
WINPROC_UnmapMsg32ATo32W( hwnd, msg, wParam, lParam );
return l;
}
/***********************************************************************
@@ -65,7 +112,7 @@ LRESULT WINAPI DefWindowProcA(
WPARAM wParam,
LPARAM lParam )
{
return 0;
}
@@ -75,7 +122,478 @@ LRESULT WINAPI DefWindowProcW(
WPARAM wParam,
LPARAM lParam )
{
return 0;
}
/**********************************************************************
* WINPROC_TestCBForStr
*
* Return TRUE if the lparam is a string
*/
WINBOOL WINPROC_TestCBForStr ( HWND hwnd )
{ WND * wnd = WIN_FindWndPtr(hwnd);
return ( !(LOWORD(wnd->dwStyle) & (CBS_OWNERDRAWFIXED | CBS_OWNERDRAWVARIABLE)) ||
(LOWORD(wnd->dwStyle) & CBS_HASSTRINGS) );
}
/**********************************************************************
* WINPROC_TestLBForStr
*
* Return TRUE if the lparam is a string
*/
WINBOOL WINPROC_TestLBForStr ( HWND hwnd )
{ WND * wnd = WIN_FindWndPtr(hwnd);
return ( !(LOWORD(wnd->dwStyle) & (LBS_OWNERDRAWFIXED | LBS_OWNERDRAWVARIABLE)) ||
(LOWORD(wnd->dwStyle) & LBS_HASSTRINGS) );
}
/**********************************************************************
* WINPROC_MapMsg32ATo32W
*
* Map a message from Ansi to Unicode.
* Return value is -1 on error, 0 if OK, 1 if an UnmapMsg call is needed.
*
* FIXME:
* WM_CHAR, WM_CHARTOITEM, WM_DEADCHAR, WM_MENUCHAR, WM_SYSCHAR, WM_SYSDEADCHAR
*
* FIXME:
* WM_GETTEXT/WM_SETTEXT and static control with SS_ICON style:
* the first four bytes are the handle of the icon
* when the WM_SETTEXT message has been used to set the icon
*/
INT WINPROC_MapMsg32ATo32W( HWND hwnd, UINT msg, WPARAM wParam, LPARAM *plparam )
{
switch(msg)
{
case WM_GETTEXT:
{
LPARAM *ptr = (LPARAM *)HeapAlloc( GetProcessHeap(), 0,
wParam * sizeof(WCHAR) + sizeof(LPARAM) );
if (!ptr)
return -1;
*ptr++ = *plparam; /* Store previous lParam */
*plparam = (LPARAM)ptr;
}
return 1;
case WM_SETTEXT:
case CB_DIR:
case CB_FINDSTRING:
case CB_FINDSTRINGEXACT:
case CB_SELECTSTRING:
case LB_DIR:
case LB_ADDFILE:
case LB_FINDSTRING:
case LB_SELECTSTRING:
case EM_REPLACESEL:
*plparam = (LPARAM)HEAP_strdupAtoW( GetProcessHeap(), 0, (LPCSTR)*plparam );
return (*plparam ? 1 : -1);
break;
case WM_NCCREATE:
case WM_CREATE:
{
CREATESTRUCTW *cs = (CREATESTRUCTW *)HeapAlloc( GetProcessHeap(), 0,
sizeof(*cs) );
if (!cs) return -1;
*cs = *(CREATESTRUCTW *)*plparam;
if (HIWORD(cs->lpszName))
cs->lpszName = HEAP_strdupAtoW( GetProcessHeap(), 0,
(LPCSTR)cs->lpszName );
if (HIWORD(cs->lpszClass))
cs->lpszClass = HEAP_strdupAtoW( GetProcessHeap(), 0,
(LPCSTR)cs->lpszClass );
*plparam = (LPARAM)cs;
}
return 1;
case WM_MDICREATE:
{
MDICREATESTRUCTW *cs = HeapAlloc( GetProcessHeap(), 0, sizeof(MDICREATESTRUCT) );
if (!cs) return -1;
*cs = *(MDICREATESTRUCT *)*plparam;
if (HIWORD(cs->szClass))
cs->szClass = HEAP_strdupAtoW( GetProcessHeap(), 0,
(LPCSTR)cs->szClass );
if (HIWORD(cs->szTitle))
cs->szTitle = HEAP_strdupAtoW( GetProcessHeap(), 0,
(LPCSTR)cs->szTitle );
*plparam = (LPARAM)cs;
}
return 1;
/* Listbox */
case LB_ADDSTRING:
case LB_INSERTSTRING:
if ( WINPROC_TestLBForStr( hwnd ))
*plparam = (LPARAM)HEAP_strdupAtoW( GetProcessHeap(), 0, (LPCSTR)*plparam );
return (*plparam ? 1 : -1);
case LB_GETTEXT: /* fixme: fixed sized buffer */
{ if ( WINPROC_TestLBForStr( hwnd ))
{ LPARAM *ptr = (LPARAM *)HeapAlloc( GetProcessHeap(), 0, 256 * sizeof(WCHAR) + sizeof(LPARAM) );
if (!ptr) return -1;
*ptr++ = *plparam; /* Store previous lParam */
*plparam = (LPARAM)ptr;
}
}
return 1;
/* Combobox */
case CB_ADDSTRING:
case CB_INSERTSTRING:
if ( WINPROC_TestCBForStr( hwnd ))
*plparam = (LPARAM)HEAP_strdupAtoW( GetProcessHeap(), 0, (LPCSTR)*plparam );
return (*plparam ? 1 : -1);
case CB_GETLBTEXT: /* fixme: fixed sized buffer */
{ if ( WINPROC_TestCBForStr( hwnd ))
{ LPARAM *ptr = (LPARAM *)HeapAlloc( GetProcessHeap(), 0, 256 * sizeof(WCHAR) + sizeof(LPARAM) );
if (!ptr) return -1;
*ptr++ = *plparam; /* Store previous lParam */
*plparam = (LPARAM)ptr;
}
}
return 1;
/* Multiline edit */
case EM_GETLINE:
{ WORD len = (WORD)*plparam;
LPARAM *ptr = (LPARAM *) HeapAlloc( GetProcessHeap(), 0, sizeof(LPARAM) + sizeof (WORD) + len*sizeof(WCHAR) );
if (!ptr) return -1;
*ptr++ = *plparam; /* Store previous lParam */
(WORD)*ptr = len; /* Store the lenght */
*plparam = (LPARAM)ptr;
}
return 1;
case WM_ASKCBFORMATNAME:
case WM_DEVMODECHANGE:
case WM_PAINTCLIPBOARD:
case WM_SIZECLIPBOARD:
case WM_WININICHANGE:
case EM_SETPASSWORDCHAR:
// FIXME(msg, "message %s (0x%x) needs translation, please report\n", SPY_GetMsgName(msg), msg );
return -1;
default: /* No translation needed */
return 0;
}
}
/**********************************************************************
* WINPROC_UnmapMsg32ATo32W
*
* Unmap a message that was mapped from Ansi to Unicode.
*/
void WINPROC_UnmapMsg32ATo32W( HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam )
{
switch(msg)
{
case WM_GETTEXT:
{
LPARAM *ptr = (LPARAM *)lParam - 1;
lstrcpynWtoA( (LPSTR)*ptr, (LPWSTR)lParam, wParam );
HeapFree( GetProcessHeap(), 0, ptr );
}
break;
case WM_NCCREATE:
case WM_CREATE:
{
CREATESTRUCTW *cs = (CREATESTRUCTW *)lParam;
if (HIWORD(cs->lpszName))
HeapFree( GetProcessHeap(), 0, (LPVOID)cs->lpszName );
if (HIWORD(cs->lpszClass))
HeapFree( GetProcessHeap(), 0, (LPVOID)cs->lpszClass );
HeapFree( GetProcessHeap(), 0, cs );
}
break;
case WM_MDICREATE:
{
MDICREATESTRUCTW *cs = (MDICREATESTRUCTW *)lParam;
if (HIWORD(cs->szTitle))
HeapFree( GetProcessHeap(), 0, (LPVOID)cs->szTitle );
if (HIWORD(cs->szClass))
HeapFree( GetProcessHeap(), 0, (LPVOID)cs->szClass );
HeapFree( GetProcessHeap(), 0, cs );
}
break;
case WM_SETTEXT:
case CB_DIR:
case CB_FINDSTRING:
case CB_FINDSTRINGEXACT:
case CB_SELECTSTRING:
case LB_DIR:
case LB_ADDFILE:
case LB_FINDSTRING:
case LB_SELECTSTRING:
case EM_REPLACESEL:
HeapFree( GetProcessHeap(), 0, (void *)lParam );
break;
/* Listbox */
case LB_ADDSTRING:
case LB_INSERTSTRING:
if ( WINPROC_TestLBForStr( hwnd ))
HeapFree( GetProcessHeap(), 0, (void *)lParam );
break;
case LB_GETTEXT:
{ if ( WINPROC_TestLBForStr( hwnd ))
{ LPARAM *ptr = (LPARAM *)lParam - 1;
lstrcpyWtoA( (LPSTR)*ptr, (LPWSTR)(lParam) );
HeapFree( GetProcessHeap(), 0, ptr );
}
}
break;
/* Combobox */
case CB_ADDSTRING:
case CB_INSERTSTRING:
if ( WINPROC_TestCBForStr( hwnd ))
HeapFree( GetProcessHeap(), 0, (void *)lParam );
break;
case CB_GETLBTEXT:
{ if ( WINPROC_TestCBForStr( hwnd ))
{ LPARAM *ptr = (LPARAM *)lParam - 1;
lstrcpyWtoA( (LPSTR)*ptr, (LPWSTR)(lParam) );
HeapFree( GetProcessHeap(), 0, ptr );
}
}
break;
/* Multiline edit */
case EM_GETLINE:
{ LPARAM *ptr = (LPARAM *)lParam - 1; /* get the old lParam */
WORD len = *(WORD *)ptr;
lstrcpynWtoA( ((LPSTR)*ptr)+2, ((LPWSTR)(lParam + 1))+1, len );
HeapFree( GetProcessHeap(), 0, ptr );
}
break;
}
}
/**********************************************************************
* WINPROC_MapMsg32WTo32A
*
* Map a message from Unicode to Ansi.
* Return value is -1 on error, 0 if OK, 1 if an UnmapMsg call is needed.
*/
INT WINPROC_MapMsg32WTo32A( HWND hwnd, UINT msg, WPARAM wParam, LPARAM *plparam )
{ switch(msg)
{
case WM_GETTEXT:
{
LPARAM *ptr = (LPARAM *)HeapAlloc( GetProcessHeap(), 0,
wParam + sizeof(LPARAM) );
if (!ptr) return -1;
*ptr++ = *plparam; /* Store previous lParam */
*plparam = (LPARAM)ptr;
}
return 1;
case WM_SETTEXT:
case CB_DIR:
case CB_FINDSTRING:
case CB_FINDSTRINGEXACT:
case CB_SELECTSTRING:
case LB_DIR:
case LB_ADDFILE:
case LB_FINDSTRING:
case LB_SELECTSTRING:
case EM_REPLACESEL:
*plparam = (LPARAM)HEAP_strdupWtoA( GetProcessHeap(), 0, (LPCWSTR)*plparam );
return (*plparam ? 1 : -1);
case WM_NCCREATE:
case WM_CREATE:
{
CREATESTRUCTA *cs = (CREATESTRUCTA *)HeapAlloc( GetProcessHeap(), 0,
sizeof(*cs) );
if (!cs) return -1;
*cs = *(CREATESTRUCTA *)*plparam;
if (HIWORD(cs->lpszName))
cs->lpszName = HEAP_strdupWtoA( GetProcessHeap(), 0,
(LPCWSTR)cs->lpszName );
if (HIWORD(cs->lpszClass))
cs->lpszClass = HEAP_strdupWtoA( GetProcessHeap(), 0,
(LPCWSTR)cs->lpszClass);
*plparam = (LPARAM)cs;
}
return 1;
case WM_MDICREATE:
{
MDICREATESTRUCTA *cs =
(MDICREATESTRUCTA *)HeapAlloc( GetProcessHeap(), 0, sizeof(*cs) );
if (!cs) return -1;
*cs = *(MDICREATESTRUCTA *)*plparam;
if (HIWORD(cs->szTitle))
cs->szTitle = HEAP_strdupWtoA( GetProcessHeap(), 0,
(LPCWSTR)cs->szTitle );
if (HIWORD(cs->szClass))
cs->szClass = HEAP_strdupWtoA( GetProcessHeap(), 0,
(LPCWSTR)cs->szClass );
*plparam = (LPARAM)cs;
}
return 1;
/* Listbox */
case LB_ADDSTRING:
case LB_INSERTSTRING:
if ( WINPROC_TestLBForStr( hwnd ))
*plparam = (LPARAM)HEAP_strdupWtoA( GetProcessHeap(), 0, (LPCWSTR)*plparam );
return (*plparam ? 1 : -1);
case LB_GETTEXT: /* fixme: fixed sized buffer */
{ if ( WINPROC_TestLBForStr( hwnd ))
{ LPARAM *ptr = (LPARAM *)HeapAlloc( GetProcessHeap(), 0, 256 + sizeof(LPARAM) );
if (!ptr) return -1;
*ptr++ = *plparam; /* Store previous lParam */
*plparam = (LPARAM)ptr;
}
}
return 1;
/* Combobox */
case CB_ADDSTRING:
case CB_INSERTSTRING:
if ( WINPROC_TestCBForStr( hwnd ))
*plparam = (LPARAM)HEAP_strdupWtoA( GetProcessHeap(), 0, (LPCWSTR)*plparam );
return (*plparam ? 1 : -1);
case CB_GETLBTEXT: /* fixme: fixed sized buffer */
{ if ( WINPROC_TestCBForStr( hwnd ))
{ LPARAM *ptr = (LPARAM *)HeapAlloc( GetProcessHeap(), 0, 256 + sizeof(LPARAM) );
if (!ptr) return -1;
*ptr++ = *plparam; /* Store previous lParam */
*plparam = (LPARAM)ptr;
}
}
return 1;
/* Multiline edit */
case EM_GETLINE:
{ WORD len = (WORD)*plparam;
LPARAM *ptr = (LPARAM *) HeapAlloc( GetProcessHeap(), 0, sizeof(LPARAM) + sizeof (WORD) + len*sizeof(CHAR) );
if (!ptr) return -1;
*ptr++ = *plparam; /* Store previous lParam */
(WORD)*ptr = len; /* Store the lenght */
*plparam = (LPARAM)ptr;
}
return 1;
case WM_ASKCBFORMATNAME:
case WM_DEVMODECHANGE:
case WM_PAINTCLIPBOARD:
case WM_SIZECLIPBOARD:
case WM_WININICHANGE:
case EM_SETPASSWORDCHAR:
// FIXME(msg, "message %s (%04x) needs translation, please report\n",SPY_GetMsgName(msg),msg );
return -1;
default: /* No translation needed */
return 0;
}
}
/**********************************************************************
* WINPROC_UnmapMsg32WTo32A
*
* Unmap a message that was mapped from Unicode to Ansi.
*/
void WINPROC_UnmapMsg32WTo32A( HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam )
{
switch(msg)
{
case WM_GETTEXT:
{
LPARAM *ptr = (LPARAM *)lParam - 1;
lstrcpynAtoW( (LPWSTR)*ptr, (LPSTR)lParam, wParam );
HeapFree( GetProcessHeap(), 0, ptr );
}
break;
case WM_SETTEXT:
case CB_DIR:
case CB_FINDSTRING:
case CB_FINDSTRINGEXACT:
case CB_SELECTSTRING:
case LB_DIR:
case LB_ADDFILE:
case LB_FINDSTRING:
case LB_SELECTSTRING:
case EM_REPLACESEL:
HeapFree( GetProcessHeap(), 0, (void *)lParam );
break;
case WM_NCCREATE:
case WM_CREATE:
{
CREATESTRUCTA *cs = (CREATESTRUCTA *)lParam;
if (HIWORD(cs->lpszName))
HeapFree( GetProcessHeap(), 0, (LPVOID)cs->lpszName );
if (HIWORD(cs->lpszClass))
HeapFree( GetProcessHeap(), 0, (LPVOID)cs->lpszClass );
HeapFree( GetProcessHeap(), 0, cs );
}
break;
case WM_MDICREATE:
{
MDICREATESTRUCTA *cs = (MDICREATESTRUCTA *)lParam;
if (HIWORD(cs->szTitle))
HeapFree( GetProcessHeap(), 0, (LPVOID)cs->szTitle );
if (HIWORD(cs->szClass))
HeapFree( GetProcessHeap(), 0, (LPVOID)cs->szClass );
HeapFree( GetProcessHeap(), 0, cs );
}
break;
/* Listbox */
case LB_ADDSTRING:
case LB_INSERTSTRING:
if ( WINPROC_TestLBForStr( hwnd ))
HeapFree( GetProcessHeap(), 0, (void *)lParam );
break;
case LB_GETTEXT:
{ if ( WINPROC_TestLBForStr( hwnd ))
{ LPARAM *ptr = (LPARAM *)lParam - 1;
lstrcpyAtoW( (LPWSTR)*ptr, (LPSTR)(lParam) );
HeapFree( GetProcessHeap(), 0, ptr );
}
}
break;
/* Combobox */
case CB_ADDSTRING:
case CB_INSERTSTRING:
if ( WINPROC_TestCBForStr( hwnd ))
HeapFree( GetProcessHeap(), 0, (void *)lParam );
break;
case CB_GETLBTEXT:
{ if ( WINPROC_TestCBForStr( hwnd ))
{ LPARAM *ptr = (LPARAM *)lParam - 1;
lstrcpyAtoW( (LPWSTR)*ptr, (LPSTR)(lParam) );
HeapFree( GetProcessHeap(), 0, ptr );
}
}
break;
/* Multiline edit */
case EM_GETLINE:
{ LPARAM *ptr = (LPARAM *)lParam - 1; /* get the old lParam */
WORD len = *(WORD *)ptr;
lstrcpynAtoW( ((LPWSTR)*ptr)+1, ((LPSTR)(lParam + 1))+2, len );
HeapFree( GetProcessHeap(), 0, ptr );
}
break;
}
}