static Ihandle* winContainerWmCommandGetIhandle(Ihandle *ih, WPARAM wp, LPARAM lp) { /* WPARAM - if HIWORD is 0 if the message is from a menu. or HIWORD is 1 if the message is from an accelerator. or HIWORD is the notification code if the message is from a control. LOWORD is the identifier. LPARAM - the control sending the message or 0. */ Ihandle *child = NULL; if (HIWORD(wp)==0 && lp==0 && LOWORD(wp)>10) { Ihandle* dlg_menu = IupGetAttributeHandle(ih, "MENU"); if (dlg_menu) child = iupwinMenuGetItemHandle((HMENU)dlg_menu->handle, LOWORD(wp)); /* menu */ } else { if (lp==0) child = ih; /* native parent */ else { child = iupwinHandleGet((HWND)lp); /* control */ if (!child) child = iupwinHandleGet(GetParent((HWND)lp)); /* control */ } } return child; }
LRESULT CALLBACK iupwinBaseWndProc(HWND hwnd, UINT msg, WPARAM wp, LPARAM lp) { int ret; LRESULT result = 0; IwinMsgProc MsgProc; Ihandle *ih; ih = iupwinHandleGet(hwnd); if (!ih) return DefWindowProc(hwnd, msg, wp, lp); /* should never happen */ /* check if the element defines a custom procedure */ MsgProc = (IwinMsgProc)IupGetCallback(ih, "_IUPWIN_CTRLMSGPROC_CB"); if (MsgProc) ret = MsgProc(ih, msg, wp, lp, &result); else ret = iupwinBaseMsgProc(ih, msg, wp, lp, &result); if (ret) return result; else { /* retrieve the control previous procedure for subclassing */ WNDPROC oldProc = (WNDPROC)IupGetCallback(ih, "_IUPWIN_OLDWNDPROC_CB"); return CallWindowProc(oldProc, hwnd, msg, wp, lp); } }
void iupwinTipsGetDispInfo(LPARAM lp) { Ihandle* ih; HWND tips_hwnd; NMTTDISPINFO* tips_info; IFnii cb; if (!lp) return; tips_info = (NMTTDISPINFO*)lp; ih = iupwinHandleGet(tips_info->hdr.hwndFrom); /* hwndFrom is the tooltip window */ if (!ih) return; tips_hwnd = (HWND)iupAttribGet(ih, "_IUPWIN_TIPSWIN"); if (tips_hwnd != tips_info->hdr.hwndFrom) return; tips_info->hinst = NULL; cb = (IFnii)IupGetCallback(ih, "TIPS_CB"); if (cb) { int x, y; iupdrvGetCursorPos(&x, &y); iupdrvScreenToClient(ih, &x, &y); cb(ih, x, y); } tips_info->lpszText = iupwinStrToSystem(iupAttribGet(ih, "TIP")); iupwinTipsUpdateInfo(ih, tips_hwnd); }
static char* winDialogGetMdiNextAttrib(Ihandle *ih) { Ihandle* client = (Ihandle*)iupAttribGet(ih, "MDICLIENT_HANDLE"); if (client) { Ihandle* child; HWND hchild = iupwin_mdinext? iupwin_mdinext: iupwin_mdifirst; /* Skip the icon title windows */ while (hchild && GetWindow (hchild, GW_OWNER)) hchild = GetWindow(hchild, GW_HWNDNEXT); if (!hchild || hchild == iupwin_mdifirst) { iupwin_mdinext = NULL; return NULL; } child = iupwinHandleGet(hchild); if (child) { iupwin_mdinext = hchild; return IupGetName(child); } } iupwin_mdinext = NULL; return NULL; }
static int winDialogMDICloseChildren(Ihandle* ih) { Ihandle* client = (Ihandle*)iupAttribGet(ih, "MDICLIENT_HANDLE"); if (iupObjectCheck(client)) { HWND hWndChild = (HWND)SendMessage(client->handle, WM_MDIGETACTIVE, 0, 0); /* As long as the MDI client has a child, close it */ while (hWndChild) { Ihandle* child = iupwinHandleGet(hWndChild); if (iupObjectCheck(child) && iupAttribGetBoolean(child, "MDICHILD")) { Icallback cb = IupGetCallback(child, "CLOSE_CB"); if (cb) { int ret = cb(child); if (ret == IUP_IGNORE) return 0; if (ret == IUP_CLOSE) IupExitLoop(); } IupDestroy(child); } hWndChild = (HWND)SendMessage(client->handle, WM_MDIGETACTIVE, 0, 0); } } return 1; }
static LRESULT CALLBACK winTabsPageWinProc(HWND hWnd, UINT msg, WPARAM wp, LPARAM lp) { switch (msg) { case WM_ERASEBKGND: { RECT rect; HDC hDC = (HDC)wp; Ihandle* ih = iupwinHandleGet(hWnd); GetClientRect(ih->handle, &rect); winTabsDrawPageBackground(ih, hDC, &rect); /* return non zero value */ return 1; } case WM_COMMAND: case WM_CTLCOLORSCROLLBAR: case WM_CTLCOLORBTN: case WM_CTLCOLOREDIT: case WM_CTLCOLORLISTBOX: case WM_CTLCOLORSTATIC: case WM_DRAWITEM: case WM_HSCROLL: case WM_NOTIFY: case WM_VSCROLL: /* Forward the container messages to its parent. */ return SendMessage(GetParent(hWnd), msg, wp, lp); } return DefWindowProc(hWnd, msg, wp, lp); }
static LRESULT CALLBACK winDialogMDIChildProc(HWND hwnd, UINT msg, WPARAM wp, LPARAM lp) { LRESULT result; Ihandle *ih = iupwinHandleGet(hwnd); if (!ih) { /* the first time WM_GETMINMAXINFO is called, Ihandle is not associated yet */ if (msg == WM_GETMINMAXINFO && winMinMaxHandle) { if (winDialogCheckMinMaxInfo(winMinMaxHandle, (MINMAXINFO*)lp)) return 0; } return DefMDIChildProc(hwnd, msg, wp, lp); } if (msg == WM_MDIACTIVATE) { HWND hNewActive = (HWND)lp; if (hNewActive == ih->handle) { Icallback cb = (Icallback)IupGetCallback(ih, "MDIACTIVATE_CB"); if (cb) cb(ih); } } if (winDialogBaseProc(ih, msg, wp, lp, &result)) return result; return DefMDIChildProc(hwnd, msg, wp, lp); }
LRESULT CALLBACK iupwinToggleProc (HWND hwnd, UINT msg, WPARAM wp, LPARAM lp) { Ihandle *n; WNDPROC oldproc = NULL; n = iupwinHandleGet(hwnd); if(n == NULL) return DefWindowProc(hwnd, msg, wp, lp); oldproc = (WNDPROC) IupGetAttribute(n, "_IUPWIN_TOGGLEOLDPROC__"); /* we call our own proc to avoid the default proc */ switch (msg) { case WM_MOUSEACTIVATE: if(winToggleInactive(n)) return MA_NOACTIVATEANDEAT; break; case WM_ACTIVATE: case WM_SETFOCUS: case BM_CLICK: case BM_SETSTATE: case BN_CLICKED: case BN_DBLCLK: case WM_KEYUP: if(winToggleInactive(n)) return 0; break; } return CallWindowProc(oldproc, hwnd, msg, wp, lp ); }
/******************************************************************** ** Frees window and class. Also destroys Ihandle information stored ** inside the window USERDATA atribute. ********************************************************************/ static void winDestroyFreeWindowClass(Ihandle *n) { char cname[255]; SetLastError(0); GetClassName(handle(n), cname, 255); assert(GetLastError() == 0); /* Ihandle will not be found when WM_DESTROY is called */ iupwinHandleRemove(n); if (iupCheck(n, "MDICLIENT")==YES) /* mdiclient class is not a IUP class */ { HWND hwndT; /* hide the MDI client window to avoid multiple repaints */ ShowWindow((HWND)handle(n), SW_HIDE); /* As long as the MDI client has a child, destroy it */ while (hwndT = GetWindow((HWND)handle(n), GW_CHILD)) { Ihandle* child; /* Skip the icon title windows */ while (hwndT && GetWindow (hwndT, GW_OWNER)) hwndT = GetWindow (hwndT, GW_HWNDNEXT); if (!hwndT) break; child = iupwinHandleGet(hwndT); if (child) IupDestroy(child); } return; } SetClassLongPtr((HWND)handle(n), GCLP_HBRBACKGROUND, 0); SetClassLongPtr((HWND)handle(n), GCLP_HCURSOR, 0); SetWindowLongPtr((HWND)handle(n), GWLP_WNDPROC, 0); /* Destroys window, so we can destroy the class */ SetLastError(0); if (iupCheck(n, "MDICHILD")==YES) { Ihandle* client = (Ihandle*)iupGetEnv(n, "_IUPWIN_MDICLIENT"); SendMessage((HWND)handle(client), WM_MDIDESTROY, (WPARAM)handle(n), 0); } else DestroyWindow(handle(n)); /* iupwinShowLastError(); */ SetLastError(0); UnregisterClass(cname, iupwin_hinstance); }
Ihandle *IupGetFocus (void) { Ihandle *h; HWND hwnd = GetFocus(); if(hwnd == NULL) return NULL; h = iupwinHandleGet(hwnd); return h; }
static void winCanvasMDICloseChildren(Ihandle* client) { HWND hWndChild = (HWND)SendMessage(client->handle, WM_MDIGETACTIVE, 0, 0); /* As long as the MDI client has a child, close it */ while (hWndChild) { Ihandle* child = iupwinHandleGet(hWndChild); if (iupObjectCheck(child) && iupAttribGetBoolean(child, "MDICHILD")) IupDestroy(child); hWndChild = (HWND)SendMessage(client->handle, WM_MDIGETACTIVE, 0, 0); } }
static Ihandle* iupwinGetTrackMouseLeave(void) { Ihandle* ih = NULL; TRACKMOUSEEVENT mouse; mouse.cbSize = sizeof(TRACKMOUSEEVENT); mouse.dwFlags = TME_QUERY | TME_LEAVE; TrackMouseEvent(&mouse); if (mouse.hwndTrack) ih = iupwinHandleGet(mouse.hwndTrack); return ih; }
Ihandle *IupSetFocus (Ihandle *n) { Ihandle *h; HWND hwnd; if(n != NULL) hwnd = SetFocus( (HWND)handle(n) ); else hwnd = SetFocus(NULL); if(hwnd == NULL) return NULL; h = iupwinHandleGet(hwnd); return h; }
static LRESULT CALLBACK winDialogMDIFrameProc(HWND hwnd, UINT msg, WPARAM wp, LPARAM lp) { LRESULT result; HWND hWndClient = NULL; Ihandle *ih = iupwinHandleGet(hwnd); if (!ih) { /* the first time WM_GETMINMAXINFO is called, Ihandle is not associated yet */ if (msg == WM_GETMINMAXINFO && winMinMaxHandle) { if (winDialogCheckMinMaxInfo(winMinMaxHandle, (MINMAXINFO*)lp)) return 0; } return DefFrameProc(hwnd, hWndClient, msg, wp, lp); } { Ihandle* client = (Ihandle*)iupAttribGet(ih, "MDICLIENT_HANDLE"); if (client) hWndClient = client->handle; } if (winDialogBaseProc(ih, msg, wp, lp, &result)) return result; if (msg == WM_MENUCOMMAND) { int menuId = GetMenuItemID((HMENU)lp, (int)wp); if (menuId >= IUP_MDI_FIRSTCHILD && hWndClient) { /* we manually activate the MDI child when its menu item is selected. */ HWND hChild = GetDlgItem(hWndClient, menuId); if (hChild) SendMessage(hWndClient, WM_MDIACTIVATE, (WPARAM)hChild, 0); } else if (menuId >= SC_SIZE && menuId <= SC_CONTEXTHELP) { /* we manually forward the message to the MDI child */ HWND hChild = (HWND)SendMessage(hWndClient, WM_MDIGETACTIVE, 0, 0); if (hChild) SendMessage(hChild, WM_SYSCOMMAND, (WPARAM)menuId, 0); } } return DefFrameProc(hwnd, hWndClient, msg, wp, lp); }
static char* winDialogGetMdiActiveAttrib(Ihandle *ih) { Ihandle* client = (Ihandle*)iupAttribGet(ih, "MDICLIENT_HANDLE"); if (client) { HWND hchild = (HWND)SendMessage(client->handle, WM_MDIGETACTIVE, 0, 0); Ihandle* child = iupwinHandleGet(hchild); if (child) { iupwin_mdinext = NULL; iupwin_mdifirst = hchild; return IupGetName(child); } } iupwin_mdifirst = NULL; iupwin_mdinext = NULL; return NULL; }
static LRESULT CALLBACK winDialogMDIFrameProc(HWND hwnd, UINT msg, WPARAM wp, LPARAM lp) { LRESULT result; HWND hWndClient = NULL; Ihandle *ih = iupwinHandleGet(hwnd); if (!ih) { /* the first time WM_GETMINMAXINFO is called, Ihandle is not associated yet */ if (msg == WM_GETMINMAXINFO && winMinMaxHandle) { if (winDialogCheckMinMaxInfo(winMinMaxHandle, (MINMAXINFO*)lp)) return 0; } return DefFrameProc(hwnd, hWndClient, msg, wp, lp); } { Ihandle* client = (Ihandle*)iupAttribGet(ih, "MDICLIENT_HANDLE"); if (client) hWndClient = client->handle; } if (winDialogBaseProc(ih, msg, wp, lp, &result)) return result; switch (msg) { case WM_MENUCOMMAND: { int menuId = GetMenuItemID((HMENU)lp, (int)wp); if (menuId >= IUP_MDICHILD_START && hWndClient) { Ihandle* child = winDialogGetMdiChildId(ih, menuId-IUP_MDICHILD_START); if (child) SendMessage(hWndClient, WM_MDIACTIVATE, (WPARAM)child->handle, 0); break; } } } return DefFrameProc(hwnd, hWndClient, msg, wp, lp); }
static LRESULT CALLBACK winDialogProc(HWND hwnd, UINT msg, WPARAM wp, LPARAM lp) { LRESULT result; Ihandle *ih = iupwinHandleGet(hwnd); if (!ih) { /* the first time WM_GETMINMAXINFO is called, Ihandle is not associated yet */ if (msg == WM_GETMINMAXINFO && winMinMaxHandle) { if (winDialogCheckMinMaxInfo(winMinMaxHandle, (MINMAXINFO*)lp)) return 0; } return DefWindowProc(hwnd, msg, wp, lp); } if (winDialogBaseProc(ih, msg, wp, lp, &result)) return result; return DefWindowProc(hwnd, msg, wp, lp); }
static LRESULT CALLBACK winListComboListWinProc(HWND hwnd, UINT msg, WPARAM wp, LPARAM lp) { int ret = 0; LRESULT result = 0; WNDPROC oldProc; Ihandle *ih; ih = iupwinHandleGet(hwnd); if (!ih) return DefWindowProc(hwnd, msg, wp, lp); /* should never happen */ /* retrieve the control previous procedure for subclassing */ oldProc = (WNDPROC)IupGetCallback(ih, "_IUPWIN_LISTOLDPROC_CB"); ret = winListComboListProc(ih, hwnd, msg, wp, lp, &result); if (ret) return result; else return CallWindowProc(oldProc, hwnd, msg, wp, lp); }
static int winPopupMenu( Ihandle* h, int x, int y ) { HWND activehwnd = GetActiveWindow(); HMENU hmenu = (HMENU) handle(h); int tray_menu = 0; POINT pt; int menuId; if (!hmenu) { iupwinCreatePopupMenu(h); hmenu = (HMENU)handle(h); if (!hmenu) return IUP_ERROR; } GetCursorPos( &pt ); if (x == IUP_MOUSEPOS) x = pt.x; if (y == IUP_MOUSEPOS) y = pt.y; if (!activehwnd) { /* search for a valid handle */ Ihandle* dlg = iupDlgListFirst(); do { if (handle(dlg)) { activehwnd = handle(dlg); if (iupCheck(dlg, "TRAY")==YES) /* keep searching for a "TRAY" dialog */ break; } dlg = iupDlgListNext(); } while (dlg); } /* Necessary to avoid tray dialogs to lock popup menus (they get sticky after the 1st time) */ if (activehwnd) { Ihandle* dlg = iupwinHandleGet(activehwnd); if (dlg && iupCheck(dlg, "TRAY")==YES) { /* To display a context menu for a notification icon, the current window must be the foreground window. */ SetForegroundWindow(activehwnd); tray_menu = 1; } } /* stop processing here. messages will not go to the message loop */ menuId = TrackPopupMenu(hmenu, TPM_LEFTALIGN|TPM_RIGHTBUTTON|TPM_RETURNCMD, x, y, 0, activehwnd, NULL); if (tray_menu) { /* You must force a task switch to the application that called TrackPopupMenu at some time in the near future. This is done by posting a benign message to the window. */ PostMessage(activehwnd, WM_NULL, 0, 0); } if (menuId) { IFni cb; Ihandle* n = iupwinGetMenuIhandle(menuId); if (!n) return IUP_NOERROR; cb = (IFni) IupGetCallback(n, IUP_ACTION); assert(number(n)>0); if (cb) { int ret = cb(n, GetMenuState ((HMENU)handle(n), number(n), MF_BYCOMMAND) == MF_CHECKED); if (ret == IUP_CLOSE) IupExitLoop(); } } return IUP_NOERROR; }
static int winInterceptMsg(MSG* gm_msg) { HWND hwnd = gm_msg->hwnd; UINT msg = gm_msg->message; WPARAM wp = gm_msg->wParam; LPARAM lp = gm_msg->lParam; Ihandle *n; static char report[12]; int is_dblclk = 0, ret = 0; static int dragging = 0; if (!hwnd) return 0; switch(msg) { case WM_MOUSEMOVE: { IFniis cb; char *r=report; short int x, y; n = iupwinHandleGet(hwnd); if (!n) return 0; cb = (IFniis) IupGetCallback(n,"CMOTION_CB"); if (!cb) return 0; x = LOWORD(lp); y = HIWORD(lp); if (!GetClassLongPtr ((HWND)handle(n), GCLP_HCURSOR)) SetCursor(NULL); if (wp & MK_SHIFT) *r++= 'S'; else *r++= ' '; if (wp & MK_CONTROL) *r++= 'C'; else *r++= ' '; if (wp & MK_LBUTTON) *r++= IUP_BUTTON1; else *r++= ' '; if (wp & MK_MBUTTON) *r++= IUP_BUTTON2; else *r++= ' '; if (wp & MK_RBUTTON) *r++= IUP_BUTTON3; else *r++= ' '; *r='\0'; if (cb (n, x, y, report)==IUP_IGNORE) ret = 1; if (dragging) { if(!(wp & (MK_LBUTTON | MK_MBUTTON | MK_RBUTTON))) { dragging = 0; ReleaseCapture(); } } } break; case WM_LBUTTONDBLCLK: case WM_MBUTTONDBLCLK: case WM_RBUTTONDBLCLK: is_dblclk = 1; case WM_LBUTTONDOWN: case WM_MBUTTONDOWN: case WM_RBUTTONDOWN: { IFniiiis cb; char *r=report; int b=0; short int x, y; n = iupwinHandleGet(hwnd); if (!n) return 0; cb = (IFniiiis) IupGetCallback(n,"CBUTTON_CB"); if (!cb) return 0; x = LOWORD(lp); y = HIWORD(lp); if (msg==WM_LBUTTONDOWN || msg==WM_LBUTTONDBLCLK) b = IUP_BUTTON1; else if (msg==WM_MBUTTONDOWN || msg==WM_MBUTTONDBLCLK) b = IUP_BUTTON2; else if (msg==WM_RBUTTONDOWN || msg==WM_RBUTTONDBLCLK) b = IUP_BUTTON3; if (wp & MK_SHIFT) *r++= 'S'; else *r++= ' '; if (wp & MK_CONTROL) *r++= 'C'; else *r++= ' '; if (wp & MK_LBUTTON) *r++= IUP_BUTTON1; else *r++= ' '; if (wp & MK_MBUTTON) *r++= IUP_BUTTON2; else *r++= ' '; if (wp & MK_RBUTTON) *r++= IUP_BUTTON3; else *r++= ' '; if (is_dblclk) *r++ = 'D'; *r='\0'; SetCapture(hwnd); dragging = 1; ret = cb (n, b, 1, x, y, report); if (ret == IUP_CLOSE) { IupExitLoop(); ReleaseCapture(); dragging = 0; } else if (ret == IUP_IGNORE) ret = 1; if (dragging) SendMessage(hwnd,WM_SETCURSOR,(WPARAM)hwnd,MAKELPARAM(1,WM_MOUSEMOVE)); } break; case WM_LBUTTONUP: case WM_MBUTTONUP: case WM_RBUTTONUP: { IFniiiis cb; char *r=report; int b=0; short int x, y; n = iupwinHandleGet(hwnd); if (!n) return 0; cb = (IFniiiis) IupGetCallback(n,"CBUTTON_CB"); if (!cb) return 0; x = LOWORD(lp); y = HIWORD(lp); if (msg==WM_LBUTTONUP) b = IUP_BUTTON1; else if (msg==WM_MBUTTONUP) b = IUP_BUTTON2; else if (msg==WM_RBUTTONUP) b = IUP_BUTTON3; if (wp & MK_SHIFT) *r++= 'S'; else *r++= ' '; if (wp & MK_CONTROL) *r++= 'C'; else *r++= ' '; if (wp & MK_LBUTTON) *r++= IUP_BUTTON1; else *r++= ' '; if (wp & MK_MBUTTON) *r++= IUP_BUTTON2; else *r++= ' '; if (wp & MK_RBUTTON) *r++= IUP_BUTTON3; else *r++= ' '; *r='\0'; if (dragging) { ReleaseCapture(); dragging=0; } ret = cb (n, b, 0, x, y, report); if (ret == IUP_CLOSE) IupExitLoop(); else if (ret == IUP_IGNORE) ret = 1; SendMessage(hwnd,WM_SETCURSOR,(WPARAM)hwnd,MAKELPARAM(1,WM_MOUSEMOVE)); } break; } return ret; }
void iupwinTipsGetDispInfo(LPARAM lp) { COLORREF color, tip_color; NMTTDISPINFO* tips_info; Ihandle* ih; HWND tips_hwnd; char* value; if (!lp) return; tips_info = (NMTTDISPINFO*)lp; ih = iupwinHandleGet(tips_info->hdr.hwndFrom); /* hwndFrom is the tooltip window */ if (!ih) return; tips_hwnd = (HWND)iupAttribGet(ih, "_IUPWIN_TIPSWIN"); if (tips_hwnd != tips_info->hdr.hwndFrom) return; tips_info->hinst = NULL; tips_info->lpszText = IupGetAttribute(ih, "TIP"); /* must use IupGetAttribute to use inheritance */ { HFONT hfont = (HFONT)iupwinGetHFontAttrib(ih); value = iupAttribGetStr(ih, "TIPFONT"); if (value) { if (iupStrEqualNoCase(value, "SYSTEM")) hfont = NULL; else hfont = iupwinFontGetNativeFont(value); } if (hfont) { HFONT tip_hfont = (HFONT)SendMessage(tips_hwnd, WM_GETFONT, 0, 0); if (tip_hfont != hfont) SendMessage(tips_hwnd, WM_SETFONT, (WPARAM)hfont, MAKELPARAM(TRUE,0)); } } iupwinGetColorRef(ih, "TIPBGCOLOR", &color); tip_color = (COLORREF)SendMessage(tips_hwnd, TTM_GETTIPBKCOLOR, 0, 0); if (color != tip_color) SendMessage(tips_hwnd, TTM_SETTIPBKCOLOR, (WPARAM)color, 0); iupwinGetColorRef(ih, "TIPFGCOLOR", &color); tip_color = (COLORREF)SendMessage(tips_hwnd, TTM_GETTIPTEXTCOLOR, 0, 0); if (color != tip_color) SendMessage(tips_hwnd, TTM_SETTIPTEXTCOLOR, (WPARAM)color, 0); { int ballon = IupGetInt(ih, "TIPBALLON"); /* must use IupGetInt to use inheritance */ DWORD style = GetWindowLong(tips_hwnd, GWL_STYLE); int tip_ballon = style & TTS_BALLOON? 1: 0; if (tip_ballon != ballon) { if (ballon) style |= TTS_BALLOON; else style &= ~TTS_BALLOON; SetWindowLong(tips_hwnd, GWL_STYLE, style); } if (ballon) { char* ballon_title = IupGetAttribute(ih, "TIPBALLONTITLE"); /* must use IupGetAttribute to use inheritance */ int ballon_icon = IupGetInt(ih, "TIPBALLONTITLEICON"); /* must use IupGetInt to use inheritance */ SendMessage(tips_hwnd, TTM_SETTITLEA, ballon_icon, (LPARAM)ballon_title); } else SendMessage(tips_hwnd, TTM_SETTITLEA, 0, 0); } { int delay = IupGetInt(ih, "TIPDELAY"); /* must use IupGetInt to use inheritance */ int tip_delay = SendMessage(tips_hwnd, TTM_GETDELAYTIME, TTDT_AUTOPOP, 0); if (delay != tip_delay) SendMessage(tips_hwnd, TTM_SETDELAYTIME, TTDT_AUTOPOP, (LPARAM)MAKELONG(delay, 0)); } { TOOLINFO ti; ZeroMemory(&ti, sizeof(TOOLINFO)); ti.cbSize = sizeof(TOOLINFO); ti.uId = 0; ti.hwnd = ih->handle; value = iupAttribGet(ih, "TIPRECT"); if (value) { int x1, x2, y1, y2; sscanf(value, "%d %d %d %d", &x1, &y1, &x2, &y2); ti.rect.left = x1; ti.rect.right = x2; ti.rect.top = y1; ti.rect.bottom = y2; } else GetClientRect(ih->handle, &ti.rect); SendMessage(tips_hwnd, TTM_NEWTOOLRECT, 0, (LPARAM)&ti); } }
int iupdrvMenuPopup(Ihandle* ih, int x, int y) { HWND hWndActive = GetActiveWindow(); int tray_menu = 0; int menuId; if (!hWndActive) { /* search for a valid handle */ Ihandle* dlg = iupDlgListFirst(); do { if (dlg->handle) { hWndActive = dlg->handle; /* found a valid handle */ /* if not a "TRAY" dialog, keep searching, because TRAY is a special case */ if (iupAttribGetBoolean(dlg, "TRAY")) break; } dlg = iupDlgListNext(); } while (dlg); } /* Necessary to avoid tray dialogs to lock popup menus (they get sticky after the 1st time) */ if (hWndActive) { Ihandle* dlg = iupwinHandleGet(hWndActive); if (dlg && iupAttribGetBoolean(dlg, "TRAY")) { /* To display a context menu for a notification icon, the current window must be the foreground window. */ SetForegroundWindow(hWndActive); tray_menu = 1; } } /* stop processing here. messages will not go to the message loop */ menuId = TrackPopupMenu((HMENU)ih->handle, TPM_LEFTALIGN|TPM_RIGHTBUTTON|TPM_RETURNCMD, x, y, 0, hWndActive, NULL); if (tray_menu) { /* You must force a task switch to the application that called TrackPopupMenu at some time in the near future. This is done by posting a benign message to the window. */ PostMessage(hWndActive, WM_NULL, 0, 0); } if (menuId) { Icallback cb; Ihandle* ih_item = iupwinMenuGetItemHandle((HMENU)ih->handle, menuId); if (!ih_item) return IUP_NOERROR; winItemCheckToggle(ih_item); cb = IupGetCallback(ih_item, "ACTION"); if (cb && cb(ih_item) == IUP_CLOSE) IupExitLoop(); } return IUP_NOERROR; }
int iupwinBaseMsgProc(Ihandle* ih, UINT msg, WPARAM wp, LPARAM lp, LRESULT *result) { switch (msg) { case WM_INPUTLANGCHANGE: iupwinKeyInit(); break; case WM_GETDLGCODE: { *result = DLGC_WANTALLKEYS; return 1; } case WM_NOTIFY: /* usually sent only to parent, */ { /* but TIPs are configured to be handled here */ NMHDR* msg_info = (NMHDR*)lp; if (msg_info->code == TTN_GETDISPINFO) iupwinTipsGetDispInfo(lp); break; } case WM_DROPFILES: iupwinDropFiles((HDROP)wp, ih); break; case WM_LBUTTONDOWN: if(iupAttribGetBoolean(ih, "DRAGSOURCE")) { if (iupwinDragStart(ih)) { *result = 0; return 1; /* abort default processing */ } } break; case WM_HELP: { Ihandle* child; HELPINFO* help_info = (HELPINFO*)lp; if (help_info->iContextType == HELPINFO_MENUITEM) child = iupwinMenuGetItemHandle((HMENU)help_info->hItemHandle, (int)help_info->iCtrlId); else child = iupwinHandleGet((HWND)help_info->hItemHandle); if (child) { Icallback cb = (Icallback) IupGetCallback(child, "HELP_CB"); if (cb) { if (cb(child) == IUP_CLOSE) IupExitLoop(); *result = 0; return 1; /* abort default processing */ } } break; } case WM_MOUSELEAVE: { Icallback leave_cb = IupGetCallback(ih, "LEAVEWINDOW_CB"); if (leave_cb) leave_cb(ih); iupAttribSet(ih, "_IUPWIN_ENTERWIN", NULL); /* enable tracking again */ break; } case WM_MOUSEHOVER: { Icallback enter_cb = IupGetCallback(ih, "ENTERWINDOW_CB"); if (enter_cb) enter_cb(ih); break; } case WM_MOUSEMOVE: { /* set tracking only once, but only until track message is processed. */ if (!iupAttribGet(ih, "_IUPWIN_ENTERWIN")) { /* set tracking only if enter or leave callbacks are defined */ Icallback enter_cb = IupGetCallback(ih, "ENTERWINDOW_CB"); Icallback leave_cb = IupGetCallback(ih, "LEAVEWINDOW_CB"); if (enter_cb || leave_cb) { /* must be called so WM_MOUSEHOVER and WM_MOUSELEAVE will be called */ winTrackMouseHoverLeave(ih); iupAttribSet(ih, "_IUPWIN_ENTERWIN", "1"); } } break; } case WM_KEYDOWN: case WM_SYSKEYDOWN: if (!iupwinKeyEvent(ih, (int)wp, 1)) { *result = 0; return 1; /* abort default processing */ } break; case WM_SYSKEYUP: case WM_KEYUP: { int ret; if (wp == VK_SNAPSHOT) /* called only on key up */ { ret = iupwinKeyEvent(ih, (int)wp, 1); if (ret && iupObjectCheck(ih)) ret = iupwinKeyEvent(ih, (int)wp, 0); } else ret = iupwinKeyEvent(ih, (int)wp, 0); if (!ret) { *result = 0; return 1; /* abort default processing */ } break; } case WM_SETFOCUS: /* TODO: Not setting WS_TABSTOP still allows the control to receive the focus when clicked. But this code does make several controls with CANFOCUS=NO to stop working. So we use it inside some of the controls. */ /* if (!iupAttribGetBoolean(ih, "CANFOCUS")) { HWND previous = (HWND)wp; if (previous && previous != ih->handle) SetFocus(previous); break; } */ iupwinWmSetFocus(ih); break; case WM_KILLFOCUS: iupCallKillFocusCb(ih); break; case WM_SETCURSOR: { if (ih->handle == (HWND)wp && LOWORD(lp)==HTCLIENT) { HCURSOR hCur = (HCURSOR)iupAttribGet(ih, "_IUPWIN_HCURSOR"); if (hCur) { SetCursor(hCur); *result = 1; return 1; } else if (iupAttribGet(ih, "CURSOR")) { SetCursor(NULL); *result = 1; return 1; } } break; } case WM_TOUCH: /* TODO: - considering touch messages are greedy, one window got it all? - how this work? only for the dialog, or also for the children? - should a container forward to its children? */ if (LOWORD(wp)) iupwinTouchProcessInput(ih, (int)LOWORD(wp), (void*)lp); break; case WOM_CLOSE: case WOM_DONE: case WOM_OPEN: { IFni cb = (IFni)IupGetCallback(ih, "WOM_CB"); if (cb) { int v = -2; /* Error */ switch(msg) { case WOM_OPEN: v = 1; break; case WOM_DONE: v = 0; break; case WOM_CLOSE: v = -1; break; } cb(ih, v); } break; } } return 0; }
int iupwinBaseContainerMsgProc(Ihandle* ih, UINT msg, WPARAM wp, LPARAM lp, LRESULT *result) { /* All messages here are sent to the parent Window, but they are usefull for child controls. */ switch (msg) { case WM_COMMAND: { Ihandle* child = winContainerWmCommandGetIhandle(ih, wp, lp); if (child) { IFwmCommand cb = (IFwmCommand)IupGetCallback(child, "_IUPWIN_COMMAND_CB"); if (cb) cb(child, wp, lp); } break; } case WM_CTLCOLOREDIT: case WM_CTLCOLORLISTBOX: case WM_CTLCOLORBTN: case WM_CTLCOLORSCROLLBAR: case WM_CTLCOLORSTATIC: { Ihandle* child = iupwinHandleGet((HWND)lp); if (child && winCheckParent(child, ih)) { IFctlColor cb = (IFctlColor)IupGetCallback(child, "_IUPWIN_CTLCOLOR_CB"); if (cb) return cb(child, (HDC)wp, result); } break; } case WM_DRAWITEM: /* for OWNERDRAW controls */ { Ihandle *child; DRAWITEMSTRUCT *drawitem = (LPDRAWITEMSTRUCT)lp; if (!drawitem) break; if (wp == 0) /* a menu */ child = iupwinMenuGetItemHandle((HMENU)drawitem->hwndItem, drawitem->itemID); else { child = iupwinHandleGet(drawitem->hwndItem); if (child && !winCheckParent(child, ih)) child = NULL; } if (child) { IFdrawItem cb = (IFdrawItem)IupGetCallback(child, "_IUPWIN_DRAWITEM_CB"); if (cb) { cb(child, (void*)drawitem); *result = TRUE; return 1; } } break; } case WM_HSCROLL: case WM_VSCROLL: { Ihandle *child = iupwinHandleGet((HWND)lp); if (child && winCheckParent(child, ih)) { IFni cb = (IFni)IupGetCallback(child, "_IUPWIN_CUSTOMSCROLL_CB"); if (cb) cb(child, LOWORD(wp)); } break; } case WM_NOTIFY: /* Currently, the following controls support custom draw functionality: Header, List-view, Rebar, Toolbar, ToolTip, Trackbar, Tree-view. And for Button if using Windows XP Style. */ { Ihandle *child; NMHDR* msg_info = (NMHDR*)lp; if (!msg_info) break; child = iupwinHandleGet(msg_info->hwndFrom); if (child && winCheckParent(child, ih)) { IFnotify cb = (IFnotify)IupGetCallback(child, "_IUPWIN_NOTIFY_CB"); if (cb) { int ret; if (cb(child, (void*)msg_info, &ret)) { *result = (LRESULT)ret; return 1; } } } break; } default: { /* sent to the list parent */ if (msg == WM_DRAGLISTMSG) { DRAGLISTINFO* lpDrag = (DRAGLISTINFO*) lp; Ihandle *child = iupwinHandleGet(lpDrag->hWnd); if (child && winCheckParent(child, ih)) { *result = iupwinListDND(child, lpDrag->uNotification, lpDrag->ptCursor); return 1; } } break; } } return iupwinBaseMsgProc(ih, msg, wp, lp, result); }