summaryrefslogtreecommitdiff
path: root/alf
diff options
context:
space:
mode:
Diffstat (limited to 'alf')
-rw-r--r--alf/alf.cpp2
-rw-r--r--alf/alf.h28
-rw-r--r--alf/alfcompat.cpp11
-rw-r--r--alf/alfcompat.h1
-rw-r--r--alf/alfpanel.cpp16
-rw-r--r--alf/alfspinbox.cpp306
6 files changed, 363 insertions, 1 deletions
diff --git a/alf/alf.cpp b/alf/alf.cpp
index c2f99ce..a6c9e01 100644
--- a/alf/alf.cpp
+++ b/alf/alf.cpp
@@ -168,7 +168,7 @@ ALF_ShouldMessageBubble(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam)
return FALSE;
return msg == ALF_WM_GETDPI
- || msg == WM_COMMAND || msg == WM_NOTIFY
+ || msg == WM_COMMAND || msg == WM_NOTIFY || msg == WM_NOTIFYFORMAT
|| msg == WM_MEASUREITEM || msg == WM_DRAWITEM
|| msg == WM_CTLCOLORBTN || msg == WM_CTLCOLOREDIT
|| msg == WM_CTLCOLORLISTBOX || msg == WM_CTLCOLORSCROLLBAR
diff --git a/alf/alf.h b/alf/alf.h
index 8969ee1..f6ef21d 100644
--- a/alf/alf.h
+++ b/alf/alf.h
@@ -125,6 +125,13 @@ typedef struct {
#define ALF_WM_ICONVIEW_GETICON (ALF_WM__BASE + 201)
#define ALF_WM_ICONVIEW_SETICON (ALF_WM__BASE + 202)
+#define ALF_WM_SPINBOX_GETRANGE (ALF_WM__BASE + 201)
+#define ALF_WM_SPINBOX_SETRANGE (ALF_WM__BASE + 202)
+#define ALF_WM_SPINBOX_GETPOS (ALF_WM__BASE + 203)
+#define ALF_WM_SPINBOX_SETPOS (ALF_WM__BASE + 204)
+#define ALF_WM_SPINBOX_GETEDIT (ALF_WM__BASE + 205)
+#define ALF_WM_SPINBOX_GETUDCTL (ALF_WM__BASE + 206)
+
#define ALF_WM_USER (ALF_WM__BASE + 300)
typedef DWORD ALFColor;
@@ -656,6 +663,27 @@ ALF_MessageDlg_Confirm(HWND owner, const TCHAR *text, const TCHAR *caption, cons
WORD
ALF_MessageDlg_ConfirmDanger(HWND owner, const TCHAR *text, const TCHAR *caption, const TCHAR *okBtnText, const TCHAR *cancelBtnText);
+// spin box
+HWND
+ALF_AddNumericSpinBox(HWND parent, WORD id, int x, int y, short val, short min, short max);
+
+BOOL
+ALF_SpinBox_Range(HWND spinbox, short *pmin, short *pmax);
+
+BOOL
+ALF_SpinBox_SetRange(HWND spinbox, short min, short max);
+
+short
+ALF_SpinBox_Pos(HWND spinbox);
+
+BOOL
+ALF_SpinBox_SetPos(HWND spinbox, short pos);
+
+HWND
+ALF_SpinBox_EditControl(HWND spinbox);
+
+HWND
+ALF_SpinBox_UpDownControl(HWND spinbox);
#ifdef __cplusplus
} // extern C
diff --git a/alf/alfcompat.cpp b/alf/alfcompat.cpp
index f5bed22..d764895 100644
--- a/alf/alfcompat.cpp
+++ b/alf/alfcompat.cpp
@@ -434,6 +434,14 @@ ALF_Compat_fallbackBufferedPaintRenderAnimation(HWND hwnd, HDC hdc)
}
static HRESULT WINAPI
+ALF_Compat_fallbackBufferedPaintStopAllAnimations(HWND hwnd)
+{
+ (void)hwnd;
+
+ return E_NOTIMPL;
+}
+
+static HRESULT WINAPI
ALF_Compat_fallbackGetThemeTransitionDuration(HTHEME hTheme,
int iPartId,
int iStateIdFrom,
@@ -679,6 +687,7 @@ void ALF_LoadCompatFunctions(void)
LOAD_FUNC(uxtheme, EndBufferedAnimation);
LOAD_FUNC(uxtheme, EndBufferedPaint);
LOAD_FUNC(uxtheme, BufferedPaintRenderAnimation);
+ LOAD_FUNC(uxtheme, BufferedPaintStopAllAnimations);
LOAD_FUNC(uxtheme, GetThemeTransitionDuration);
LOAD_FUNC(uxtheme, GetThemePartSize);
LOAD_FUNC(uxtheme, GetThemeColor);
@@ -774,6 +783,7 @@ void ALF_UnloadCompatFunctions(void)
UNLOAD_FUNC(EndBufferedAnimation);
UNLOAD_FUNC(EndBufferedPaint);
UNLOAD_FUNC(BufferedPaintRenderAnimation);
+ UNLOAD_FUNC(BufferedPaintStopAllAnimations);
UNLOAD_FUNC(GetThemeTransitionDuration);
UNLOAD_FUNC(GetThemePartSize);
UNLOAD_FUNC(GetThemeColor);
@@ -814,6 +824,7 @@ ALF_Compat_HPAINTBUFFER (WINAPI *ALF_Compat_BeginBufferedPaint)(HDC,const RECT *
HRESULT (WINAPI *ALF_Compat_EndBufferedAnimation)(ALF_Compat_HANIMATIONBUFFER,BOOL) = NULL;
HRESULT (WINAPI *ALF_Compat_EndBufferedPaint)(ALF_Compat_HPAINTBUFFER,BOOL) = NULL;
BOOL (WINAPI *ALF_Compat_BufferedPaintRenderAnimation)(HWND,HDC) = NULL;
+HRESULT (WINAPI *ALF_Compat_BufferedPaintStopAllAnimations)(HWND) = NULL;
HRESULT (WINAPI *ALF_Compat_GetThemeTransitionDuration)(HTHEME,int,int,int,int,DWORD*) = NULL;
HRESULT (WINAPI *ALF_Compat_GetThemeColor)(HTHEME,int,int,int,COLORREF*) = NULL;
HRESULT (WINAPI *ALF_Compat_GetThemeMargins)(HTHEME,HDC,int,int,int,const RECT *,MARGINS *) = NULL;
diff --git a/alf/alfcompat.h b/alf/alfcompat.h
index 8f6b80f..2946453 100644
--- a/alf/alfcompat.h
+++ b/alf/alfcompat.h
@@ -140,6 +140,7 @@ extern ALF_Compat_HPAINTBUFFER (WINAPI *ALF_Compat_BeginBufferedPaint)(HDC,const
extern HRESULT (WINAPI *ALF_Compat_EndBufferedAnimation)(ALF_Compat_HANIMATIONBUFFER,BOOL);
extern HRESULT (WINAPI *ALF_Compat_EndBufferedPaint)(ALF_Compat_HPAINTBUFFER,BOOL);
extern BOOL (WINAPI *ALF_Compat_BufferedPaintRenderAnimation)(HWND,HDC);
+extern HRESULT (WINAPI *ALF_Compat_BufferedPaintStopAllAnimations)(HWND);
extern HRESULT (WINAPI *ALF_Compat_GetThemeTransitionDuration)(HTHEME,int,int,int,int,DWORD*);
extern HRESULT (WINAPI *ALF_Compat_GetThemeColor)(HTHEME,int,int,int,COLORREF*);
extern HRESULT (WINAPI *ALF_Compat_GetThemeMargins)(HTHEME,HDC,int,int,int,const RECT *,MARGINS *);
diff --git a/alf/alfpanel.cpp b/alf/alfpanel.cpp
index 62bac1e..be02890 100644
--- a/alf/alfpanel.cpp
+++ b/alf/alfpanel.cpp
@@ -152,6 +152,22 @@ ALF_Panel_DefWindowProc(HWND window, UINT msg, WPARAM wparam, LPARAM lparam)
return TRUE;
}
+ if (msg == WM_COMMAND && priv->vtbl && priv->vtbl->command) {
+ HWND source = (HWND)lparam;
+ WORD code = HIWORD(wparam);
+ WORD id = LOWORD(wparam);
+ LRESULT r = priv->vtbl->command(priv->closure, window, code, id, source);
+ if (r)
+ return r;
+ }
+
+ if (msg == WM_NOTIFY && priv->vtbl && priv->vtbl->notify) {
+ NMHDR *nmhdr = (NMHDR *)lparam;
+ LRESULT r = priv->vtbl->notify(priv->closure, window, wparam, nmhdr);
+ if (r)
+ return r;
+ }
+
if (ALF_ShouldMessageBubble(window, msg, wparam, lparam))
return SendMessage(GetParent(window), msg, wparam, lparam);
diff --git a/alf/alfspinbox.cpp b/alf/alfspinbox.cpp
new file mode 100644
index 0000000..bd3dd70
--- /dev/null
+++ b/alf/alfspinbox.cpp
@@ -0,0 +1,306 @@
+#include "alfpriv.h"
+
+typedef struct {
+ HWND hwndEdit;
+ HWND hwndUpdown;
+ int dpi;
+} ALFSpinBoxPriv;
+
+static void
+ALF_SpinBox_Initialize(ALFSpinBoxPriv *priv, HWND hwnd)
+{
+ priv->dpi = 96;
+
+ RECT rcClient;
+ GetClientRect(hwnd, &rcClient);
+
+ priv->hwndEdit = CreateWindowEx(ALF_Compat_Is40() ? WS_EX_CLIENTEDGE : 0,
+ TEXT("EDIT"),
+ TEXT("0"),
+ WS_CHILD | WS_VISIBLE | WS_TABSTOP | (ALF_Compat_Is40() ? 0 : WS_BORDER),
+ 0, 0, rcClient.right-rcClient.left, rcClient.bottom-rcClient.top,
+ hwnd,
+ NULL,
+ ALF_HINSTANCE,
+ NULL);
+ priv->hwndUpdown = CreateWindowEx(0,
+ TEXT("msctls_updown32"),
+ NULL,
+ WS_CHILD | WS_VISIBLE | (ALF_Compat_Is40() ? UDS_ALIGNRIGHT : WS_BORDER) | UDS_AUTOBUDDY | UDS_SETBUDDYINT | UDS_ARROWKEYS | UDS_NOTHOUSANDS,
+ 0, 0,
+ 0, 0,
+ hwnd,
+ NULL,
+ ALF_HINSTANCE,
+ NULL);
+}
+
+static void
+ALF_SpinBox_Destroy(ALFSpinBoxPriv *priv, HWND hwnd)
+{
+ (void)priv;
+ (void)hwnd;
+
+ // nothing to do here (yet)
+ // child windows are destroyed automatically
+}
+
+static void
+ALF_SpinBox_Resize(ALFSpinBoxPriv *priv, HWND hwnd)
+{
+ (void)hwnd;
+
+ RECT rcClient;
+ GetClientRect(hwnd, &rcClient);
+
+ int overlap = GetWindowLong(priv->hwndEdit, GWL_EXSTYLE) & WS_EX_CLIENTEDGE
+ ? ALF_Compat_GetSystemMetricsForDpi(SM_CXBORDER, (UINT)priv->dpi) * 2
+ : ALF_Compat_GetSystemMetricsForDpi(SM_CXBORDER, (UINT)priv->dpi);
+ int updownwidth = ALF_Compat_GetSystemMetricsForDpi(SM_CXVSCROLL, (UINT)priv->dpi) - ALF_Compat_GetSystemMetricsForDpi(SM_CXBORDER, (UINT)priv->dpi);
+
+ if (updownwidth > rcClient.bottom - rcClient.top)
+ updownwidth = rcClient.bottom - rcClient.top;
+
+
+ RECT rcEdit = {
+ 0, 0, rcClient.right - rcClient.left - updownwidth, rcClient.bottom - rcClient.top
+ };
+ RECT rcUpdown = {
+ rcEdit.right - overlap, 0, rcClient.right - rcClient.left, rcClient.bottom - rcClient.top
+ };
+
+ HDWP hdwp = BeginDeferWindowPos(2);
+ hdwp = DeferWindowPos(hdwp, priv->hwndEdit, NULL, rcEdit.left, rcEdit.top, rcEdit.right - rcEdit.left, rcEdit.bottom - rcEdit.top, SWP_NOACTIVATE|SWP_NOZORDER);
+ hdwp = DeferWindowPos(hdwp, priv->hwndUpdown, NULL, rcUpdown.left, rcUpdown.top, rcUpdown.right - rcUpdown.left, rcUpdown.bottom - rcUpdown.top, SWP_NOACTIVATE|SWP_NOZORDER);
+ EndDeferWindowPos(hdwp);
+}
+
+static void
+ALF_SpinBox_SetFont(ALFSpinBoxPriv *priv, HFONT font, LPARAM lparam)
+{
+ SendMessage(priv->hwndEdit, WM_SETFONT, (WPARAM)font, lparam);
+}
+
+static LRESULT
+ALF_SpinBox_GetFont(ALFSpinBoxPriv *priv, WPARAM wp, LPARAM lp)
+{
+ return SendMessage(priv->hwndEdit, WM_GETFONT, wp, lp);
+}
+
+static void
+ALF_SpinBox_HandleDpiChange(ALFSpinBoxPriv *priv, HWND hwnd, int newdpi)
+{
+ if (priv->dpi == newdpi)
+ return;
+
+ priv->dpi = newdpi;
+ ALF_SpinBox_Resize(priv, hwnd);
+}
+
+static LRESULT
+ALF_SpinBox_HandleGetRange(ALFSpinBoxPriv *priv, HWND hwnd)
+{
+ (void)hwnd;
+ return SendMessage(priv->hwndUpdown, UDM_GETRANGE, 0, 0);
+}
+
+static LRESULT
+ALF_SpinBox_HandleSetRange(ALFSpinBoxPriv *priv, HWND hwnd, LPARAM lparam)
+{
+ (void)hwnd;
+
+ SendMessage(priv->hwndUpdown, UDM_SETRANGE, 0, lparam);
+ return 1;
+}
+
+static LRESULT
+ALF_SpinBox_HandleGetPos(ALFSpinBoxPriv *priv, HWND hwnd)
+{
+ (void)hwnd;
+
+ return SendMessage(priv->hwndUpdown, UDM_GETPOS, 0, 0);
+}
+
+static LRESULT
+ALF_SpinBox_HandleSetPos(ALFSpinBoxPriv *priv, HWND hwnd, LPARAM lparam)
+{
+ (void)hwnd;
+
+ SendMessage(priv->hwndUpdown, UDM_SETPOS, 0, lparam);
+ return 1;
+}
+
+static LRESULT
+ALF_SpinBox_HandleCommand(ALFSpinBoxPriv *priv, HWND hwnd, WORD code, WORD id, HWND control)
+{
+ if (control == priv->hwndEdit) {
+ return SendMessage(GetParent(hwnd), WM_COMMAND, MAKEWPARAM(GetWindowLong(hwnd, GWL_ID), code), (LPARAM)hwnd);
+ } else {
+ return SendMessage(GetParent(hwnd), WM_COMMAND, MAKEWPARAM(id, code), (LPARAM)control);
+ }
+}
+
+static LRESULT
+ALF_SpinBox_HandleNotify(ALFSpinBoxPriv *priv, HWND hwnd, WPARAM wparam, const NMHDR *pnmh)
+{
+ if (pnmh->hwndFrom == priv->hwndUpdown && pnmh->code == UDN_DELTAPOS) {
+ NMUPDOWN nmud = *(const NMUPDOWN *)pnmh;
+ nmud.hdr.hwndFrom = hwnd;
+ nmud.hdr.idFrom = (UINT_PTR)GetWindowLongPtr(hwnd, GWLP_ID);
+
+ return SendMessage(GetParent(hwnd), WM_NOTIFY, nmud.hdr.idFrom, (LPARAM)&nmud);
+ } else {
+ return SendMessage(GetParent(hwnd), WM_NOTIFY, wparam, (LPARAM)pnmh);
+ }
+}
+
+static LRESULT
+ALF_SpinBox_HandleGetEditControl(ALFSpinBoxPriv *priv)
+{
+ return (LRESULT)priv->hwndEdit;
+}
+
+static LRESULT
+ALF_SpinBox_HandleGetUpDownControl(ALFSpinBoxPriv *priv)
+{
+ return (LRESULT)priv->hwndUpdown;
+}
+
+static LRESULT
+ALF_SpinBox_HandlePaint(ALFSpinBoxPriv *priv, HWND hwnd)
+{
+ (void)priv;
+
+ PAINTSTRUCT ps;
+ HDC dc = BeginPaint(hwnd, &ps);
+ FillRect(dc, &ps.rcPaint, GetSysColorBrush(COLOR_BTNFACE));
+ EndPaint(hwnd, &ps);
+ return 0;
+}
+
+static LRESULT WINAPI
+ALF_SpinBox_WndProc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam)
+{
+ ALFSpinBoxPriv *priv = (ALFSpinBoxPriv *)GetWindowLongPtr(hwnd, 0);
+
+ if (!priv && msg == WM_NCCREATE) {
+ priv = ALF_New(ALFSpinBoxPriv, 1);
+ SetWindowLongPtr(hwnd, 0, (LONG_PTR)priv);
+ }
+
+ if (!priv)
+ return DefWindowProc(hwnd, msg, wparam, lparam);
+
+ switch (msg) {
+ case WM_CREATE:
+ ALF_SpinBox_Initialize(priv, hwnd);
+ break;
+ case WM_DESTROY:
+ ALF_SpinBox_Destroy(priv, hwnd);
+ SetWindowLongPtr(hwnd, 0, 0);
+ ALF_Free(priv);
+ priv = NULL;
+ break;
+ case WM_SETFONT:
+ ALF_SpinBox_SetFont(priv, (HFONT)wparam, lparam);
+ break;
+ case WM_GETFONT:
+ return ALF_SpinBox_GetFont(priv, wparam, lparam);
+ case WM_SIZE:
+ ALF_SpinBox_Resize(priv, hwnd);
+ break;
+ case ALF_WM_DPICHANGE:
+ ALF_SpinBox_HandleDpiChange(priv, hwnd, (int)lparam);
+ return 0;
+ case ALF_WM_SPINBOX_GETRANGE:
+ return ALF_SpinBox_HandleGetRange(priv, hwnd);
+ case ALF_WM_SPINBOX_SETRANGE:
+ return ALF_SpinBox_HandleSetRange(priv, hwnd, lparam);
+ case ALF_WM_SPINBOX_GETPOS:
+ return ALF_SpinBox_HandleGetPos(priv, hwnd);
+ case ALF_WM_SPINBOX_SETPOS:
+ return ALF_SpinBox_HandleSetPos(priv, hwnd, lparam);
+ case ALF_WM_SPINBOX_GETEDIT:
+ return ALF_SpinBox_HandleGetEditControl(priv);
+ case ALF_WM_SPINBOX_GETUDCTL:
+ return ALF_SpinBox_HandleGetUpDownControl(priv);
+ case WM_GETTEXT:
+ return (LRESULT)GetWindowText(priv->hwndEdit, (TCHAR *)lparam, (int)wparam);
+ case WM_GETTEXTLENGTH:
+ return (LRESULT)GetWindowTextLength(priv->hwndEdit);
+ case WM_SETTEXT:
+ return (LRESULT)SetWindowText(priv->hwndEdit, (const TCHAR *)lparam);
+ case WM_COMMAND:
+ return ALF_SpinBox_HandleCommand(priv, hwnd, HIWORD(wparam), LOWORD(wparam), (HWND)lparam);
+ case WM_NOTIFY:
+ return ALF_SpinBox_HandleNotify(priv, hwnd, wparam, (const NMHDR *)lparam);
+ case WM_PAINT:
+ return ALF_SpinBox_HandlePaint(priv, hwnd);
+ case WM_ERASEBKGND:
+ return 1;
+ }
+
+ if (ALF_ShouldMessageBubble(hwnd, msg, wparam, lparam))
+ return SendMessage(GetParent(hwnd), msg, wparam, lparam);
+
+ return DefWindowProc(hwnd, msg, wparam, lparam);
+}
+
+HWND
+ALF_AddNumericSpinBox(HWND parent, WORD id, int x, int y, short val, short min, short max)
+{
+ HWND hwnd = ALF_CreateControlWindow(WS_EX_CONTROLPARENT,
+ TEXT(""),
+ WS_CHILD | WS_VISIBLE | WS_CLIPCHILDREN,
+ 0, 0, 0, 0,
+ parent,
+ (HMENU)(ULONG_PTR)id,
+ ALF_SpinBox_WndProc,
+ NULL);
+
+ ALF_AddControl(parent, x, y, hwnd, 0, 0, ALF_LAYOUT_SIZE_EDIT | ALF_LAYOUT_INHERITFONT | ALF_LAYOUT_SENDDPICHANGE);
+
+ ALF_SpinBox_SetRange(hwnd, min, max);
+ ALF_SpinBox_SetPos(hwnd, val);
+
+ return hwnd;
+}
+
+BOOL
+ALF_SpinBox_Range(HWND spinbox, short *pmin, short *pmax)
+{
+ LRESULT r = SendMessage(spinbox, ALF_WM_SPINBOX_GETRANGE, 0, 0);
+ *pmin = GET_X_LPARAM(r);
+ *pmax = GET_Y_LPARAM(r);
+ return TRUE;
+}
+
+BOOL
+ALF_SpinBox_SetRange(HWND spinbox, short min, short max)
+{
+ return (BOOL)SendMessage(spinbox, ALF_WM_SPINBOX_SETRANGE, 0, MAKELPARAM((WORD)max, (WORD)min));
+}
+
+short
+ALF_SpinBox_Pos(HWND spinbox)
+{
+ return (short)SendMessage(spinbox, ALF_WM_SPINBOX_GETPOS, 0, 0);
+}
+
+BOOL
+ALF_SpinBox_SetPos(HWND spinbox, short pos)
+{
+ return (BOOL)SendMessage(spinbox, ALF_WM_SPINBOX_SETPOS, 0, (LPARAM)pos);
+}
+
+HWND
+ALF_SpinBox_EditControl(HWND spinbox)
+{
+ return (HWND)SendMessage(spinbox, ALF_WM_SPINBOX_GETEDIT, 0, 0);
+}
+
+HWND
+ALF_SpinBox_UpDownControl(HWND spinbox)
+{
+ return (HWND)SendMessage(spinbox, ALF_WM_SPINBOX_GETUDCTL, 0, 0);
+}