Skip to content

Commit 7a44d2f

Browse files
SplitwirezDarkFire01
authored andcommitted
[UXTHEME] Implement various Vista+ functions, mostly from WINE
1 parent c7a7376 commit 7a44d2f

6 files changed

Lines changed: 419 additions & 41 deletions

File tree

dll/win32/uxtheme/CMakeLists.txt

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,12 @@
11

22
include_directories(${REACTOS_SOURCE_DIR}/sdk/include/reactos/wine)
33
add_definitions(-D__WINESRC__ -D__ROS_LONG64__)
4-
spec2def(uxtheme.dll uxtheme.spec ADD_IMPORTLIB)
4+
5+
if(DLL_EXPORT_VERSION GREATER_EQUAL 0x600)
6+
spec2def(uxtheme.dll uxtheme_vista.spec ADD_IMPORTLIB)
7+
else()
8+
spec2def(uxtheme.dll uxtheme.spec ADD_IMPORTLIB)
9+
endif()
510

611
list(APPEND SOURCE
712
buffer.c

dll/win32/uxtheme/buffer.c

Lines changed: 149 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,29 @@
1919
*/
2020

2121
#include "uxthemep.h"
22+
#include <wine/heap.h>
23+
24+
#if (DLL_EXPORT_VERSION >= _WIN32_WINNT_VISTA)
25+
struct paintbuffer
26+
{
27+
HDC targetdc;
28+
HDC memorydc;
29+
HBITMAP bitmap;
30+
RECT rect;
31+
void *bits;
32+
};
33+
34+
static void free_paintbuffer(struct paintbuffer *buffer)
35+
{
36+
DeleteObject(buffer->bitmap);
37+
DeleteDC(buffer->memorydc);
38+
heap_free(buffer);
39+
}
40+
41+
static struct paintbuffer *get_buffer_obj(HPAINTBUFFER handle)
42+
{
43+
return handle;
44+
}
2245

2346
/***********************************************************************
2447
* BufferedPaintInit (UXTHEME.@)
@@ -41,35 +64,104 @@ HRESULT WINAPI BufferedPaintUnInit(VOID)
4164
/***********************************************************************
4265
* BeginBufferedPaint (UXTHEME.@)
4366
*/
44-
HPAINTBUFFER WINAPI BeginBufferedPaint(HDC hdcTarget,
45-
const RECT * prcTarget,
46-
BP_BUFFERFORMAT dwFormat,
47-
BP_PAINTPARAMS *pPaintParams,
48-
HDC *phdc)
67+
HPAINTBUFFER WINAPI BeginBufferedPaint(HDC targetdc, const RECT *rect,
68+
BP_BUFFERFORMAT format, BP_PAINTPARAMS *params, HDC *retdc)
4969
{
50-
static int i;
70+
#if (defined(_MSC_VER))
71+
char bmibuf[FIELD_OFFSET(BITMAPINFO, bmiColors) + 256 * sizeof(RGBQUAD)];
72+
#else
73+
char bmibuf[FIELD_OFFSET(BITMAPINFO, bmiColors[256])];
74+
#endif
75+
BITMAPINFO *bmi = (BITMAPINFO *)bmibuf;
76+
struct paintbuffer *buffer;
5177

52-
TRACE("Stub (%p %p %d %p %p)\n", hdcTarget, prcTarget, dwFormat,
53-
pPaintParams, phdc);
78+
TRACE("(%p %s %d %p %p)\n", targetdc, wine_dbgstr_rect(rect), format,
79+
params, retdc);
5480

55-
if (!i++)
56-
FIXME("Stub (%p %p %d %p %p)\n", hdcTarget, prcTarget, dwFormat,
57-
pPaintParams, phdc);
58-
return NULL;
81+
if (retdc)
82+
*retdc = NULL;
83+
84+
if (!targetdc || IsRectEmpty(rect))
85+
return NULL;
86+
87+
if (params)
88+
FIXME("painting parameters are ignored\n");
89+
90+
buffer = heap_alloc(sizeof(*buffer));
91+
buffer->targetdc = targetdc;
92+
buffer->rect = *rect;
93+
buffer->memorydc = CreateCompatibleDC(targetdc);
94+
95+
switch (format)
96+
{
97+
case BPBF_COMPATIBLEBITMAP:
98+
buffer->bitmap = CreateCompatibleBitmap(targetdc, rect->right - rect->left, rect->bottom - rect->top);
99+
buffer->bits = NULL;
100+
break;
101+
case BPBF_DIB:
102+
case BPBF_TOPDOWNDIB:
103+
case BPBF_TOPDOWNMONODIB:
104+
/* create DIB section */
105+
memset(bmi, 0, sizeof(bmibuf));
106+
bmi->bmiHeader.biSize = sizeof(bmi->bmiHeader);
107+
bmi->bmiHeader.biHeight = format == BPBF_DIB ? rect->bottom - rect->top :
108+
-(rect->bottom - rect->top);
109+
bmi->bmiHeader.biWidth = rect->right - rect->left;
110+
bmi->bmiHeader.biBitCount = format == BPBF_TOPDOWNMONODIB ? 1 : 32;
111+
bmi->bmiHeader.biPlanes = 1;
112+
bmi->bmiHeader.biCompression = BI_RGB;
113+
buffer->bitmap = CreateDIBSection(buffer->memorydc, bmi, DIB_RGB_COLORS, &buffer->bits, NULL, 0);
114+
break;
115+
default:
116+
WARN("Unknown buffer format %d\n", format);
117+
buffer->bitmap = NULL;
118+
free_paintbuffer(buffer);
119+
return NULL;
120+
}
121+
122+
if (!buffer->bitmap)
123+
{
124+
WARN("Failed to create buffer bitmap\n");
125+
free_paintbuffer(buffer);
126+
return NULL;
127+
}
128+
129+
SetWindowOrgEx(buffer->memorydc, rect->left, rect->top, NULL);
130+
IntersectClipRect(buffer->memorydc, rect->left, rect->top, rect->right, rect->bottom);
131+
DeleteObject(SelectObject(buffer->memorydc, buffer->bitmap));
132+
133+
*retdc = buffer->memorydc;
134+
135+
return (HPAINTBUFFER)buffer;
59136
}
60137

61138

62139
/***********************************************************************
63140
* EndBufferedPaint (UXTHEME.@)
64141
*/
65-
HRESULT WINAPI EndBufferedPaint(HPAINTBUFFER hPaintBuffer, BOOL fUpdateTarget)
142+
HRESULT WINAPI EndBufferedPaint(HPAINTBUFFER bufferhandle, BOOL update)
66143
{
67-
FIXME("Stub (%p %d)\n", hPaintBuffer, fUpdateTarget);
144+
struct paintbuffer *buffer = get_buffer_obj(bufferhandle);
145+
146+
TRACE("(%p %d)\n", bufferhandle, update);
147+
148+
if (!buffer)
149+
return E_INVALIDARG;
150+
151+
if (update)
152+
{
153+
if (!BitBlt(buffer->targetdc, buffer->rect.left, buffer->rect.top,
154+
buffer->rect.right - buffer->rect.left, buffer->rect.bottom - buffer->rect.top,
155+
buffer->memorydc, buffer->rect.left, buffer->rect.top, SRCCOPY))
156+
{
157+
WARN("BitBlt() failed\n");
158+
}
159+
}
160+
161+
free_paintbuffer(buffer);
68162
return S_OK;
69163
}
70164

71-
#ifndef __REACTOS__
72-
73165
/***********************************************************************
74166
* BufferedPaintClear (UXTHEME.@)
75167
*/
@@ -91,38 +183,65 @@ HRESULT WINAPI BufferedPaintSetAlpha(HPAINTBUFFER hBufferedPaint, const RECT *pr
91183
/***********************************************************************
92184
* GetBufferedPaintBits (UXTHEME.@)
93185
*/
94-
HRESULT WINAPI GetBufferedPaintBits(HPAINTBUFFER hBufferedPaint, RGBQUAD **ppbBuffer,
95-
int *pcxRow)
186+
HRESULT WINAPI GetBufferedPaintBits(HPAINTBUFFER bufferhandle, RGBQUAD **bits, int *width)
96187
{
97-
FIXME("Stub (%p %p %p)\n", hBufferedPaint, ppbBuffer, pcxRow);
98-
return E_NOTIMPL;
188+
struct paintbuffer *buffer = get_buffer_obj(bufferhandle);
189+
190+
TRACE("(%p %p %p)\n", buffer, bits, width);
191+
192+
if (!bits || !width)
193+
return E_POINTER;
194+
195+
if (!buffer || !buffer->bits)
196+
return E_FAIL;
197+
198+
*bits = buffer->bits;
199+
*width = buffer->rect.right - buffer->rect.left;
200+
201+
return S_OK;
99202
}
100203

101204
/***********************************************************************
102205
* GetBufferedPaintDC (UXTHEME.@)
103206
*/
104-
HDC WINAPI GetBufferedPaintDC(HPAINTBUFFER hBufferedPaint)
207+
HDC WINAPI GetBufferedPaintDC(HPAINTBUFFER bufferhandle)
105208
{
106-
FIXME("Stub (%p)\n", hBufferedPaint);
107-
return NULL;
209+
struct paintbuffer *buffer = get_buffer_obj(bufferhandle);
210+
211+
TRACE("(%p)\n", buffer);
212+
213+
return buffer ? buffer->memorydc : NULL;
108214
}
109215

110216
/***********************************************************************
111217
* GetBufferedPaintTargetDC (UXTHEME.@)
112218
*/
113-
HDC WINAPI GetBufferedPaintTargetDC(HPAINTBUFFER hBufferedPaint)
219+
HDC WINAPI GetBufferedPaintTargetDC(HPAINTBUFFER bufferhandle)
114220
{
115-
FIXME("Stub (%p)\n", hBufferedPaint);
116-
return NULL;
221+
struct paintbuffer *buffer = get_buffer_obj(bufferhandle);
222+
223+
TRACE("(%p)\n", buffer);
224+
225+
return buffer ? buffer->targetdc : NULL;
117226
}
118227

119228
/***********************************************************************
120229
* GetBufferedPaintTargetRect (UXTHEME.@)
121230
*/
122-
HRESULT WINAPI GetBufferedPaintTargetRect(HPAINTBUFFER hBufferedPaint, RECT *prc)
231+
HRESULT WINAPI GetBufferedPaintTargetRect(HPAINTBUFFER bufferhandle, RECT *rect)
123232
{
124-
FIXME("Stub (%p %p)\n", hBufferedPaint, prc);
125-
return E_NOTIMPL;
233+
struct paintbuffer *buffer = get_buffer_obj(bufferhandle);
234+
235+
TRACE("(%p %p)\n", buffer, rect);
236+
237+
if (!rect)
238+
return E_POINTER;
239+
240+
if (!buffer)
241+
return E_FAIL;
242+
243+
*rect = buffer->rect;
244+
return S_OK;
126245
}
127246

128247
/***********************************************************************
@@ -168,5 +287,4 @@ HRESULT WINAPI EndBufferedAnimation(HANIMATIONBUFFER hbpAnimation, BOOL fUpdateT
168287

169288
return E_NOTIMPL;
170289
}
171-
172-
#endif /* __REACTOS__ */
290+
#endif /* (DLL_EXPORT_VERSION >= _WIN32_WINNT_VISTA) */

dll/win32/uxtheme/metric.c

Lines changed: 27 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -220,16 +220,38 @@ HRESULT WINAPI GetThemeSysString(HTHEME hTheme, int iStringID,
220220
return E_PROP_ID_UNSUPPORTED;
221221
}
222222

223-
#ifndef __REACTOS__
224223
/***********************************************************************
225224
* GetThemeTransitionDuration (UXTHEME.@)
226225
*/
227226
HRESULT WINAPI GetThemeTransitionDuration(HTHEME hTheme, int iPartId, int iStateIdFrom,
228227
int iStateIdTo, int iPropId, DWORD *pdwDuration)
229228
{
230-
FIXME("(%p, %u, %u, %u, %u, %p) stub\n", hTheme, iPartId, iStateIdFrom, iStateIdTo,
231-
iPropId, pdwDuration);
229+
INTLIST intlist;
230+
HRESULT hr;
231+
232+
TRACE("(%p, %d, %d, %d, %d, %p)\n", hTheme, iPartId, iStateIdFrom, iStateIdTo, iPropId,
233+
pdwDuration);
234+
235+
if (!pdwDuration || iStateIdFrom < 1 || iStateIdTo < 1)
236+
return E_INVALIDARG;
237+
238+
hr = GetThemeIntList(hTheme, iPartId, 0, iPropId, &intlist);
239+
if (FAILED(hr))
240+
{
241+
if (hr == E_PROP_ID_UNSUPPORTED)
242+
*pdwDuration = 0;
243+
244+
return hr;
245+
}
246+
247+
if (intlist.iValueCount < 1 || iStateIdFrom > intlist.iValues[0]
248+
|| iStateIdTo > intlist.iValues[0]
249+
|| intlist.iValueCount != 1 + intlist.iValues[0] * intlist.iValues[0])
250+
{
251+
*pdwDuration = 0;
252+
return E_INVALIDARG;
253+
}
232254

233-
return E_NOTIMPL;
255+
*pdwDuration = intlist.iValues[1 + intlist.iValues[0] * (iStateIdFrom - 1) + (iStateIdTo - 1)];
256+
return S_OK;
234257
}
235-
#endif

dll/win32/uxtheme/system.c

Lines changed: 64 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -648,6 +648,37 @@ BOOL WINAPI IsThemeActive(void)
648648
return bActive;
649649
}
650650

651+
typedef HRESULT (WINAPI* DWMISCOMPOSITIONENABLED)(BOOL *enabled);
652+
653+
/************************************************************
654+
* IsCompositionActive (UXTHEME.@)
655+
*/
656+
BOOL WINAPI IsCompositionActive(void)
657+
{
658+
BOOL bIsCompositionActive;
659+
DWMISCOMPOSITIONENABLED pDwmIsCompositionEnabled;
660+
HMODULE hdwmapi = GetModuleHandleW(L"dwmapi.dll");
661+
662+
if (!hdwmapi)
663+
{
664+
hdwmapi = LoadLibraryW(L"dwmapi.dll");
665+
if (!hdwmapi)
666+
{
667+
ERR("Failed to load dwmapi\n");
668+
return FALSE;
669+
}
670+
671+
pDwmIsCompositionEnabled = (DWMISCOMPOSITIONENABLED)GetProcAddress(hdwmapi, "DwmIsCompositionEnabled");
672+
}
673+
if (!pDwmIsCompositionEnabled)
674+
return FALSE;
675+
676+
if (pDwmIsCompositionEnabled(&bIsCompositionActive) == S_OK)
677+
return bIsCompositionActive;
678+
679+
return FALSE;
680+
}
681+
651682
/***********************************************************************
652683
* EnableTheming (UXTHEME.@)
653684
*
@@ -847,9 +878,23 @@ HTHEME WINAPI OpenThemeDataFromFile(HTHEMEFILE hThemeFile, HWND hwnd, LPCWSTR ps
847878
/***********************************************************************
848879
* OpenThemeData (UXTHEME.@)
849880
*/
850-
HTHEME WINAPI OpenThemeData(HWND hwnd, LPCWSTR classlist)
881+
HTHEME WINAPI OpenThemeData(HWND hwnd, LPCWSTR pszClassList)
882+
{
883+
return OpenThemeDataInternal(g_ActiveThemeFile, hwnd, pszClassList, 0);
884+
}
885+
886+
/***********************************************************************
887+
* OpenThemeDataForDpi (UXTHEME.@)
888+
*/
889+
HTHEME
890+
WINAPI
891+
OpenThemeDataForDpi(
892+
_In_ HWND hwnd,
893+
_In_ LPCWSTR pszClassList,
894+
_In_ UINT dpi)
851895
{
852-
return OpenThemeDataInternal(g_ActiveThemeFile, hwnd, classlist, 0);
896+
FIXME("dpi (%x) is currently ignored", dpi);
897+
return OpenThemeDataInternal(g_ActiveThemeFile, hwnd, pszClassList, 0);
853898
}
854899

855900
/***********************************************************************
@@ -903,6 +948,23 @@ HRESULT WINAPI SetWindowTheme(HWND hwnd, LPCWSTR pszSubAppName,
903948
return hr;
904949
}
905950

951+
#if (DLL_EXPORT_VERSION >= _WIN32_WINNT_VISTA)
952+
/***********************************************************************
953+
* SetWindowThemeAttribute (UXTHEME.@)
954+
*/
955+
HRESULT
956+
WINAPI
957+
SetWindowThemeAttribute(
958+
_In_ HWND hwnd,
959+
_In_ enum WINDOWTHEMEATTRIBUTETYPE eAttribute,
960+
_In_ PVOID pvAttribute,
961+
_In_ DWORD cbAttribute)
962+
{
963+
FIXME("(%p,%d,%p,%ld): stub\n", hwnd, eAttribute, pvAttribute, cbAttribute);
964+
return E_NOTIMPL;
965+
}
966+
#endif /* (DLL_EXPORT_VERSION >= _WIN32_WINNT_VISTA) */
967+
906968
/***********************************************************************
907969
* GetCurrentThemeName (UXTHEME.@)
908970
*/

0 commit comments

Comments
 (0)