kernel32: Forward RtlRaiseException to ntdll on ARM.
[wine] / dlls / d3dx9_36 / line.c
1 /*
2  * Copyright 2010 Christian Costa
3  *
4  * This library is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU Lesser General Public
6  * License as published by the Free Software Foundation; either
7  * version 2.1 of the License, or (at your option) any later version.
8  *
9  * This library is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12  * Lesser General Public License for more details.
13  *
14  * You should have received a copy of the GNU Lesser General Public
15  * License along with this library; if not, write to the Free Software
16  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
17  *
18  */
19
20 #include "wine/debug.h"
21 #include "d3dx9_36_private.h"
22
23 WINE_DEFAULT_DEBUG_CHANNEL(d3dx);
24
25 static const struct ID3DXLineVtbl ID3DXLine_Vtbl;
26
27 typedef struct ID3DXLineImpl {
28     ID3DXLine ID3DXLine_iface;
29     LONG ref;
30
31     IDirect3DDevice9 *device;
32     IDirect3DStateBlock9 *state;
33 } ID3DXLineImpl;
34
35 static inline ID3DXLineImpl *impl_from_ID3DXLine(ID3DXLine *iface)
36 {
37     return CONTAINING_RECORD(iface, ID3DXLineImpl, ID3DXLine_iface);
38 }
39
40 /*** IUnknown methods ***/
41 static HRESULT WINAPI ID3DXLineImpl_QueryInterface(ID3DXLine* iface, REFIID riid, LPVOID* object)
42 {
43     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
44
45     TRACE("(%p)->(%s, %p)\n", This, debugstr_guid(riid), object);
46
47     if (IsEqualGUID(riid, &IID_IUnknown) ||
48         IsEqualGUID(riid, &IID_ID3DXLine))
49     {
50         ID3DXLine_AddRef(iface);
51         *object = This;
52         return S_OK;
53     }
54
55     ERR("Interface %s not found\n", debugstr_guid(riid));
56
57     return E_NOINTERFACE;
58 }
59
60 static ULONG WINAPI ID3DXLineImpl_AddRef(ID3DXLine* iface)
61 {
62     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
63
64     TRACE("(%p)->(): AddRef from %u\n", This, This->ref);
65
66     return InterlockedIncrement(&This->ref);
67 }
68
69 static ULONG WINAPI ID3DXLineImpl_Release(ID3DXLine* iface)
70 {
71     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
72     ULONG ref = InterlockedDecrement(&This->ref);
73
74     TRACE("(%p)->(): Release from %u\n", This, ref + 1);
75
76     if (!ref)
77     {
78         IDirect3DDevice9_Release(This->device);
79         HeapFree(GetProcessHeap(), 0, This);
80     }
81
82     return ref;
83 }
84
85 /*** ID3DXLine methods ***/
86 static HRESULT WINAPI ID3DXLineImpl_GetDevice(ID3DXLine* iface, LPDIRECT3DDEVICE9* device)
87 {
88     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
89
90     TRACE ("(%p)->(%p): relay\n", This, device);
91
92     if (device == NULL) return D3DERR_INVALIDCALL;
93
94     *device = This->device;
95     IDirect3DDevice9_AddRef(This->device);
96
97     return D3D_OK;
98 }
99
100 static HRESULT WINAPI ID3DXLineImpl_Begin(ID3DXLine* iface)
101 {
102     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
103
104     HRESULT hr;
105     D3DXMATRIX identity, projection;
106     D3DVIEWPORT9 vp;
107
108     TRACE ("(%p)->()\n", This);
109
110     if (This->state != NULL) /* We already began. Return error. */
111         return D3DERR_INVALIDCALL;
112
113     hr = IDirect3DDevice9_CreateStateBlock(This->device, D3DSBT_ALL, &This->state);
114     if (FAILED(hr)) return D3DXERR_INVALIDDATA;
115
116     hr = IDirect3DDevice9_GetViewport(This->device, &vp);
117     if (FAILED(hr)) goto failed;
118
119     D3DXMatrixIdentity(&identity);
120     D3DXMatrixOrthoOffCenterLH(&projection,
121                                0.0, vp.Width, /* Min and max x */
122                                vp.Height, 0.0, /* Min and max y. Screen y is on top so this is inverted */
123                                0.0, 1.0); /* Min and max z */
124
125     hr = IDirect3DDevice9_SetTransform(This->device, D3DTS_WORLD, &identity);
126     if (FAILED(hr)) goto failed;
127
128     hr = IDirect3DDevice9_SetTransform(This->device, D3DTS_VIEW, &identity);
129     if (FAILED(hr)) goto failed;
130
131     hr = IDirect3DDevice9_SetTransform(This->device, D3DTS_PROJECTION, &projection);
132     if (FAILED(hr)) goto failed;
133
134     /* Windows sets similar states so we do the same */
135
136     hr = IDirect3DDevice9_SetRenderState(This->device, D3DRS_LIGHTING, FALSE);
137     if (FAILED(hr)) goto failed;
138
139     hr = IDirect3DDevice9_SetRenderState(This->device, D3DRS_FOGENABLE, FALSE);
140     if (FAILED(hr)) goto failed;
141
142     hr = IDirect3DDevice9_SetRenderState(This->device, D3DRS_SHADEMODE, D3DSHADE_FLAT);
143     if (FAILED(hr)) goto failed;
144
145     hr = IDirect3DDevice9_SetRenderState(This->device, D3DRS_ALPHABLENDENABLE, TRUE);
146     if (FAILED(hr)) goto failed;
147
148     hr = IDirect3DDevice9_SetRenderState(This->device, D3DRS_SRCBLEND, D3DBLEND_SRCALPHA);
149     if (FAILED(hr)) goto failed;
150
151     hr = IDirect3DDevice9_SetRenderState(This->device, D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA);
152     if (FAILED(hr)) goto failed;
153
154     return D3D_OK;
155 failed:
156     IDirect3DStateBlock9_Apply(This->state);
157     IDirect3DStateBlock9_Release(This->state);
158     This->state = NULL;
159     return D3DXERR_INVALIDDATA;
160 }
161
162 static HRESULT WINAPI ID3DXLineImpl_Draw(ID3DXLine* iface, CONST D3DXVECTOR2* vertexlist, DWORD vertexlistcount, D3DCOLOR color)
163 {
164     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
165
166     FIXME("(%p)->(%p, %u, %#x): stub\n", This, vertexlist, vertexlistcount, color);
167
168     return E_NOTIMPL;
169 }
170
171 static HRESULT WINAPI ID3DXLineImpl_DrawTransform(ID3DXLine* iface, CONST D3DXVECTOR3* vertexlist, DWORD vertexlistcount,
172                                                   CONST D3DXMATRIX* transform, D3DCOLOR color)
173 {
174     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
175
176     FIXME("(%p)->(%p, %u, %p, %#x): stub\n", This, vertexlist, vertexlistcount, transform, color);
177
178     return E_NOTIMPL;
179 }
180
181 static HRESULT WINAPI ID3DXLineImpl_SetPattern(ID3DXLine* iface, DWORD pattern)
182 {
183     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
184
185     FIXME("(%p)->(%#x): stub\n", This, pattern);
186
187     return E_NOTIMPL;
188 }
189
190 static DWORD WINAPI ID3DXLineImpl_GetPattern(ID3DXLine* iface)
191 {
192     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
193
194     FIXME("(%p)->(): stub\n", This);
195
196     return 0xFFFFFFFF;
197 }
198
199 static HRESULT WINAPI ID3DXLineImpl_SetPatternScale(ID3DXLine* iface, FLOAT scale)
200 {
201     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
202
203     FIXME("(%p)->(%f): stub\n", This, scale);
204
205     return E_NOTIMPL;
206 }
207
208 static FLOAT WINAPI ID3DXLineImpl_GetPatternScale(ID3DXLine* iface)
209 {
210     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
211
212     FIXME("(%p)->(): stub\n", This);
213
214     return 1.0f;
215 }
216
217 static HRESULT WINAPI ID3DXLineImpl_SetWidth(ID3DXLine* iface, FLOAT width)
218 {
219     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
220
221     FIXME("(%p)->(%f): stub\n", This, width);
222
223     return E_NOTIMPL;
224 }
225
226 static FLOAT WINAPI ID3DXLineImpl_GetWidth(ID3DXLine* iface)
227 {
228     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
229
230     FIXME("(%p)->(): stub\n", This);
231
232     return 1.0f;
233 }
234
235 static HRESULT WINAPI ID3DXLineImpl_SetAntialias(ID3DXLine* iface, BOOL antialias)
236 {
237     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
238
239     FIXME("(%p)->(%u): stub\n", This, antialias);
240
241     return E_NOTIMPL;
242 }
243
244 static BOOL WINAPI ID3DXLineImpl_GetAntialias(ID3DXLine* iface)
245 {
246     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
247
248     FIXME("(%p)->(): stub\n", This);
249
250     return FALSE;
251 }
252
253 static HRESULT WINAPI ID3DXLineImpl_SetGLLines(ID3DXLine* iface, BOOL gl_lines)
254 {
255     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
256
257     FIXME("(%p)->(%u): stub\n", This, gl_lines);
258
259     return E_NOTIMPL;
260 }
261
262 static BOOL WINAPI ID3DXLineImpl_GetGLLines(ID3DXLine* iface)
263 {
264     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
265
266     FIXME("(%p)->(): stub\n", This);
267
268     return FALSE;
269 }
270
271 static HRESULT WINAPI ID3DXLineImpl_End(ID3DXLine* iface)
272 {
273     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
274
275     HRESULT hr;
276
277     TRACE ("(%p)->()\n", This);
278
279     if (This->state == NULL) /* We haven't begun yet. */
280         return D3DERR_INVALIDCALL;
281
282     hr = IDirect3DStateBlock9_Apply(This->state);
283     IDirect3DStateBlock9_Release(This->state);
284     This->state = NULL;
285
286     if (FAILED(hr)) return D3DXERR_INVALIDDATA;
287     else return D3D_OK;
288 }
289
290 static HRESULT WINAPI ID3DXLineImpl_OnLostDevice(ID3DXLine* iface)
291 {
292     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
293
294     FIXME("(%p)->(): stub\n", This);
295
296     return E_NOTIMPL;
297 }
298 static HRESULT WINAPI ID3DXLineImpl_OnResetDevice(ID3DXLine* iface)
299 {
300     ID3DXLineImpl *This = impl_from_ID3DXLine(iface);
301
302     FIXME("(%p)->(): stub\n", This);
303
304     return E_NOTIMPL;
305 }
306
307 static const struct ID3DXLineVtbl ID3DXLine_Vtbl =
308 {
309     /*** IUnknown methods ***/
310     ID3DXLineImpl_QueryInterface,
311     ID3DXLineImpl_AddRef,
312     ID3DXLineImpl_Release,
313     /*** ID3DXLine methods ***/
314     ID3DXLineImpl_GetDevice,
315     ID3DXLineImpl_Begin,
316     ID3DXLineImpl_Draw,
317     ID3DXLineImpl_DrawTransform,
318     ID3DXLineImpl_SetPattern,
319     ID3DXLineImpl_GetPattern,
320     ID3DXLineImpl_SetPatternScale,
321     ID3DXLineImpl_GetPatternScale,
322     ID3DXLineImpl_SetWidth,
323     ID3DXLineImpl_GetWidth,
324     ID3DXLineImpl_SetAntialias,
325     ID3DXLineImpl_GetAntialias,
326     ID3DXLineImpl_SetGLLines,
327     ID3DXLineImpl_GetGLLines,
328     ID3DXLineImpl_End,
329     ID3DXLineImpl_OnLostDevice,
330     ID3DXLineImpl_OnResetDevice
331 };
332
333 HRESULT WINAPI D3DXCreateLine(LPDIRECT3DDEVICE9 device, LPD3DXLINE* line)
334 {
335     ID3DXLineImpl* object;
336
337     TRACE("(%p, %p)\n", device, line);
338
339     if (!device || !line)
340         return D3DERR_INVALIDCALL;
341
342     object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(ID3DXLineImpl));
343     if (!object)
344     {
345         ERR("Out of memory\n");
346         return E_OUTOFMEMORY;
347     }
348
349     object->ID3DXLine_iface.lpVtbl = &ID3DXLine_Vtbl;
350     object->ref = 1;
351     object->device = device;
352     object->state = NULL; /* We only initialize it on Begin */
353     IDirect3DDevice9_AddRef(device);
354
355     *line = &object->ID3DXLine_iface;
356
357     return D3D_OK;
358 }