xref: /reactos/dll/directx/wine/d3dx9_36/line.c (revision 4561998a)
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 "config.h"
21 #include "wine/port.h"
22 
23 #include "d3dx9_private.h"
24 
25 WINE_DEFAULT_DEBUG_CHANNEL(d3dx);
26 
27 struct d3dx9_line
28 {
29     ID3DXLine ID3DXLine_iface;
30     LONG ref;
31 
32     IDirect3DDevice9 *device;
33     IDirect3DStateBlock9 *state;
34 };
35 
36 static inline struct d3dx9_line *impl_from_ID3DXLine(ID3DXLine *iface)
37 {
38     return CONTAINING_RECORD(iface, struct d3dx9_line, ID3DXLine_iface);
39 }
40 
41 static HRESULT WINAPI d3dx9_line_QueryInterface(ID3DXLine *iface, REFIID riid, void **out)
42 {
43     TRACE("iface %p, riid %s, out %p.\n", iface, debugstr_guid(riid), out);
44 
45     if (IsEqualGUID(riid, &IID_ID3DXLine)
46             || IsEqualGUID(riid, &IID_IUnknown))
47     {
48         ID3DXLine_AddRef(iface);
49         *out = iface;
50         return S_OK;
51     }
52 
53     WARN("%s not implemented, returning E_NOINTERFACE.\n", debugstr_guid(riid));
54 
55     *out = NULL;
56     return E_NOINTERFACE;
57 }
58 
59 static ULONG WINAPI d3dx9_line_AddRef(ID3DXLine *iface)
60 {
61     struct d3dx9_line *line = impl_from_ID3DXLine(iface);
62     ULONG refcount = InterlockedIncrement(&line->ref);
63 
64     TRACE("%p increasing refcount to %u.\n", line, refcount);
65 
66     return refcount;
67 }
68 
69 static ULONG WINAPI d3dx9_line_Release(ID3DXLine *iface)
70 {
71     struct d3dx9_line *line = impl_from_ID3DXLine(iface);
72     ULONG refcount = InterlockedDecrement(&line->ref);
73 
74     TRACE("%p decreasing refcount to %u.\n", line, refcount);
75 
76     if (!refcount)
77     {
78         IDirect3DDevice9_Release(line->device);
79         HeapFree(GetProcessHeap(), 0, line);
80     }
81 
82     return refcount;
83 }
84 
85 static HRESULT WINAPI d3dx9_line_GetDevice(struct ID3DXLine *iface, struct IDirect3DDevice9 **device)
86 {
87     struct d3dx9_line *line = impl_from_ID3DXLine(iface);
88 
89     TRACE("iface %p, device %p.\n", iface, line);
90 
91     if (!device)
92         return D3DERR_INVALIDCALL;
93 
94     *device = line->device;
95     IDirect3DDevice9_AddRef(line->device);
96 
97     return D3D_OK;
98 }
99 
100 static HRESULT WINAPI d3dx9_line_Begin(ID3DXLine *iface)
101 {
102     struct d3dx9_line *line = impl_from_ID3DXLine(iface);
103     D3DXMATRIX identity, projection;
104     D3DVIEWPORT9 vp;
105 
106     TRACE("iface %p.\n", iface);
107 
108     if (line->state)
109         return D3DERR_INVALIDCALL;
110 
111     if (FAILED(IDirect3DDevice9_CreateStateBlock(line->device, D3DSBT_ALL, &line->state)))
112         return D3DXERR_INVALIDDATA;
113 
114     if (FAILED(IDirect3DDevice9_GetViewport(line->device, &vp)))
115         goto failed;
116 
117     D3DXMatrixIdentity(&identity);
118     D3DXMatrixOrthoOffCenterLH(&projection, 0.0, (FLOAT)vp.Width, (FLOAT)vp.Height, 0.0, 0.0, 1.0);
119 
120     if (FAILED(IDirect3DDevice9_SetTransform(line->device, D3DTS_WORLD, &identity)))
121         goto failed;
122     if (FAILED(IDirect3DDevice9_SetTransform(line->device, D3DTS_VIEW, &identity)))
123         goto failed;
124     if (FAILED(IDirect3DDevice9_SetTransform(line->device, D3DTS_PROJECTION, &projection)))
125         goto failed;
126 
127     if (FAILED(IDirect3DDevice9_SetRenderState(line->device, D3DRS_LIGHTING, FALSE)))
128         goto failed;
129     if (FAILED(IDirect3DDevice9_SetRenderState(line->device, D3DRS_FOGENABLE, FALSE)))
130         goto failed;
131     if (FAILED(IDirect3DDevice9_SetRenderState(line->device, D3DRS_SHADEMODE, D3DSHADE_FLAT)))
132         goto failed;
133     if (FAILED(IDirect3DDevice9_SetRenderState(line->device, D3DRS_ALPHABLENDENABLE, TRUE)))
134         goto failed;
135     if (FAILED(IDirect3DDevice9_SetRenderState(line->device, D3DRS_SRCBLEND, D3DBLEND_SRCALPHA)))
136         goto failed;
137     if (FAILED(IDirect3DDevice9_SetRenderState(line->device, D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA)))
138         goto failed;
139 
140     return D3D_OK;
141 
142 failed:
143     IDirect3DStateBlock9_Apply(line->state);
144     IDirect3DStateBlock9_Release(line->state);
145     line->state = NULL;
146     return D3DXERR_INVALIDDATA;
147 }
148 
149 static HRESULT WINAPI d3dx9_line_Draw(ID3DXLine *iface, const D3DXVECTOR2 *vertex_list,
150         DWORD vertex_list_count, D3DCOLOR color)
151 {
152     FIXME("iface %p, vertex_list %p, vertex_list_count %u, color 0x%08x stub!\n",
153             iface, vertex_list, vertex_list_count, color);
154 
155     return E_NOTIMPL;
156 }
157 
158 static HRESULT WINAPI d3dx9_line_DrawTransform(ID3DXLine *iface, const D3DXVECTOR3 *vertex_list,
159         DWORD vertex_list_count, const D3DXMATRIX *transform, D3DCOLOR color)
160 {
161     FIXME("iface %p, vertex_list %p, vertex_list_count %u, transform %p, color 0x%08x stub!\n",
162             iface, vertex_list, vertex_list_count, transform, color);
163 
164     return E_NOTIMPL;
165 }
166 
167 static HRESULT WINAPI d3dx9_line_SetPattern(ID3DXLine *iface, DWORD pattern)
168 {
169     FIXME("iface %p, pattern 0x%08x stub!\n", iface, pattern);
170 
171     return E_NOTIMPL;
172 }
173 
174 static DWORD WINAPI d3dx9_line_GetPattern(ID3DXLine *iface)
175 {
176     FIXME("iface %p stub!\n", iface);
177 
178     return 0xffffffff;
179 }
180 
181 static HRESULT WINAPI d3dx9_line_SetPatternScale(ID3DXLine *iface, float scale)
182 {
183     FIXME("iface %p, scale %.8e stub!\n", iface, scale);
184 
185     return E_NOTIMPL;
186 }
187 
188 static float WINAPI d3dx9_line_GetPatternScale(ID3DXLine *iface)
189 {
190     FIXME("iface %p stub!\n", iface);
191 
192     return 1.0f;
193 }
194 
195 static HRESULT WINAPI d3dx9_line_SetWidth(ID3DXLine *iface, float width)
196 {
197     FIXME("iface %p, width %.8e stub!\n", iface, width);
198 
199     return E_NOTIMPL;
200 }
201 
202 static float WINAPI d3dx9_line_GetWidth(ID3DXLine *iface)
203 {
204     FIXME("iface %p stub!\n", iface);
205 
206     return 1.0f;
207 }
208 
209 static HRESULT WINAPI d3dx9_line_SetAntialias(ID3DXLine *iface, BOOL antialias)
210 {
211     FIXME("iface %p, antialias %#x stub!\n", iface, antialias);
212 
213     return E_NOTIMPL;
214 }
215 
216 static BOOL WINAPI d3dx9_line_GetAntialias(ID3DXLine *iface)
217 {
218     FIXME("iface %p stub!\n", iface);
219 
220     return FALSE;
221 }
222 
223 static HRESULT WINAPI d3dx9_line_SetGLLines(ID3DXLine *iface, BOOL gl_lines)
224 {
225     FIXME("iface %p, gl_lines %#x stub!\n", iface, gl_lines);
226 
227     return E_NOTIMPL;
228 }
229 
230 static BOOL WINAPI d3dx9_line_GetGLLines(ID3DXLine *iface)
231 {
232     FIXME("iface %p stub!\n", iface);
233 
234     return FALSE;
235 }
236 
237 static HRESULT WINAPI d3dx9_line_End(ID3DXLine *iface)
238 {
239     struct d3dx9_line *line = impl_from_ID3DXLine(iface);
240 
241     HRESULT hr;
242 
243     TRACE("iface %p.\n", iface);
244 
245     if (!line->state)
246         return D3DERR_INVALIDCALL;
247 
248     hr = IDirect3DStateBlock9_Apply(line->state);
249     IDirect3DStateBlock9_Release(line->state);
250     line->state = NULL;
251 
252     if (FAILED(hr))
253         return D3DXERR_INVALIDDATA;
254 
255     return D3D_OK;
256 }
257 
258 static HRESULT WINAPI d3dx9_line_OnLostDevice(ID3DXLine *iface)
259 {
260     FIXME("iface %p stub!\n", iface);
261 
262     return E_NOTIMPL;
263 }
264 static HRESULT WINAPI d3dx9_line_OnResetDevice(ID3DXLine *iface)
265 {
266     FIXME("iface %p stub!\n", iface);
267 
268     return E_NOTIMPL;
269 }
270 
271 static const struct ID3DXLineVtbl d3dx9_line_vtbl =
272 {
273     d3dx9_line_QueryInterface,
274     d3dx9_line_AddRef,
275     d3dx9_line_Release,
276     d3dx9_line_GetDevice,
277     d3dx9_line_Begin,
278     d3dx9_line_Draw,
279     d3dx9_line_DrawTransform,
280     d3dx9_line_SetPattern,
281     d3dx9_line_GetPattern,
282     d3dx9_line_SetPatternScale,
283     d3dx9_line_GetPatternScale,
284     d3dx9_line_SetWidth,
285     d3dx9_line_GetWidth,
286     d3dx9_line_SetAntialias,
287     d3dx9_line_GetAntialias,
288     d3dx9_line_SetGLLines,
289     d3dx9_line_GetGLLines,
290     d3dx9_line_End,
291     d3dx9_line_OnLostDevice,
292     d3dx9_line_OnResetDevice,
293 };
294 
295 HRESULT WINAPI D3DXCreateLine(struct IDirect3DDevice9 *device, struct ID3DXLine **line)
296 {
297     struct d3dx9_line *object;
298 
299     TRACE("device %p, line %p.\n", device, line);
300 
301     if (!device || !line)
302         return D3DERR_INVALIDCALL;
303 
304     if (!(object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*object))))
305         return E_OUTOFMEMORY;
306 
307     object->ID3DXLine_iface.lpVtbl = &d3dx9_line_vtbl;
308     object->ref = 1;
309     object->device = device;
310     IDirect3DDevice9_AddRef(device);
311 
312     *line = &object->ID3DXLine_iface;
313 
314     return D3D_OK;
315 }
316