dinput: Stub IDirectInputJoyConfig8 interface.
[wine] / dlls / ddraw / clipper.c
1 /* DirectDrawClipper implementation
2  *
3  * Copyright 2000 (c) Marcus Meissner
4  * Copyright 2000 (c) TransGaming Technologies Inc.
5  * Copyright 2006 (c) Stefan Dösinger
6  *
7  * This library is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU Lesser General Public
9  * License as published by the Free Software Foundation; either
10  * version 2.1 of the License, or (at your option) any later version.
11  *
12  * This library is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15  * Lesser General Public License for more details.
16  *
17  * You should have received a copy of the GNU Lesser General Public
18  * License along with this library; if not, write to the Free Software
19  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
20  */
21
22 #include "config.h"
23 #include "wine/port.h"
24
25 #include "ddraw_private.h"
26
27 WINE_DEFAULT_DEBUG_CHANNEL(ddraw);
28
29 static inline IDirectDrawClipperImpl *impl_from_IDirectDrawClipper(IDirectDrawClipper *iface)
30 {
31     return CONTAINING_RECORD(iface, IDirectDrawClipperImpl, IDirectDrawClipper_iface);
32 }
33
34 /*****************************************************************************
35  * IDirectDrawClipper::QueryInterface
36  *
37  * Can query the IUnknown and IDirectDrawClipper interface from a
38  * Clipper object. The IUnknown Interface is equal to the IDirectDrawClipper
39  * interface. Can't create other interfaces.
40  *
41  * Arguments:
42  *  riid: Interface id asked for
43  *  ppvObj: Returns the pointer to the interface
44  *
45  * Return values:
46  *  DD_OK on success
47  *  E_NOINTERFACE if the requested interface wasn't found.
48  *
49  *****************************************************************************/
50 static HRESULT WINAPI IDirectDrawClipperImpl_QueryInterface(IDirectDrawClipper *iface, REFIID riid,
51         void **ppvObj)
52 {
53
54     TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), ppvObj);
55
56     if (IsEqualGUID(&IID_IDirectDrawClipper, riid)
57             || IsEqualGUID(&IID_IUnknown, riid))
58     {
59         IUnknown_AddRef(iface);
60         *ppvObj = iface;
61         return S_OK;
62     }
63
64     return E_NOINTERFACE;
65 }
66
67 /*****************************************************************************
68  * IDirectDrawClipper::AddRef
69  *
70  * Increases the reference count of the interface, returns the new count
71  *
72  *****************************************************************************/
73 static ULONG WINAPI IDirectDrawClipperImpl_AddRef(IDirectDrawClipper *iface)
74 {
75     IDirectDrawClipperImpl *This = impl_from_IDirectDrawClipper(iface);
76     ULONG ref = InterlockedIncrement(&This->ref);
77
78     TRACE("%p increasing refcount to %u.\n", This, ref);
79
80     return ref;
81 }
82
83 /*****************************************************************************
84  * IDirectDrawClipper::Release
85  *
86  * Decreases the reference count of the interface, returns the new count
87  * If the refcount is decreased to 0, the interface is destroyed.
88  *
89  *****************************************************************************/
90 static ULONG WINAPI IDirectDrawClipperImpl_Release(IDirectDrawClipper *iface)
91 {
92     IDirectDrawClipperImpl *This = impl_from_IDirectDrawClipper(iface);
93     ULONG ref = InterlockedDecrement(&This->ref);
94
95     TRACE("%p decreasing refcount to %u.\n", This, ref);
96
97     if (ref == 0)
98     {
99         wined3d_mutex_lock();
100         wined3d_clipper_decref(This->wineD3DClipper);
101         wined3d_mutex_unlock();
102         HeapFree(GetProcessHeap(), 0, This);
103         return 0;
104     }
105     else return ref;
106 }
107
108 /*****************************************************************************
109  * IDirectDrawClipper::SetHWnd
110  *
111  * Assigns a hWnd to the clipper interface.
112  *
113  * Arguments:
114  *  Flags: Unsupported so far
115  *  hWnd: The hWnd to set
116  *
117  * Return values:
118  *  DD_OK on success
119  *  DDERR_INVALIDPARAMS if Flags was != 0
120  *
121  *****************************************************************************/
122
123 static HRESULT WINAPI IDirectDrawClipperImpl_SetHWnd(IDirectDrawClipper *iface, DWORD dwFlags,
124         HWND hWnd)
125 {
126     IDirectDrawClipperImpl *This = impl_from_IDirectDrawClipper(iface);
127     HRESULT hr;
128
129     TRACE("iface %p, flags %#x, window %p.\n", iface, dwFlags, hWnd);
130
131     wined3d_mutex_lock();
132     hr = wined3d_clipper_set_window(This->wineD3DClipper, dwFlags, hWnd);
133     wined3d_mutex_unlock();
134
135     switch(hr)
136     {
137         case WINED3DERR_INVALIDCALL:        return DDERR_INVALIDPARAMS;
138         default:                            return hr;
139     }
140 }
141
142 /*****************************************************************************
143  * IDirectDrawClipper::GetClipList
144  *
145  * Retrieve a copy of the clip list
146  *
147  * Arguments:
148  *  Rect: Rectangle to be used to clip the clip list or NULL for the
149  *        entire clip list
150  *  ClipList: structure for the resulting copy of the clip list.
151  *            If NULL, fills Size up to the number of bytes necessary to hold
152  *            the entire clip.
153  *  Size: Size of resulting clip list; size of the buffer at ClipList
154  *        or, if ClipList is NULL, receives the required size of the buffer
155  *        in bytes
156  *
157  * RETURNS
158  *  Either DD_OK or DDERR_*
159  ************************************************************************/
160 static HRESULT WINAPI IDirectDrawClipperImpl_GetClipList(IDirectDrawClipper *iface, RECT *lpRect,
161         RGNDATA *lpClipList, DWORD *lpdwSize)
162 {
163     IDirectDrawClipperImpl *This = impl_from_IDirectDrawClipper(iface);
164     HRESULT hr;
165
166     TRACE("iface %p, rect %s, clip_list %p, clip_list_size %p.\n",
167             iface, wine_dbgstr_rect(lpRect), lpClipList, lpdwSize);
168
169     wined3d_mutex_lock();
170     hr = wined3d_clipper_get_clip_list(This->wineD3DClipper, lpRect, lpClipList, lpdwSize);
171     wined3d_mutex_unlock();
172
173     return hr;
174 }
175
176 /*****************************************************************************
177  * IDirectDrawClipper::SetClipList
178  *
179  * Sets or deletes (if lprgn is NULL) the clip list
180  *
181  * This implementation is a stub and returns DD_OK always to make the app
182  * happy.
183  *
184  * PARAMS
185  *  lprgn   Pointer to a LRGNDATA structure or NULL
186  *  dwFlags not used, must be 0
187  * RETURNS
188  *  Either DD_OK or DDERR_*
189  *****************************************************************************/
190 static HRESULT WINAPI IDirectDrawClipperImpl_SetClipList(IDirectDrawClipper *iface, RGNDATA *lprgn,
191         DWORD dwFlag)
192 {
193     IDirectDrawClipperImpl *This = impl_from_IDirectDrawClipper(iface);
194     HRESULT hr;
195
196     TRACE("iface %p, clip_list %p, flags %#x.\n", iface, lprgn, dwFlag);
197
198     wined3d_mutex_lock();
199     hr = wined3d_clipper_set_clip_list(This->wineD3DClipper, lprgn, dwFlag);
200     wined3d_mutex_unlock();
201
202     return hr;
203 }
204
205 /*****************************************************************************
206  * IDirectDrawClipper::GetHWnd
207  *
208  * Returns the hwnd assigned with SetHWnd
209  *
210  * Arguments:
211  *  hWndPtr: Address to store the HWND at
212  *
213  * Return values:
214  *  Always returns DD_OK;
215  *****************************************************************************/
216 static HRESULT WINAPI IDirectDrawClipperImpl_GetHWnd(IDirectDrawClipper *iface, HWND *hWndPtr)
217 {
218     IDirectDrawClipperImpl *This = impl_from_IDirectDrawClipper(iface);
219     HRESULT hr;
220
221     TRACE("iface %p, window %p.\n", iface, hWndPtr);
222
223     wined3d_mutex_lock();
224     hr = wined3d_clipper_get_window(This->wineD3DClipper, hWndPtr);
225     wined3d_mutex_unlock();
226
227     return hr;
228 }
229
230 /*****************************************************************************
231  * IDirectDrawClipper::Initialize
232  *
233  * Initializes the interface. Well, there isn't much to do for this
234  * implementation, but it stores the DirectDraw Interface.
235  *
236  * Arguments:
237  *  DD: Pointer to a IDirectDraw interface
238  *  Flags: Unsupported by now
239  *
240  * Return values:
241  *  DD_OK on success
242  *  DDERR_ALREADYINITIALIZED if this interface isn't initialized already
243  *****************************************************************************/
244 static HRESULT WINAPI IDirectDrawClipperImpl_Initialize(IDirectDrawClipper *iface,
245         IDirectDraw *ddraw, DWORD dwFlags)
246 {
247     IDirectDrawClipperImpl *This = impl_from_IDirectDrawClipper(iface);
248
249     TRACE("iface %p, ddraw %p, flags %#x.\n", iface, ddraw, dwFlags);
250
251     wined3d_mutex_lock();
252     if (This->initialized)
253     {
254         wined3d_mutex_unlock();
255         return DDERR_ALREADYINITIALIZED;
256     }
257
258     This->initialized = TRUE;
259     wined3d_mutex_unlock();
260
261     return DD_OK;
262 }
263
264 /*****************************************************************************
265  * IDirectDrawClipper::IsClipListChanged
266  *
267  * This function is a stub
268  *
269  * Arguments:
270  *  Changed:
271  *
272  * Return values:
273  *  DD_OK, because it's a stub
274  *****************************************************************************/
275 static HRESULT WINAPI IDirectDrawClipperImpl_IsClipListChanged(IDirectDrawClipper *iface,
276         BOOL *lpbChanged)
277 {
278     FIXME("iface %p, changed %p stub!\n", iface, lpbChanged);
279
280     /* XXX What is safest? */
281     *lpbChanged = FALSE;
282
283     return DD_OK;
284 }
285
286 /*****************************************************************************
287  * The VTable
288  *****************************************************************************/
289 static const struct IDirectDrawClipperVtbl ddraw_clipper_vtbl =
290 {
291     IDirectDrawClipperImpl_QueryInterface,
292     IDirectDrawClipperImpl_AddRef,
293     IDirectDrawClipperImpl_Release,
294     IDirectDrawClipperImpl_GetClipList,
295     IDirectDrawClipperImpl_GetHWnd,
296     IDirectDrawClipperImpl_Initialize,
297     IDirectDrawClipperImpl_IsClipListChanged,
298     IDirectDrawClipperImpl_SetClipList,
299     IDirectDrawClipperImpl_SetHWnd
300 };
301
302 HRESULT ddraw_clipper_init(IDirectDrawClipperImpl *clipper)
303 {
304     clipper->IDirectDrawClipper_iface.lpVtbl = &ddraw_clipper_vtbl;
305     clipper->ref = 1;
306     clipper->wineD3DClipper = wined3d_clipper_create();
307     if (!clipper->wineD3DClipper)
308     {
309         WARN("Failed to create wined3d clipper.\n");
310         return E_OUTOFMEMORY;
311     }
312
313     return DD_OK;
314 }
315
316 IDirectDrawClipperImpl *unsafe_impl_from_IDirectDrawClipper(IDirectDrawClipper *iface)
317 {
318     if (!iface)
319         return NULL;
320     assert(iface->lpVtbl == &ddraw_clipper_vtbl);
321
322     return impl_from_IDirectDrawClipper(iface);
323 }