d3d9/tests: Get rid of struct nvertex.
[wine.git] / dlls / d3d9 / tests / visual.c
blobe099f9c56671ce1442b3cb4b61683570de813e44
1 /*
2 * Copyright 2005, 2007-2008 Henri Verbeet
3 * Copyright (C) 2007-2013 Stefan Dösinger(for CodeWeavers)
4 * Copyright (C) 2008 Jason Green(for TransGaming)
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
21 /* This test framework allows limited testing of rendering results. Things are rendered, shown on
22 * the framebuffer, read back from there and compared to expected colors.
24 * However, neither d3d nor opengl is guaranteed to be pixel exact, and thus the capability of this test
25 * is rather limited. As a general guideline for adding tests, do not rely on corner pixels. Draw a big enough
26 * area which shows specific behavior(like a quad on the whole screen), and try to get resulting colors with
27 * all bits set or unset in all channels(like pure red, green, blue, white, black). Hopefully everything that
28 * causes visible results in games can be tested in a way that does not depend on pixel exactness
31 #define COBJMACROS
32 #include <d3d9.h>
33 #include "wine/test.h"
35 struct vec2
37 float x, y;
40 struct vec3
42 float x, y, z;
45 struct vec4
47 float x, y, z, w;
50 static HWND create_window(void)
52 WNDCLASSA wc = {0};
53 HWND ret;
54 wc.lpfnWndProc = DefWindowProcA;
55 wc.lpszClassName = "d3d9_test_wc";
56 RegisterClassA(&wc);
58 ret = CreateWindowA("d3d9_test_wc", "d3d9_test", WS_SYSMENU | WS_POPUP,
59 0, 0, 640, 480, 0, 0, 0, 0);
60 ShowWindow(ret, SW_SHOW);
61 return ret;
64 static BOOL color_match(D3DCOLOR c1, D3DCOLOR c2, BYTE max_diff)
66 if (abs((c1 & 0xff) - (c2 & 0xff)) > max_diff) return FALSE;
67 c1 >>= 8; c2 >>= 8;
68 if (abs((c1 & 0xff) - (c2 & 0xff)) > max_diff) return FALSE;
69 c1 >>= 8; c2 >>= 8;
70 if (abs((c1 & 0xff) - (c2 & 0xff)) > max_diff) return FALSE;
71 c1 >>= 8; c2 >>= 8;
72 if (abs((c1 & 0xff) - (c2 & 0xff)) > max_diff) return FALSE;
73 return TRUE;
76 /* Locks a given surface and returns the color at (x,y). It's the caller's
77 * responsibility to only pass in lockable surfaces and valid x,y coordinates */
78 static DWORD getPixelColorFromSurface(IDirect3DSurface9 *surface, UINT x, UINT y)
80 DWORD color;
81 HRESULT hr;
82 D3DSURFACE_DESC desc;
83 RECT rectToLock = {x, y, x+1, y+1};
84 D3DLOCKED_RECT lockedRect;
86 hr = IDirect3DSurface9_GetDesc(surface, &desc);
87 if(FAILED(hr)) /* This is not a test */
89 trace("Can't get the surface description, hr=%08x\n", hr);
90 return 0xdeadbeef;
93 hr = IDirect3DSurface9_LockRect(surface, &lockedRect, &rectToLock, D3DLOCK_READONLY);
94 if(FAILED(hr)) /* This is not a test */
96 trace("Can't lock the surface, hr=%08x\n", hr);
97 return 0xdeadbeef;
99 switch(desc.Format) {
100 case D3DFMT_A8R8G8B8:
102 color = ((DWORD *) lockedRect.pBits)[0] & 0xffffffff;
103 break;
105 default:
106 trace("Error: unknown surface format: %d\n", desc.Format);
107 color = 0xdeadbeef;
108 break;
110 hr = IDirect3DSurface9_UnlockRect(surface);
111 if(FAILED(hr))
113 trace("Can't unlock the surface, hr=%08x\n", hr);
115 return color;
118 static DWORD getPixelColor(IDirect3DDevice9 *device, UINT x, UINT y)
120 DWORD ret;
121 IDirect3DSurface9 *surf = NULL, *target = NULL;
122 HRESULT hr;
123 D3DLOCKED_RECT lockedRect;
124 RECT rectToLock = {x, y, x+1, y+1};
126 hr = IDirect3DDevice9_CreateOffscreenPlainSurface(device, 640, 480,
127 D3DFMT_A8R8G8B8, D3DPOOL_SYSTEMMEM, &surf, NULL);
128 if (FAILED(hr) || !surf)
130 trace("Can't create an offscreen plain surface to read the render target data, hr=%08x\n", hr);
131 return 0xdeadbeef;
134 hr = IDirect3DDevice9_GetRenderTarget(device, 0, &target);
135 if(FAILED(hr))
137 trace("Can't get the render target, hr=%08x\n", hr);
138 ret = 0xdeadbeed;
139 goto out;
142 hr = IDirect3DDevice9_GetRenderTargetData(device, target, surf);
143 if (FAILED(hr))
145 trace("Can't read the render target data, hr=%08x\n", hr);
146 ret = 0xdeadbeec;
147 goto out;
150 hr = IDirect3DSurface9_LockRect(surf, &lockedRect, &rectToLock, D3DLOCK_READONLY);
151 if(FAILED(hr))
153 trace("Can't lock the offscreen surface, hr=%08x\n", hr);
154 ret = 0xdeadbeeb;
155 goto out;
158 /* Remove the X channel for now. DirectX and OpenGL have different ideas how to treat it apparently, and it isn't
159 * really important for these tests
161 ret = ((DWORD *) lockedRect.pBits)[0] & 0x00ffffff;
162 hr = IDirect3DSurface9_UnlockRect(surf);
163 if(FAILED(hr))
165 trace("Can't unlock the offscreen surface, hr=%08x\n", hr);
168 out:
169 if(target) IDirect3DSurface9_Release(target);
170 if(surf) IDirect3DSurface9_Release(surf);
171 return ret;
174 static IDirect3DDevice9 *create_device(IDirect3D9 *d3d, HWND device_window, HWND focus_window, BOOL windowed)
176 D3DPRESENT_PARAMETERS present_parameters = {0};
177 IDirect3DDevice9 *device;
179 present_parameters.Windowed = windowed;
180 present_parameters.hDeviceWindow = device_window;
181 present_parameters.SwapEffect = D3DSWAPEFFECT_DISCARD;
182 present_parameters.BackBufferWidth = 640;
183 present_parameters.BackBufferHeight = 480;
184 present_parameters.BackBufferFormat = D3DFMT_A8R8G8B8;
185 present_parameters.EnableAutoDepthStencil = TRUE;
186 present_parameters.AutoDepthStencilFormat = D3DFMT_D24S8;
188 if (SUCCEEDED(IDirect3D9_CreateDevice(d3d, D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, focus_window,
189 D3DCREATE_HARDWARE_VERTEXPROCESSING, &present_parameters, &device)))
190 return device;
192 return NULL;
195 static void cleanup_device(IDirect3DDevice9 *device)
197 if (device)
199 D3DPRESENT_PARAMETERS present_parameters;
200 IDirect3DSwapChain9 *swapchain;
201 ULONG ref;
203 IDirect3DDevice9_GetSwapChain(device, 0, &swapchain);
204 IDirect3DSwapChain9_GetPresentParameters(swapchain, &present_parameters);
205 IDirect3DSwapChain9_Release(swapchain);
206 ref = IDirect3DDevice9_Release(device);
207 ok(ref == 0, "The device was not properly freed: refcount %u.\n", ref);
208 DestroyWindow(present_parameters.hDeviceWindow);
212 static void test_sanity(void)
214 IDirect3DDevice9 *device;
215 IDirect3D9 *d3d;
216 D3DCOLOR color;
217 ULONG refcount;
218 HWND window;
219 HRESULT hr;
221 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
222 0, 0, 640, 480, NULL, NULL, NULL, NULL);
223 d3d = Direct3DCreate9(D3D_SDK_VERSION);
224 ok(!!d3d, "Failed to create a D3D object.\n");
225 if (!(device = create_device(d3d, window, window, TRUE)))
227 skip("Failed to create a D3D device, skipping tests.\n");
228 goto done;
231 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffff0000, 1.0f, 0);
232 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
233 color = getPixelColor(device, 1, 1);
234 ok(color == 0x00ff0000, "Got unexpected color 0x%08x.\n", color);
236 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
237 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
239 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff00ddee, 0.0, 0);
240 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
241 color = getPixelColor(device, 639, 479);
242 ok(color == 0x0000ddee, "Got unexpected color 0x%08x.\n", color);
244 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
245 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
247 refcount = IDirect3DDevice9_Release(device);
248 ok(!refcount, "Device has %u references left.\n", refcount);
249 done:
250 IDirect3D9_Release(d3d);
251 DestroyWindow(window);
254 static void lighting_test(void)
256 DWORD nfvf = D3DFVF_XYZ | D3DFVF_DIFFUSE | D3DFVF_NORMAL;
257 DWORD fvf = D3DFVF_XYZ | D3DFVF_DIFFUSE;
258 IDirect3DDevice9 *device;
259 D3DMATERIAL9 material;
260 IDirect3D9 *d3d;
261 D3DCOLOR color;
262 ULONG refcount;
263 HWND window;
264 HRESULT hr;
266 static const D3DMATRIX mat =
268 1.0f, 0.0f, 0.0f, 0.0f,
269 0.0f, 1.0f, 0.0f, 0.0f,
270 0.0f, 0.0f, 1.0f, 0.0f,
271 0.0f, 0.0f, 0.0f, 1.0f,
272 }}};
273 static const struct
275 struct vec3 position;
276 DWORD diffuse;
278 unlitquad[] =
280 {{-1.0f, -1.0f, 0.1f}, 0xffff0000},
281 {{-1.0f, 0.0f, 0.1f}, 0xffff0000},
282 {{ 0.0f, 0.0f, 0.1f}, 0xffff0000},
283 {{ 0.0f, -1.0f, 0.1f}, 0xffff0000},
285 litquad[] =
287 {{-1.0f, 0.0f, 0.1f}, 0xff00ff00},
288 {{-1.0f, 1.0f, 0.1f}, 0xff00ff00},
289 {{ 0.0f, 1.0f, 0.1f}, 0xff00ff00},
290 {{ 0.0f, 0.0f, 0.1f}, 0xff00ff00},
292 lighting_test[] =
294 {{-1.0f, -1.0f, 0.1f}, 0x8000ff00},
295 {{ 1.0f, -1.0f, 0.1f}, 0x80000000},
296 {{-1.0f, 1.0f, 0.1f}, 0x8000ff00},
297 {{ 1.0f, 1.0f, 0.1f}, 0x80000000},
299 static const struct
301 struct vec3 position;
302 struct vec3 normal;
303 DWORD diffuse;
305 unlitnquad[] =
307 {{0.0f, -1.0f, 0.1f}, {1.0f, 1.0f, 1.0f}, 0xff0000ff},
308 {{0.0f, 0.0f, 0.1f}, {1.0f, 1.0f, 1.0f}, 0xff0000ff},
309 {{1.0f, 0.0f, 0.1f}, {1.0f, 1.0f, 1.0f}, 0xff0000ff},
310 {{1.0f, -1.0f, 0.1f}, {1.0f, 1.0f, 1.0f}, 0xff0000ff},
312 litnquad[] =
314 {{0.0f, 0.0f, 0.1f}, {1.0f, 1.0f, 1.0f}, 0xffffff00},
315 {{0.0f, 1.0f, 0.1f}, {1.0f, 1.0f, 1.0f}, 0xffffff00},
316 {{1.0f, 1.0f, 0.1f}, {1.0f, 1.0f, 1.0f}, 0xffffff00},
317 {{1.0f, 0.0f, 0.1f}, {1.0f, 1.0f, 1.0f}, 0xffffff00},
319 static const WORD Indices[] = {0, 1, 2, 2, 3, 0};
321 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
322 0, 0, 640, 480, NULL, NULL, NULL, NULL);
323 d3d = Direct3DCreate9(D3D_SDK_VERSION);
324 ok(!!d3d, "Failed to create a D3D object.\n");
325 if (!(device = create_device(d3d, window, window, TRUE)))
327 skip("Failed to create a D3D device, skipping tests.\n");
328 goto done;
331 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffffffff, 0.0, 0);
332 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
334 /* Setup some states that may cause issues */
335 hr = IDirect3DDevice9_SetTransform(device, D3DTS_WORLDMATRIX(0), &mat);
336 ok(hr == D3D_OK, "IDirect3DDevice9_SetTransform returned %08x\n", hr);
337 hr = IDirect3DDevice9_SetTransform(device, D3DTS_VIEW, &mat);
338 ok(hr == D3D_OK, "IDirect3DDevice9_SetTransform returned %08x\n", hr);
339 hr = IDirect3DDevice9_SetTransform(device, D3DTS_PROJECTION, &mat);
340 ok(hr == D3D_OK, "IDirect3DDevice9_SetTransform returned %08x\n", hr);
341 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_CLIPPING, FALSE);
342 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
343 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, FALSE);
344 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
345 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGENABLE, FALSE);
346 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
347 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_STENCILENABLE, FALSE);
348 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
349 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ALPHATESTENABLE, FALSE);
350 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
351 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ALPHABLENDENABLE, FALSE);
352 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
353 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_SCISSORTESTENABLE, FALSE);
354 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
355 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_CULLMODE, D3DCULL_NONE);
356 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState failed with %08x\n", hr);
357 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_COLORWRITEENABLE, D3DCOLORWRITEENABLE_RED | D3DCOLORWRITEENABLE_GREEN | D3DCOLORWRITEENABLE_BLUE);
358 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState failed with %08x\n", hr);
360 hr = IDirect3DDevice9_SetFVF(device, 0);
361 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF returned %08x\n", hr);
363 hr = IDirect3DDevice9_SetFVF(device, fvf);
364 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF returned %08x\n", hr);
366 hr = IDirect3DDevice9_BeginScene(device);
367 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
369 /* No lights are defined... That means, lit vertices should be entirely black */
370 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
371 ok(SUCCEEDED(hr), "Failed to disable lighting, hr %#x.\n", hr);
372 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 4 /* NumVerts */,
373 2 /* PrimCount */, Indices, D3DFMT_INDEX16, unlitquad, sizeof(unlitquad[0]));
374 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
376 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, TRUE);
377 ok(SUCCEEDED(hr), "Failed to enable lighting, hr %#x.\n", hr);
378 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 4 /* NumVerts */,
379 2 /* PrimCount */, Indices, D3DFMT_INDEX16, litquad, sizeof(litquad[0]));
380 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
382 hr = IDirect3DDevice9_SetFVF(device, nfvf);
383 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
385 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
386 ok(SUCCEEDED(hr), "Failed to disable lighting, hr %#x.\n", hr);
387 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 4 /* NumVerts */,
388 2 /* PrimCount */, Indices, D3DFMT_INDEX16, unlitnquad, sizeof(unlitnquad[0]));
389 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
391 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, TRUE);
392 ok(SUCCEEDED(hr), "Failed to enable lighting, hr %#x.\n", hr);
393 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 4 /* NumVerts */,
394 2 /* PrimCount */, Indices, D3DFMT_INDEX16, litnquad, sizeof(litnquad[0]));
395 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
397 hr = IDirect3DDevice9_EndScene(device);
398 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
400 color = getPixelColor(device, 160, 360); /* Lower left quad - unlit without normals */
401 ok(color == 0x00ff0000, "Unlit quad without normals has color 0x%08x, expected 0x00ff0000.\n", color);
402 color = getPixelColor(device, 160, 120); /* Upper left quad - lit without normals */
403 ok(color == 0x00000000, "Lit quad without normals has color 0x%08x, expected 0x00000000.\n", color);
404 color = getPixelColor(device, 480, 360); /* Lower left quad - unlit with normals */
405 ok(color == 0x000000ff, "Unlit quad with normals has color 0x%08x, expected 0x000000ff.\n", color);
406 color = getPixelColor(device, 480, 120); /* Upper left quad - lit with normals */
407 ok(color == 0x00000000, "Lit quad with normals has color 0x%08x, expected 0x00000000.\n", color);
409 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
411 memset(&material, 0, sizeof(material));
412 material.Diffuse.r = 0.0;
413 material.Diffuse.g = 0.0;
414 material.Diffuse.b = 0.0;
415 material.Diffuse.a = 1.0;
416 material.Ambient.r = 0.0;
417 material.Ambient.g = 0.0;
418 material.Ambient.b = 0.0;
419 material.Ambient.a = 0.0;
420 material.Specular.r = 0.0;
421 material.Specular.g = 0.0;
422 material.Specular.b = 0.0;
423 material.Specular.a = 0.0;
424 material.Emissive.r = 0.0;
425 material.Emissive.g = 0.0;
426 material.Emissive.b = 0.0;
427 material.Emissive.a = 0.0;
428 material.Power = 0.0;
429 hr = IDirect3DDevice9_SetMaterial(device, &material);
430 ok(hr == D3D_OK, "IDirect3DDevice9_SetMaterial returned %08x\n", hr);
432 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_DIFFUSEMATERIALSOURCE, D3DMCS_MATERIAL);
433 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
434 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_SPECULARMATERIALSOURCE, D3DMCS_MATERIAL);
435 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
437 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
438 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState returned %08x\n", hr);
439 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_DIFFUSE | D3DTA_ALPHAREPLICATE);
440 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState returned %08x\n", hr);
442 hr = IDirect3DDevice9_BeginScene(device);
443 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
445 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
446 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
447 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, lighting_test, sizeof(lighting_test[0]));
448 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
450 hr = IDirect3DDevice9_EndScene(device);
451 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
453 color = getPixelColor(device, 320, 240);
454 ok(color == 0x00ffffff, "Lit vertex alpha test returned color %08x, expected 0x00ffffff\n", color);
455 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
457 refcount = IDirect3DDevice9_Release(device);
458 ok(!refcount, "Device has %u references left.\n", refcount);
459 done:
460 IDirect3D9_Release(d3d);
461 DestroyWindow(window);
464 static void clear_test(void)
466 /* Tests the correctness of clearing parameters */
467 HRESULT hr;
468 D3DRECT rect[2];
469 D3DRECT rect_negneg;
470 DWORD color;
471 D3DVIEWPORT9 old_vp, vp;
472 RECT scissor;
473 DWORD oldColorWrite;
474 BOOL invalid_clear_failed = FALSE;
475 IDirect3DDevice9 *device;
476 IDirect3D9 *d3d;
477 ULONG refcount;
478 HWND window;
480 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
481 0, 0, 640, 480, NULL, NULL, NULL, NULL);
482 d3d = Direct3DCreate9(D3D_SDK_VERSION);
483 ok(!!d3d, "Failed to create a D3D object.\n");
484 if (!(device = create_device(d3d, window, window, TRUE)))
486 skip("Failed to create a D3D device, skipping tests.\n");
487 goto done;
490 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffffffff, 0.0, 0);
491 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
493 /* Positive x, negative y */
494 rect[0].x1 = 0;
495 rect[0].y1 = 480;
496 rect[0].x2 = 320;
497 rect[0].y2 = 240;
499 /* Positive x, positive y */
500 rect[1].x1 = 0;
501 rect[1].y1 = 0;
502 rect[1].x2 = 320;
503 rect[1].y2 = 240;
504 /* Clear 2 rectangles with one call. The refrast returns an error in this case, every real driver tested so far
505 * returns D3D_OK, but ignores the rectangle silently
507 hr = IDirect3DDevice9_Clear(device, 2, rect, D3DCLEAR_TARGET, 0xffff0000, 0.0, 0);
508 ok(hr == D3D_OK || hr == D3DERR_INVALIDCALL, "IDirect3DDevice9_Clear failed with %08x\n", hr);
509 if(hr == D3DERR_INVALIDCALL) invalid_clear_failed = TRUE;
511 /* negative x, negative y */
512 rect_negneg.x1 = 640;
513 rect_negneg.y1 = 240;
514 rect_negneg.x2 = 320;
515 rect_negneg.y2 = 0;
516 hr = IDirect3DDevice9_Clear(device, 1, &rect_negneg, D3DCLEAR_TARGET, 0xff00ff00, 0.0, 0);
517 ok(hr == D3D_OK || hr == D3DERR_INVALIDCALL, "IDirect3DDevice9_Clear failed with %08x\n", hr);
518 if(hr == D3DERR_INVALIDCALL) invalid_clear_failed = TRUE;
520 color = getPixelColor(device, 160, 360); /* lower left quad */
521 ok(color == 0x00ffffff, "Clear rectangle 3(pos, neg) has color %08x\n", color);
522 color = getPixelColor(device, 160, 120); /* upper left quad */
523 if(invalid_clear_failed) {
524 /* If the negative rectangle was refused, the other rectangles in the list shouldn't be cleared either */
525 ok(color == 0x00ffffff, "Clear rectangle 1(pos, pos) has color %08x\n", color);
526 } else {
527 /* If the negative rectangle was dropped silently, the correct ones are cleared */
528 ok(color == 0x00ff0000, "Clear rectangle 1(pos, pos) has color %08x\n", color);
530 color = getPixelColor(device, 480, 360); /* lower right quad */
531 ok(color == 0x00ffffff, "Clear rectangle 4(NULL) has color %08x\n", color);
532 color = getPixelColor(device, 480, 120); /* upper right quad */
533 ok(color == 0x00ffffff, "Clear rectangle 4(neg, neg) has color %08x\n", color);
535 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
537 /* Hack to work around a nvidia windows driver bug. The clear below is supposed to
538 * clear the red quad in the top left part of the render target. For some reason it
539 * doesn't work if the clear color is 0xffffffff on some versions of the Nvidia Windows
540 * driver(tested on 8.17.12.5896, Win7). A clear with a different color works around
541 * this bug and fixes the clear with the white color. Even 0xfeffffff works, but let's
542 * pick some obvious value
544 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xdeadbabe, 0.0, 0);
545 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
547 /* Test how the viewport affects clears */
548 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffffffff, 0.0, 0);
549 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
550 hr = IDirect3DDevice9_GetViewport(device, &old_vp);
551 ok(hr == D3D_OK, "IDirect3DDevice9_GetViewport failed with %08x\n", hr);
553 vp.X = 160;
554 vp.Y = 120;
555 vp.Width = 160;
556 vp.Height = 120;
557 vp.MinZ = 0.0;
558 vp.MaxZ = 1.0;
559 hr = IDirect3DDevice9_SetViewport(device, &vp);
560 ok(hr == D3D_OK, "IDirect3DDevice9_SetViewport failed with %08x\n", hr);
561 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff0000ff, 0.0, 0);
562 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
564 vp.X = 320;
565 vp.Y = 240;
566 vp.Width = 320;
567 vp.Height = 240;
568 vp.MinZ = 0.0;
569 vp.MaxZ = 1.0;
570 hr = IDirect3DDevice9_SetViewport(device, &vp);
571 ok(hr == D3D_OK, "IDirect3DDevice9_SetViewport failed with %08x\n", hr);
572 rect[0].x1 = 160;
573 rect[0].y1 = 120;
574 rect[0].x2 = 480;
575 rect[0].y2 = 360;
576 hr = IDirect3DDevice9_Clear(device, 1, &rect[0], D3DCLEAR_TARGET, 0xff00ff00, 0.0, 0);
577 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
579 hr = IDirect3DDevice9_SetViewport(device, &old_vp);
580 ok(hr == D3D_OK, "IDirect3DDevice9_SetViewport failed with %08x\n", hr);
582 color = getPixelColor(device, 158, 118);
583 ok(color == 0x00ffffff, "(158,118) has color %08x\n", color);
584 color = getPixelColor(device, 162, 118);
585 ok(color == 0x00ffffff, "(162,118) has color %08x\n", color);
586 color = getPixelColor(device, 158, 122);
587 ok(color == 0x00ffffff, "(158,122) has color %08x\n", color);
588 color = getPixelColor(device, 162, 122);
589 ok(color == 0x000000ff, "(162,122) has color %08x\n", color);
591 color = getPixelColor(device, 318, 238);
592 ok(color == 0x000000ff, "(318,238) has color %08x\n", color);
593 color = getPixelColor(device, 322, 238);
594 ok(color == 0x00ffffff, "(322,328) has color %08x\n", color);
595 color = getPixelColor(device, 318, 242);
596 ok(color == 0x00ffffff, "(318,242) has color %08x\n", color);
597 color = getPixelColor(device, 322, 242);
598 ok(color == 0x0000ff00, "(322,242) has color %08x\n", color);
600 color = getPixelColor(device, 478, 358);
601 ok(color == 0x0000ff00, "(478,358 has color %08x\n", color);
602 color = getPixelColor(device, 482, 358);
603 ok(color == 0x00ffffff, "(482,358) has color %08x\n", color);
604 color = getPixelColor(device, 478, 362);
605 ok(color == 0x00ffffff, "(478,362) has color %08x\n", color);
606 color = getPixelColor(device, 482, 362);
607 ok(color == 0x00ffffff, "(482,362) has color %08x\n", color);
609 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
611 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffffffff, 0.0, 0);
612 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
614 scissor.left = 160;
615 scissor.right = 480;
616 scissor.top = 120;
617 scissor.bottom = 360;
618 hr = IDirect3DDevice9_SetScissorRect(device, &scissor);
619 ok(hr == D3D_OK, "IDirect3DDevice_SetScissorRect failed with %08x\n", hr);
620 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_SCISSORTESTENABLE, TRUE);
621 ok(hr == D3D_OK, "IDirect3DDevice_SetScissorRect failed with %08x\n", hr);
623 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff00ff00, 0.0, 0);
624 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
625 hr = IDirect3DDevice9_Clear(device, 1, &rect[1], D3DCLEAR_TARGET, 0xffff0000, 0.0, 0);
626 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
628 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_SCISSORTESTENABLE, FALSE);
629 ok(hr == D3D_OK, "IDirect3DDevice_SetScissorRect failed with %08x\n", hr);
631 color = getPixelColor(device, 158, 118);
632 ok(color == 0x00ffffff, "Pixel 158/118 has color %08x\n", color);
633 color = getPixelColor(device, 162, 118);
634 ok(color == 0x00ffffff, "Pixel 162/118 has color %08x\n", color);
635 color = getPixelColor(device, 158, 122);
636 ok(color == 0x00ffffff, "Pixel 158/122 has color %08x\n", color);
637 color = getPixelColor(device, 162, 122);
638 ok(color == 0x00ff0000, "Pixel 162/122 has color %08x\n", color);
640 color = getPixelColor(device, 158, 358);
641 ok(color == 0x00ffffff, "Pixel 158/358 has color %08x\n", color);
642 color = getPixelColor(device, 162, 358);
643 ok(color == 0x0000ff00, "Pixel 162/358 has color %08x\n", color);
644 color = getPixelColor(device, 158, 358);
645 ok(color == 0x00ffffff, "Pixel 158/358 has color %08x\n", color);
646 color = getPixelColor(device, 162, 362);
647 ok(color == 0x00ffffff, "Pixel 162/362 has color %08x\n", color);
649 color = getPixelColor(device, 478, 118);
650 ok(color == 0x00ffffff, "Pixel 158/118 has color %08x\n", color);
651 color = getPixelColor(device, 478, 122);
652 ok(color == 0x0000ff00, "Pixel 162/118 has color %08x\n", color);
653 color = getPixelColor(device, 482, 122);
654 ok(color == 0x00ffffff, "Pixel 158/122 has color %08x\n", color);
655 color = getPixelColor(device, 482, 358);
656 ok(color == 0x00ffffff, "Pixel 162/122 has color %08x\n", color);
658 color = getPixelColor(device, 478, 358);
659 ok(color == 0x0000ff00, "Pixel 478/358 has color %08x\n", color);
660 color = getPixelColor(device, 478, 362);
661 ok(color == 0x00ffffff, "Pixel 478/118 has color %08x\n", color);
662 color = getPixelColor(device, 482, 358);
663 ok(color == 0x00ffffff, "Pixel 482/122 has color %08x\n", color);
664 color = getPixelColor(device, 482, 362);
665 ok(color == 0x00ffffff, "Pixel 482/122 has color %08x\n", color);
667 color = getPixelColor(device, 318, 238);
668 ok(color == 0x00ff0000, "Pixel 318/238 has color %08x\n", color);
669 color = getPixelColor(device, 318, 242);
670 ok(color == 0x0000ff00, "Pixel 318/242 has color %08x\n", color);
671 color = getPixelColor(device, 322, 238);
672 ok(color == 0x0000ff00, "Pixel 322/238 has color %08x\n", color);
673 color = getPixelColor(device, 322, 242);
674 ok(color == 0x0000ff00, "Pixel 322/242 has color %08x\n", color);
676 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
678 hr = IDirect3DDevice9_GetRenderState(device, D3DRS_COLORWRITEENABLE, &oldColorWrite);
679 ok(hr == D3D_OK, "IDirect3DDevice9_GetRenderState failed with %08x\n", hr);
680 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_COLORWRITEENABLE, D3DCOLORWRITEENABLE_RED);
681 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState failed with %08x\n", hr);
683 /* Same nvidia windows driver trouble with white clears as earlier in the same test */
684 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xdeadbeef, 0.0, 0);
685 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
687 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffffffff, 0.0, 0);
688 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
690 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_COLORWRITEENABLE, oldColorWrite);
691 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState failed with %08x\n", hr);
693 /* Colorwriteenable does not affect the clear */
694 color = getPixelColor(device, 320, 240);
695 ok(color == 0x00ffffff, "Color write protected clear returned color %08x\n", color);
697 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
699 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0x00ffffff, 0.0, 0);
700 ok(SUCCEEDED(hr), "IDirect3DDevice9_Clear failed with %08x\n", hr);
702 rect[0].x1 = 0;
703 rect[0].y1 = 0;
704 rect[0].x2 = 640;
705 rect[0].y2 = 480;
706 hr = IDirect3DDevice9_Clear(device, 0, rect, D3DCLEAR_TARGET, 0x00ff0000, 0.0, 0);
707 ok(SUCCEEDED(hr), "IDirect3DDevice9_Clear failed with %08x\n", hr);
709 color = getPixelColor(device, 320, 240);
710 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0xff, 0xff, 0xff), 1),
711 "Clear with count = 0, rect != NULL has color %08x\n", color);
713 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
715 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffffffff, 0.0, 0);
716 ok(SUCCEEDED(hr), "IDirect3DDevice9_Clear failed with %08x\n", hr);
717 hr = IDirect3DDevice9_Clear(device, 1, NULL, D3DCLEAR_TARGET, 0xff00ff00, 0.0, 0);
718 ok(SUCCEEDED(hr), "IDirect3DDevice9_Clear failed with %08x\n", hr);
720 color = getPixelColor(device, 320, 240);
721 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x00, 0xff, 0x00), 1),
722 "Clear with count = 1, rect = NULL has color %08x\n", color);
724 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
726 refcount = IDirect3DDevice9_Release(device);
727 ok(!refcount, "Device has %u references left.\n", refcount);
728 done:
729 IDirect3D9_Release(d3d);
730 DestroyWindow(window);
733 static void color_fill_test(void)
735 IDirect3DSurface9 *offscreen_surface;
736 IDirect3DSurface9 *backbuffer;
737 IDirect3DSurface9 *rt_surface;
738 D3DCOLOR fill_color, color;
739 IDirect3DDevice9 *device;
740 IDirect3D9 *d3d;
741 ULONG refcount;
742 HWND window;
743 HRESULT hr;
745 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
746 0, 0, 640, 480, NULL, NULL, NULL, NULL);
747 d3d = Direct3DCreate9(D3D_SDK_VERSION);
748 ok(!!d3d, "Failed to create a D3D object.\n");
749 if (!(device = create_device(d3d, window, window, TRUE)))
751 skip("Failed to create a D3D device, skipping tests.\n");
752 goto done;
755 /* Test ColorFill on a the backbuffer (should pass) */
756 hr = IDirect3DDevice9_GetBackBuffer(device, 0, 0, D3DBACKBUFFER_TYPE_MONO, &backbuffer);
757 ok(hr == D3D_OK, "Can't get back buffer, hr = %08x\n", hr);
759 fill_color = 0x112233;
760 hr = IDirect3DDevice9_ColorFill(device, backbuffer, NULL, fill_color);
761 ok(SUCCEEDED(hr), "Color fill failed, hr %#x.\n", hr);
763 color = getPixelColor(device, 0, 0);
764 ok(color == fill_color, "Expected color %08x, got %08x\n", fill_color, color);
766 IDirect3DSurface9_Release(backbuffer);
768 /* Test ColorFill on a render target surface (should pass) */
769 hr = IDirect3DDevice9_CreateRenderTarget(device, 32, 32, D3DFMT_A8R8G8B8,
770 D3DMULTISAMPLE_NONE, 0, TRUE, &rt_surface, NULL );
771 ok(hr == D3D_OK, "Unable to create render target surface, hr = %08x\n", hr);
773 fill_color = 0x445566;
774 hr = IDirect3DDevice9_ColorFill(device, rt_surface, NULL, fill_color);
775 ok(SUCCEEDED(hr), "Color fill failed, hr %#x.\n", hr);
777 color = getPixelColorFromSurface(rt_surface, 0, 0);
778 ok(color == fill_color, "Expected color %08x, got %08x\n", fill_color, color);
780 IDirect3DSurface9_Release(rt_surface);
782 /* Test ColorFill on an offscreen plain surface in D3DPOOL_DEFAULT (should pass) */
783 hr = IDirect3DDevice9_CreateOffscreenPlainSurface(device, 32, 32,
784 D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &offscreen_surface, NULL);
785 ok(hr == D3D_OK, "Unable to create offscreen plain surface, hr = %08x\n", hr);
787 fill_color = 0x778899;
788 hr = IDirect3DDevice9_ColorFill(device, offscreen_surface, NULL, fill_color);
789 ok(SUCCEEDED(hr), "Color fill failed, hr %#x.\n", hr);
791 color = getPixelColorFromSurface(offscreen_surface, 0, 0);
792 ok(color == fill_color, "Expected color %08x, got %08x\n", fill_color, color);
794 IDirect3DSurface9_Release(offscreen_surface);
796 /* Try ColorFill on an offscreen surface in sysmem (should fail) */
797 hr = IDirect3DDevice9_CreateOffscreenPlainSurface(device, 32, 32,
798 D3DFMT_A8R8G8B8, D3DPOOL_SYSTEMMEM, &offscreen_surface, NULL);
799 ok(hr == D3D_OK, "Unable to create offscreen plain surface, hr = %08x\n", hr);
801 hr = IDirect3DDevice9_ColorFill(device, offscreen_surface, NULL, 0);
802 ok(hr == D3DERR_INVALIDCALL, "ColorFill on offscreen sysmem surface failed with hr = %08x\n", hr);
804 IDirect3DSurface9_Release(offscreen_surface);
806 refcount = IDirect3DDevice9_Release(device);
807 ok(!refcount, "Device has %u references left.\n", refcount);
808 done:
809 IDirect3D9_Release(d3d);
810 DestroyWindow(window);
814 * c7 mova ARGB mov ARGB
815 * -2.4 -2 0x00ffff00 -3 0x00ff0000
816 * -1.6 -2 0x00ffff00 -2 0x00ffff00
817 * -0.4 0 0x0000ffff -1 0x0000ff00
818 * 0.4 0 0x0000ffff 0 0x0000ffff
819 * 1.6 2 0x00ff00ff 1 0x000000ff
820 * 2.4 2 0x00ff00ff 2 0x00ff00ff
822 static void test_mova(void)
824 IDirect3DVertexDeclaration9 *vertex_declaration;
825 IDirect3DVertexShader9 *mova_shader;
826 IDirect3DVertexShader9 *mov_shader;
827 IDirect3DDevice9 *device;
828 unsigned int i, j;
829 IDirect3D9 *d3d;
830 ULONG refcount;
831 D3DCAPS9 caps;
832 HWND window;
833 HRESULT hr;
835 static const DWORD mova_test[] =
837 0xfffe0200, /* vs_2_0 */
838 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
839 0x05000051, 0xa00f0000, 0x3f800000, 0x00000000, 0x00000000, 0x3f800000, /* def c0, 1.0, 0.0, 0.0, 1.0 */
840 0x05000051, 0xa00f0001, 0x3f800000, 0x3f800000, 0x00000000, 0x3f800000, /* def c1, 1.0, 1.0, 0.0, 1.0 */
841 0x05000051, 0xa00f0002, 0x00000000, 0x3f800000, 0x00000000, 0x3f800000, /* def c2, 0.0, 1.0, 0.0, 1.0 */
842 0x05000051, 0xa00f0003, 0x00000000, 0x3f800000, 0x3f800000, 0x3f800000, /* def c3, 0.0, 1.0, 1.0, 1.0 */
843 0x05000051, 0xa00f0004, 0x00000000, 0x00000000, 0x3f800000, 0x3f800000, /* def c4, 0.0, 0.0, 1.0, 1.0 */
844 0x05000051, 0xa00f0005, 0x3f800000, 0x00000000, 0x3f800000, 0x3f800000, /* def c5, 1.0, 0.0, 1.0, 1.0 */
845 0x05000051, 0xa00f0006, 0x3f800000, 0x3f800000, 0x3f800000, 0x3f800000, /* def c6, 1.0, 1.0, 1.0, 1.0 */
846 0x0200002e, 0xb0010000, 0xa0000007, /* mova a0.x, c7.x */
847 0x03000001, 0xd00f0000, 0xa0e42003, 0xb0000000, /* mov oD0, c[a0.x + 3] */
848 0x02000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
849 0x0000ffff /* END */
851 static const DWORD mov_test[] =
853 0xfffe0101, /* vs_1_1 */
854 0x0000001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
855 0x00000051, 0xa00f0000, 0x3f800000, 0x00000000, 0x00000000, 0x3f800000, /* def c0, 1.0, 0.0, 0.0, 1.0 */
856 0x00000051, 0xa00f0001, 0x3f800000, 0x3f800000, 0x00000000, 0x3f800000, /* def c1, 1.0, 1.0, 0.0, 1.0 */
857 0x00000051, 0xa00f0002, 0x00000000, 0x3f800000, 0x00000000, 0x3f800000, /* def c2, 0.0, 1.0, 0.0, 1.0 */
858 0x00000051, 0xa00f0003, 0x00000000, 0x3f800000, 0x3f800000, 0x3f800000, /* def c3, 0.0, 1.0, 1.0, 1.0 */
859 0x00000051, 0xa00f0004, 0x00000000, 0x00000000, 0x3f800000, 0x3f800000, /* def c4, 0.0, 0.0, 1.0, 1.0 */
860 0x00000051, 0xa00f0005, 0x3f800000, 0x00000000, 0x3f800000, 0x3f800000, /* def c5, 1.0, 0.0, 1.0, 1.0 */
861 0x00000051, 0xa00f0006, 0x3f800000, 0x3f800000, 0x3f800000, 0x3f800000, /* def c6, 1.0, 1.0, 1.0, 1.0 */
862 0x00000001, 0xb0010000, 0xa0000007, /* mov a0.x, c7.x */
863 0x00000001, 0xd00f0000, 0xa0e42003, /* mov oD0, c[a0.x + 3] */
864 0x00000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
865 0x0000ffff /* END */
867 static const struct
869 float in[4];
870 DWORD out;
872 test_data[2][6] =
875 {{-2.4f, 0.0f, 0.0f, 0.0f}, 0x00ff0000},
876 {{-1.6f, 0.0f, 0.0f, 0.0f}, 0x00ffff00},
877 {{-0.4f, 0.0f, 0.0f, 0.0f}, 0x0000ff00},
878 {{ 0.4f, 0.0f, 0.0f, 0.0f}, 0x0000ffff},
879 {{ 1.6f, 0.0f, 0.0f, 0.0f}, 0x000000ff},
880 {{ 2.4f, 0.0f, 0.0f, 0.0f}, 0x00ff00ff}
883 {{-2.4f, 0.0f, 0.0f, 0.0f}, 0x00ffff00},
884 {{-1.6f, 0.0f, 0.0f, 0.0f}, 0x00ffff00},
885 {{-0.4f, 0.0f, 0.0f, 0.0f}, 0x0000ffff},
886 {{ 0.4f, 0.0f, 0.0f, 0.0f}, 0x0000ffff},
887 {{ 1.6f, 0.0f, 0.0f, 0.0f}, 0x00ff00ff},
888 {{ 2.4f, 0.0f, 0.0f, 0.0f}, 0x00ff00ff}
891 static const struct vec3 quad[] =
893 {-1.0f, -1.0f, 0.0f},
894 {-1.0f, 1.0f, 0.0f},
895 { 1.0f, -1.0f, 0.0f},
896 { 1.0f, 1.0f, 0.0f},
898 static const D3DVERTEXELEMENT9 decl_elements[] =
900 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
901 D3DDECL_END()
904 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
905 0, 0, 640, 480, NULL, NULL, NULL, NULL);
906 d3d = Direct3DCreate9(D3D_SDK_VERSION);
907 ok(!!d3d, "Failed to create a D3D object.\n");
908 if (!(device = create_device(d3d, window, window, TRUE)))
910 skip("Failed to create a D3D device, skipping tests.\n");
911 goto done;
914 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
915 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
916 if (caps.VertexShaderVersion < D3DVS_VERSION(2, 0))
918 skip("No vs_2_0 support, skipping tests.\n");
919 IDirect3DDevice9_Release(device);
920 goto done;
923 hr = IDirect3DDevice9_CreateVertexShader(device, mova_test, &mova_shader);
924 ok(SUCCEEDED(hr), "CreateVertexShader failed (%08x)\n", hr);
925 hr = IDirect3DDevice9_CreateVertexShader(device, mov_test, &mov_shader);
926 ok(SUCCEEDED(hr), "CreateVertexShader failed (%08x)\n", hr);
927 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements, &vertex_declaration);
928 ok(SUCCEEDED(hr), "CreateVertexDeclaration failed (%08x)\n", hr);
929 hr = IDirect3DDevice9_SetVertexDeclaration(device, vertex_declaration);
930 ok(SUCCEEDED(hr), "SetVertexDeclaration failed (%08x)\n", hr);
932 hr = IDirect3DDevice9_SetVertexShader(device, mov_shader);
933 ok(SUCCEEDED(hr), "SetVertexShader failed (%08x)\n", hr);
934 for (j = 0; j < sizeof(test_data) / sizeof(*test_data); ++j)
936 for (i = 0; i < sizeof(*test_data) / sizeof(**test_data); ++i)
938 DWORD color;
940 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 7, test_data[j][i].in, 1);
941 ok(SUCCEEDED(hr), "SetVertexShaderConstantF failed (%08x)\n", hr);
943 hr = IDirect3DDevice9_BeginScene(device);
944 ok(SUCCEEDED(hr), "BeginScene failed (%08x)\n", hr);
946 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
947 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed (%08x)\n", hr);
949 hr = IDirect3DDevice9_EndScene(device);
950 ok(SUCCEEDED(hr), "EndScene failed (%08x)\n", hr);
952 color = getPixelColor(device, 320, 240);
953 ok(color == test_data[j][i].out, "Expected color %08x, got %08x (for input %f, instruction %s)\n",
954 test_data[j][i].out, color, test_data[j][i].in[0], j == 0 ? "mov" : "mova");
956 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
957 ok(SUCCEEDED(hr), "Present failed (%08x)\n", hr);
959 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0, 0.0f, 0);
960 ok(SUCCEEDED(hr), "Clear failed (%08x)\n", hr);
962 hr = IDirect3DDevice9_SetVertexShader(device, mova_shader);
963 ok(SUCCEEDED(hr), "SetVertexShader failed (%08x)\n", hr);
966 IDirect3DVertexDeclaration9_Release(vertex_declaration);
967 IDirect3DVertexShader9_Release(mova_shader);
968 IDirect3DVertexShader9_Release(mov_shader);
969 refcount = IDirect3DDevice9_Release(device);
970 ok(!refcount, "Device has %u references left.\n", refcount);
971 done:
972 IDirect3D9_Release(d3d);
973 DestroyWindow(window);
976 static void fog_test(void)
978 float start = 0.0f, end = 1.0f;
979 IDirect3DDevice9 *device;
980 IDirect3D9 *d3d;
981 D3DCOLOR color;
982 ULONG refcount;
983 D3DCAPS9 caps;
984 HWND window;
985 HRESULT hr;
986 int i;
988 /* Gets full z based fog with linear fog, no fog with specular color. */
989 static const struct
991 float x, y, z;
992 D3DCOLOR diffuse;
993 D3DCOLOR specular;
995 untransformed_1[] =
997 {-1.0f, -1.0f, 0.1f, 0xffff0000, 0xff000000},
998 {-1.0f, 0.0f, 0.1f, 0xffff0000, 0xff000000},
999 { 0.0f, 0.0f, 0.1f, 0xffff0000, 0xff000000},
1000 { 0.0f, -1.0f, 0.1f, 0xffff0000, 0xff000000},
1002 /* Ok, I am too lazy to deal with transform matrices. */
1003 untransformed_2[] =
1005 {-1.0f, 0.0f, 1.0f, 0xffff0000, 0xff000000},
1006 {-1.0f, 1.0f, 1.0f, 0xffff0000, 0xff000000},
1007 { 0.0f, 1.0f, 1.0f, 0xffff0000, 0xff000000},
1008 { 0.0f, 0.0f, 1.0f, 0xffff0000, 0xff000000},
1010 untransformed_3[] =
1012 {-1.0f, -1.0f, 0.4999f, 0xffff0000, 0xff000000},
1013 {-1.0f, 1.0f, 0.4999f, 0xffff0000, 0xff000000},
1014 { 1.0f, -1.0f, 0.4999f, 0xffff0000, 0xff000000},
1015 { 1.0f, 1.0f, 0.4999f, 0xffff0000, 0xff000000},
1017 far_quad1[] =
1019 {-1.0f, -1.0f, 0.5f, 0xffff0000, 0xff000000},
1020 {-1.0f, 0.0f, 0.5f, 0xffff0000, 0xff000000},
1021 { 0.0f, 0.0f, 0.5f, 0xffff0000, 0xff000000},
1022 { 0.0f, -1.0f, 0.5f, 0xffff0000, 0xff000000},
1024 far_quad2[] =
1026 {-1.0f, 0.0f, 1.5f, 0xffff0000, 0xff000000},
1027 {-1.0f, 1.0f, 1.5f, 0xffff0000, 0xff000000},
1028 { 0.0f, 1.0f, 1.5f, 0xffff0000, 0xff000000},
1029 { 0.0f, 0.0f, 1.5f, 0xffff0000, 0xff000000},
1031 /* Untransformed ones. Give them a different diffuse color to make the
1032 * test look nicer. It also makes making sure that they are drawn
1033 * correctly easier. */
1034 static const struct
1036 float x, y, z, rhw;
1037 D3DCOLOR diffuse;
1038 D3DCOLOR specular;
1040 transformed_1[] =
1042 {320.0f, 0.0f, 1.0f, 1.0f, 0xffffff00, 0xff000000},
1043 {640.0f, 0.0f, 1.0f, 1.0f, 0xffffff00, 0xff000000},
1044 {640.0f, 240.0f, 1.0f, 1.0f, 0xffffff00, 0xff000000},
1045 {320.0f, 240.0f, 1.0f, 1.0f, 0xffffff00, 0xff000000},
1047 transformed_2[] =
1049 {320.0f, 240.0f, 1.0f, 1.0f, 0xffffff00, 0xff000000},
1050 {640.0f, 240.0f, 1.0f, 1.0f, 0xffffff00, 0xff000000},
1051 {640.0f, 480.0f, 1.0f, 1.0f, 0xffffff00, 0xff000000},
1052 {320.0f, 480.0f, 1.0f, 1.0f, 0xffffff00, 0xff000000},
1054 static const struct
1056 struct vec3 position;
1057 DWORD diffuse;
1059 rev_fog_quads[] =
1061 {{-1.0f, -1.0f, 0.1f}, 0x000000ff},
1062 {{-1.0f, 0.0f, 0.1f}, 0x000000ff},
1063 {{ 0.0f, 0.0f, 0.1f}, 0x000000ff},
1064 {{ 0.0f, -1.0f, 0.1f}, 0x000000ff},
1066 {{ 0.0f, -1.0f, 0.9f}, 0x000000ff},
1067 {{ 0.0f, 0.0f, 0.9f}, 0x000000ff},
1068 {{ 1.0f, 0.0f, 0.9f}, 0x000000ff},
1069 {{ 1.0f, -1.0f, 0.9f}, 0x000000ff},
1071 {{ 0.0f, 0.0f, 0.4f}, 0x000000ff},
1072 {{ 0.0f, 1.0f, 0.4f}, 0x000000ff},
1073 {{ 1.0f, 1.0f, 0.4f}, 0x000000ff},
1074 {{ 1.0f, 0.0f, 0.4f}, 0x000000ff},
1076 {{-1.0f, 0.0f, 0.7f}, 0x000000ff},
1077 {{-1.0f, 1.0f, 0.7f}, 0x000000ff},
1078 {{ 0.0f, 1.0f, 0.7f}, 0x000000ff},
1079 {{ 0.0f, 0.0f, 0.7f}, 0x000000ff},
1081 static const D3DMATRIX ident_mat =
1083 1.0f, 0.0f, 0.0f, 0.0f,
1084 0.0f, 1.0f, 0.0f, 0.0f,
1085 0.0f, 0.0f, 1.0f, 0.0f,
1086 0.0f, 0.0f, 0.0f, 1.0f
1087 }}};
1088 static const D3DMATRIX world_mat1 =
1090 1.0f, 0.0f, 0.0f, 0.0f,
1091 0.0f, 1.0f, 0.0f, 0.0f,
1092 0.0f, 0.0f, 1.0f, 0.0f,
1093 0.0f, 0.0f, -0.5f, 1.0f
1094 }}};
1095 static const D3DMATRIX world_mat2 =
1097 1.0f, 0.0f, 0.0f, 0.0f,
1098 0.0f, 1.0f, 0.0f, 0.0f,
1099 0.0f, 0.0f, 1.0f, 0.0f,
1100 0.0f, 0.0f, 1.0f, 1.0f
1101 }}};
1102 static const D3DMATRIX proj_mat =
1104 1.0f, 0.0f, 0.0f, 0.0f,
1105 0.0f, 1.0f, 0.0f, 0.0f,
1106 0.0f, 0.0f, 1.0f, 0.0f,
1107 0.0f, 0.0f, -1.0f, 1.0f
1108 }}};
1109 static const WORD Indices[] = {0, 1, 2, 2, 3, 0};
1110 static const WORD Indices2[] =
1112 0, 1, 2, 2, 3, 0,
1113 4, 5, 6, 6, 7, 4,
1114 8, 9, 10, 10, 11, 8,
1115 12, 13, 14, 14, 15, 12,
1118 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
1119 0, 0, 640, 480, NULL, NULL, NULL, NULL);
1120 d3d = Direct3DCreate9(D3D_SDK_VERSION);
1121 ok(!!d3d, "Failed to create a D3D object.\n");
1122 if (!(device = create_device(d3d, window, window, TRUE)))
1124 skip("Failed to create a D3D device, skipping tests.\n");
1125 goto done;
1128 memset(&caps, 0, sizeof(caps));
1129 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
1130 ok(hr == D3D_OK, "IDirect3DDevice9_GetDeviceCaps returned %08x\n", hr);
1131 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffff00ff, 0.0, 0);
1132 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
1134 /* Setup initial states: No lighting, fog on, fog color */
1135 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, FALSE);
1136 ok(SUCCEEDED(hr), "Failed to disable D3DRS_ZENABLE, hr %#x.\n", hr);
1137 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
1138 ok(hr == D3D_OK, "Turning off lighting returned %08x\n", hr);
1139 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGENABLE, TRUE);
1140 ok(hr == D3D_OK, "Turning on fog calculations returned %08x\n", hr);
1141 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGCOLOR, 0xff00ff00 /* A nice green */);
1142 ok(hr == D3D_OK, "Setting fog color returned %#08x\n", hr);
1143 /* Some of the tests seem to depend on the projection matrix explicitly
1144 * being set to an identity matrix, even though that's the default.
1145 * (AMD Radeon HD 6310, Windows 7) */
1146 hr = IDirect3DDevice9_SetTransform(device, D3DTS_PROJECTION, &ident_mat);
1147 ok(SUCCEEDED(hr), "Failed to set projection transform, hr %#x.\n", hr);
1149 /* First test: Both table fog and vertex fog off */
1150 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGTABLEMODE, D3DFOG_NONE);
1151 ok(hr == D3D_OK, "Turning off table fog returned %08x\n", hr);
1152 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGVERTEXMODE, D3DFOG_NONE);
1153 ok(hr == D3D_OK, "Turning off vertex fog returned %08x\n", hr);
1155 /* Start = 0, end = 1. Should be default, but set them */
1156 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGSTART, *((DWORD *) &start));
1157 ok(hr == D3D_OK, "Setting fog start returned %08x\n", hr);
1158 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGEND, *((DWORD *) &end));
1159 ok(hr == D3D_OK, "Setting fog end returned %08x\n", hr);
1161 hr = IDirect3DDevice9_BeginScene(device);
1162 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
1164 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE | D3DFVF_SPECULAR);
1165 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
1167 /* Untransformed, vertex fog = NONE, table fog = NONE:
1168 * Read the fog weighting from the specular color. */
1169 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 4 /* NumVerts */,
1170 2 /* PrimCount */, Indices, D3DFMT_INDEX16, untransformed_1, sizeof(untransformed_1[0]));
1171 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
1173 /* That makes it use the Z value */
1174 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGVERTEXMODE, D3DFOG_LINEAR);
1175 ok(SUCCEEDED(hr), "Failed to set D3DFOG_LINEAR fog vertex mode, hr %#x.\n", hr);
1176 /* Untransformed, vertex fog != none (or table fog != none):
1177 * Use the Z value as input into the equation. */
1178 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 4 /* NumVerts */,
1179 2 /* PrimCount */, Indices, D3DFMT_INDEX16, untransformed_2, sizeof(untransformed_2[0]));
1180 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
1182 /* transformed verts */
1183 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZRHW | D3DFVF_DIFFUSE | D3DFVF_SPECULAR);
1184 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
1185 /* Transformed, vertex fog != NONE, pixel fog == NONE:
1186 * Use specular color alpha component. */
1187 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 4 /* NumVerts */,
1188 2 /* PrimCount */, Indices, D3DFMT_INDEX16, transformed_1, sizeof(transformed_1[0]));
1189 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
1191 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGTABLEMODE, D3DFOG_LINEAR);
1192 ok(SUCCEEDED(hr), "Failed to set D3DFOG_LINEAR fog table mode, hr %#x.\n", hr);
1193 /* Transformed, table fog != none, vertex anything:
1194 * Use Z value as input to the fog equation. */
1195 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 4 /* NumVerts */,
1196 2 /* PrimCount */, Indices, D3DFMT_INDEX16, transformed_2, sizeof(transformed_2[0]));
1197 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
1199 hr = IDirect3DDevice9_EndScene(device);
1200 ok(hr == D3D_OK, "EndScene returned %08x\n", hr);
1202 color = getPixelColor(device, 160, 360);
1203 ok(color == 0x00ff0000, "Untransformed vertex with no table or vertex fog has color %08x\n", color);
1204 color = getPixelColor(device, 160, 120);
1205 ok(color_match(color, 0x0000ff00, 1), "Untransformed vertex with linear vertex fog has color %08x\n", color);
1206 color = getPixelColor(device, 480, 120);
1207 ok(color == 0x00ffff00, "Transformed vertex with linear vertex fog has color %08x\n", color);
1208 if(caps.RasterCaps & D3DPRASTERCAPS_FOGTABLE)
1210 color = getPixelColor(device, 480, 360);
1211 ok(color_match(color, 0x0000ff00, 1), "Transformed vertex with linear table fog has color %08x\n", color);
1213 else
1215 /* Without fog table support the vertex fog is still applied, even though table fog is turned on.
1216 * The settings above result in no fogging with vertex fog
1218 color = getPixelColor(device, 480, 120);
1219 ok(color == 0x00ffff00, "Transformed vertex with linear vertex fog has color %08x\n", color);
1220 trace("Info: Table fog not supported by this device\n");
1222 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
1224 /* Now test the special case fogstart == fogend */
1225 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff0000ff, 0.0, 0);
1226 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
1228 hr = IDirect3DDevice9_BeginScene(device);
1229 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
1231 start = 512;
1232 end = 512;
1233 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGSTART, *((DWORD *)&start));
1234 ok(SUCCEEDED(hr), "Failed to set fog start, hr %#x.\n", hr);
1235 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGEND, *((DWORD *)&end));
1236 ok(SUCCEEDED(hr), "Failed to set fog end, hr %#x.\n", hr);
1238 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE | D3DFVF_SPECULAR);
1239 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
1240 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGVERTEXMODE, D3DFOG_LINEAR);
1241 ok(SUCCEEDED(hr), "Failed to set D3DFOG_LINEAR fog vertex mode, hr %#x.\n", hr);
1242 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGTABLEMODE, D3DFOG_NONE);
1243 ok(SUCCEEDED(hr), "Failed to set D3DFOG_NONE fog table mode, hr %#x.\n", hr);
1245 /* Untransformed vertex, z coord = 0.1, fogstart = 512, fogend = 512.
1246 * Would result in a completely fog-free primitive because start > zcoord,
1247 * but because start == end, the primitive is fully covered by fog. The
1248 * same happens to the 2nd untransformed quad with z = 1.0. The third
1249 * transformed quad remains unfogged because the fogcoords are read from
1250 * the specular color and has fixed fogstart and fogend. */
1251 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 4 /* NumVerts */,
1252 2 /* PrimCount */, Indices, D3DFMT_INDEX16, untransformed_1, sizeof(untransformed_1[0]));
1253 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
1254 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 4 /* NumVerts */,
1255 2 /* PrimCount */, Indices, D3DFMT_INDEX16, untransformed_2, sizeof(untransformed_2[0]));
1256 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
1258 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZRHW | D3DFVF_DIFFUSE | D3DFVF_SPECULAR);
1259 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
1260 /* Transformed, vertex fog != NONE, pixel fog == NONE:
1261 * Use specular color alpha component. */
1262 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 4 /* NumVerts */,
1263 2 /* PrimCount */, Indices, D3DFMT_INDEX16, transformed_1, sizeof(transformed_1[0]));
1264 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
1266 hr = IDirect3DDevice9_EndScene(device);
1267 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
1269 color = getPixelColor(device, 160, 360);
1270 ok(color_match(color, 0x0000ff00, 1), "Untransformed vertex with vertex fog and z = 0.1 has color %08x\n", color);
1271 color = getPixelColor(device, 160, 120);
1272 ok(color_match(color, 0x0000ff00, 1), "Untransformed vertex with vertex fog and z = 1.0 has color %08x\n", color);
1273 color = getPixelColor(device, 480, 120);
1274 ok(color == 0x00ffff00, "Transformed vertex with linear vertex fog has color %08x\n", color);
1275 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
1277 /* Test "reversed" fog without shaders. With shaders this fails on a few Windows D3D implementations,
1278 * but without shaders it seems to work everywhere
1280 end = 0.2;
1281 start = 0.8;
1282 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGSTART, *((DWORD *) &start));
1283 ok(hr == D3D_OK, "Setting fog start returned %08x\n", hr);
1284 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGEND, *((DWORD *) &end));
1285 ok(hr == D3D_OK, "Setting fog end returned %08x\n", hr);
1286 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
1287 ok( hr == D3D_OK, "IDirect3DDevice9_SetFVF returned %08x\n", hr);
1289 /* Test reversed fog without shaders. ATI cards have problems with reversed fog and shaders, so
1290 * it doesn't seem very important for games. ATI cards also have problems with reversed table fog,
1291 * so skip this for now
1293 for(i = 0; i < 1 /*2 - Table fog test disabled, fails on ATI */; i++) {
1294 const char *mode = (i ? "table" : "vertex");
1295 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffff0000, 0.0, 0);
1296 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
1297 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGVERTEXMODE, i == 0 ? D3DFOG_LINEAR : D3DFOG_NONE);
1298 ok( hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
1299 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGTABLEMODE, i == 0 ? D3DFOG_NONE : D3DFOG_LINEAR);
1300 ok( hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
1301 hr = IDirect3DDevice9_BeginScene(device);
1302 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
1303 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 16 /* NumVerts */,
1304 8 /* PrimCount */, Indices2, D3DFMT_INDEX16, rev_fog_quads, sizeof(rev_fog_quads[0]));
1305 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
1306 hr = IDirect3DDevice9_EndScene(device);
1307 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
1309 color = getPixelColor(device, 160, 360);
1310 ok(color_match(color, 0x0000ff00, 1),
1311 "Reversed %s fog: z=0.1 has color 0x%08x, expected 0x0000ff00 or 0x0000fe00\n", mode, color);
1313 color = getPixelColor(device, 160, 120);
1314 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x00, 0x2b, 0xd4), 2),
1315 "Reversed %s fog: z=0.7 has color 0x%08x\n", mode, color);
1317 color = getPixelColor(device, 480, 120);
1318 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x00, 0xaa, 0x55), 2),
1319 "Reversed %s fog: z=0.4 has color 0x%08x\n", mode, color);
1321 color = getPixelColor(device, 480, 360);
1322 ok(color == 0x000000ff, "Reversed %s fog: z=0.9 has color 0x%08x, expected 0x000000ff\n", mode, color);
1324 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
1326 if(!(caps.RasterCaps & D3DPRASTERCAPS_FOGTABLE)) {
1327 skip("D3DPRASTERCAPS_FOGTABLE not supported, skipping reversed table fog test\n");
1328 break;
1332 if (caps.RasterCaps & D3DPRASTERCAPS_FOGTABLE)
1334 /* A simple fog + non-identity world matrix test */
1335 hr = IDirect3DDevice9_SetTransform(device, D3DTS_WORLDMATRIX(0), &world_mat1);
1336 ok(hr == D3D_OK, "IDirect3DDevice9_SetTransform returned %#08x\n", hr);
1338 start = 0.0;
1339 end = 1.0;
1340 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGSTART, *((DWORD *)&start));
1341 ok(hr == D3D_OK, "Setting fog start returned %08x\n", hr);
1342 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGEND, *((DWORD *)&end));
1343 ok(hr == D3D_OK, "Setting fog end returned %08x\n", hr);
1344 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGTABLEMODE, D3DFOG_LINEAR);
1345 ok(hr == D3D_OK, "Setting fog table mode to D3DFOG_LINEAR returned %#08x\n", hr);
1346 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGVERTEXMODE, D3DFOG_NONE);
1347 ok(hr == D3D_OK, "Turning off vertex fog returned %#08x\n", hr);
1349 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffff00ff, 0.0, 0);
1350 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %#08x\n", hr);
1352 hr = IDirect3DDevice9_BeginScene(device);
1353 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
1355 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE | D3DFVF_SPECULAR);
1356 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
1358 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0, 4,
1359 2, Indices, D3DFMT_INDEX16, far_quad1, sizeof(far_quad1[0]));
1360 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
1361 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0, 4,
1362 2, Indices, D3DFMT_INDEX16, far_quad2, sizeof(far_quad2[0]));
1363 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
1365 hr = IDirect3DDevice9_EndScene(device);
1366 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
1368 color = getPixelColor(device, 160, 360);
1369 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0xff, 0x00, 0x00), 4),
1370 "Unfogged quad has color %08x\n", color);
1371 color = getPixelColor(device, 160, 120);
1372 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x00, 0xff, 0x00), 1),
1373 "Fogged out quad has color %08x\n", color);
1375 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
1377 /* Test fog behavior with an orthogonal (but non-identity) projection matrix */
1378 hr = IDirect3DDevice9_SetTransform(device, D3DTS_WORLDMATRIX(0), &world_mat2);
1379 ok(hr == D3D_OK, "SetTransform returned %#08x\n", hr);
1380 hr = IDirect3DDevice9_SetTransform(device, D3DTS_PROJECTION, &proj_mat);
1381 ok(hr == D3D_OK, "SetTransform returned %#08x\n", hr);
1383 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffff00ff, 0.0, 0);
1384 ok(hr == D3D_OK, "Clear returned %#08x\n", hr);
1386 hr = IDirect3DDevice9_BeginScene(device);
1387 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
1389 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE | D3DFVF_SPECULAR);
1390 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
1392 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0, 4,
1393 2, Indices, D3DFMT_INDEX16, untransformed_1, sizeof(untransformed_1[0]));
1394 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
1395 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0, 4,
1396 2, Indices, D3DFMT_INDEX16, untransformed_2, sizeof(untransformed_2[0]));
1397 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
1399 hr = IDirect3DDevice9_EndScene(device);
1400 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
1402 color = getPixelColor(device, 160, 360);
1403 ok(color_match(color, 0x00e51900, 4), "Partially fogged quad has color %08x\n", color);
1404 color = getPixelColor(device, 160, 120);
1405 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x00, 0xff, 0x00), 1),
1406 "Fogged out quad has color %08x\n", color);
1408 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
1410 hr = IDirect3DDevice9_SetTransform(device, D3DTS_WORLDMATRIX(0), &ident_mat);
1411 ok(hr == D3D_OK, "SetTransform returned %#08x\n", hr);
1412 hr = IDirect3DDevice9_SetTransform(device, D3DTS_PROJECTION, &ident_mat);
1413 ok(hr == D3D_OK, "SetTransform returned %#08x\n", hr);
1415 else
1417 skip("D3DPRASTERCAPS_FOGTABLE not supported, skipping some fog tests\n");
1420 /* Test RANGEFOG vs FOGTABLEMODE */
1421 if ((caps.RasterCaps & (D3DPRASTERCAPS_FOGTABLE | D3DPRASTERCAPS_FOGRANGE)) ==
1422 (D3DPRASTERCAPS_FOGTABLE | D3DPRASTERCAPS_FOGRANGE))
1424 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffff00ff, 0.0, 0);
1425 ok(SUCCEEDED(hr), "IDirect3DDevice9_Clear failed, hr %#x.\n", hr);
1426 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE | D3DFVF_SPECULAR);
1427 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetFVF failed, hr %#x.\n", hr);
1429 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_RANGEFOGENABLE, TRUE);
1430 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetRenderState failed, hr %#x.\n", hr);
1432 /* z=0.4999, set the fogstart to 0.5 and fogend slightly higher. If range fog
1433 * is not used, the fog coordinate will be equal to fogstart and the quad not
1434 * fogged. If range fog is used the fog coordinate will be slightly higher and
1435 * the fog coordinate will be > fogend, so we get a fully fogged quad. The fog
1436 * is calculated per vertex and interpolated, so even the center of the screen
1437 * where the difference doesn't matter will be fogged, but check the corners in
1438 * case a d3d/gl implementation decides to calculate the fog factor per fragment */
1439 start = 0.5f;
1440 end = 0.50001f;
1441 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGSTART, *((DWORD *) &start));
1442 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetRenderState failed, hr %#x.\n", hr);
1443 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGEND, *((DWORD *) &end));
1444 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetRenderState failed, hr %#x.\n", hr);
1446 /* Table fog: Range fog is not used */
1447 hr = IDirect3DDevice9_BeginScene(device);
1448 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
1450 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGTABLEMODE, D3DFOG_LINEAR);
1451 ok(SUCCEEDED(hr), "Failed to set D3DFOG_LINEAR fog table mode, hr %#x.\n", hr);
1452 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2,
1453 untransformed_3, sizeof(*untransformed_3));
1454 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
1456 hr = IDirect3DDevice9_EndScene(device);
1457 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
1459 color = getPixelColor(device, 10, 10);
1460 ok(color == 0x00ff0000, "Rangefog with table fog returned color 0x%08x\n", color);
1461 color = getPixelColor(device, 630, 10);
1462 ok(color == 0x00ff0000, "Rangefog with table fog returned color 0x%08x\n", color);
1463 color = getPixelColor(device, 10, 470);
1464 ok(color == 0x00ff0000, "Rangefog with table fog returned color 0x%08x\n", color);
1465 color = getPixelColor(device, 630, 470);
1466 ok(color == 0x00ff0000, "Rangefog with table fog returned color 0x%08x\n", color);
1468 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
1469 ok(SUCCEEDED(hr), "IDirect3DDevice9_Present failed, hr %#x.\n", hr);
1471 /* Vertex fog: Rangefog is used */
1472 hr = IDirect3DDevice9_BeginScene(device);
1473 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
1475 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGTABLEMODE, D3DFOG_NONE);
1476 ok(SUCCEEDED(hr), "Failed to set D3DFOG_NONE fog table mode, hr %#x.\n", hr);
1477 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGVERTEXMODE, D3DFOG_LINEAR);
1478 ok(SUCCEEDED(hr), "Failed to set D3DFOG_LINEAR fog vertex mode, hr %#x.\n", hr);
1479 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2,
1480 untransformed_3, sizeof(*untransformed_3));
1481 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
1483 hr = IDirect3DDevice9_EndScene(device);
1484 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
1486 color = getPixelColor(device, 10, 10);
1487 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x00, 0xff, 0x00), 1),
1488 "Rangefog with vertex fog returned color 0x%08x\n", color);
1489 color = getPixelColor(device, 630, 10);
1490 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x00, 0xff, 0x00), 1),
1491 "Rangefog with vertex fog returned color 0x%08x\n", color);
1492 color = getPixelColor(device, 10, 470);
1493 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x00, 0xff, 0x00), 1),
1494 "Rangefog with vertex fog returned color 0x%08x\n", color);
1495 color = getPixelColor(device, 630, 470);
1496 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x00, 0xff, 0x00), 1),
1497 "Rangefog with vertex fog returned color 0x%08x\n", color);
1499 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
1500 ok(SUCCEEDED(hr), "IDirect3DDevice9_Present failed, hr %#x.\n", hr);
1502 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_RANGEFOGENABLE, FALSE);
1503 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetRenderState failed, hr %#x.\n", hr);
1505 else
1507 skip("Range fog or table fog not supported, skipping range fog tests\n");
1510 refcount = IDirect3DDevice9_Release(device);
1511 ok(!refcount, "Device has %u references left.\n", refcount);
1512 done:
1513 IDirect3D9_Release(d3d);
1514 DestroyWindow(window);
1517 /* This test verifies the behaviour of cube maps wrt. texture wrapping.
1518 * D3D cube map wrapping always behaves like GL_CLAMP_TO_EDGE,
1519 * regardless of the actual addressing mode set. The way this test works is
1520 * that we sample in one of the corners of the cubemap with filtering enabled,
1521 * and check the interpolated color. There are essentially two reasonable
1522 * things an implementation can do: Either pick one of the faces and
1523 * interpolate the edge texel with itself (i.e., clamp within the face), or
1524 * interpolate between the edge texels of the three involved faces. It should
1525 * never involve the border color or the other side (texcoord wrapping) of a
1526 * face in the interpolation. */
1527 static void test_cube_wrap(void)
1529 IDirect3DVertexDeclaration9 *vertex_declaration;
1530 IDirect3DSurface9 *face_surface, *surface;
1531 IDirect3DCubeTexture9 *texture;
1532 D3DLOCKED_RECT locked_rect;
1533 IDirect3DDevice9 *device;
1534 unsigned int x, y, face;
1535 IDirect3D9 *d3d;
1536 ULONG refcount;
1537 D3DCAPS9 caps;
1538 HWND window;
1539 HRESULT hr;
1541 static const float quad[][6] =
1543 {-1.0f, -1.0f, 0.0f, 1.0f, 1.0f, 1.0f},
1544 {-1.0f, 1.0f, 0.0f, 1.0f, 1.0f, 1.0f},
1545 { 1.0f, -1.0f, 0.0f, 1.0f, 1.0f, 1.0f},
1546 { 1.0f, 1.0f, 0.0f, 1.0f, 1.0f, 1.0f},
1548 static const D3DVERTEXELEMENT9 decl_elements[] =
1550 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
1551 {0, 12, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
1552 D3DDECL_END()
1554 static const struct
1556 D3DTEXTUREADDRESS mode;
1557 const char *name;
1559 address_modes[] =
1561 {D3DTADDRESS_WRAP, "D3DTADDRESS_WRAP"},
1562 {D3DTADDRESS_MIRROR, "D3DTADDRESS_MIRROR"},
1563 {D3DTADDRESS_CLAMP, "D3DTADDRESS_CLAMP"},
1564 {D3DTADDRESS_BORDER, "D3DTADDRESS_BORDER"},
1565 {D3DTADDRESS_MIRRORONCE, "D3DTADDRESS_MIRRORONCE"},
1568 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
1569 0, 0, 640, 480, NULL, NULL, NULL, NULL);
1570 d3d = Direct3DCreate9(D3D_SDK_VERSION);
1571 ok(!!d3d, "Failed to create a D3D object.\n");
1572 if (!(device = create_device(d3d, window, window, TRUE)))
1574 skip("Failed to create a D3D device, skipping tests.\n");
1575 goto done;
1578 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
1579 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
1580 if (!(caps.TextureCaps & D3DPTEXTURECAPS_CUBEMAP))
1582 skip("No cube texture support, skipping tests.\n");
1583 IDirect3DDevice9_Release(device);
1584 goto done;
1587 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements, &vertex_declaration);
1588 ok(SUCCEEDED(hr), "CreateVertexDeclaration failed (0x%08x)\n", hr);
1589 hr = IDirect3DDevice9_SetVertexDeclaration(device, vertex_declaration);
1590 ok(SUCCEEDED(hr), "SetVertexDeclaration failed (0x%08x)\n", hr);
1592 hr = IDirect3DDevice9_CreateOffscreenPlainSurface(device, 128, 128,
1593 D3DFMT_A8R8G8B8, D3DPOOL_SYSTEMMEM, &surface, NULL);
1594 ok(SUCCEEDED(hr), "CreateOffscreenPlainSurface failed (0x%08x)\n", hr);
1596 hr = IDirect3DDevice9_CreateCubeTexture(device, 128, 1, 0, D3DFMT_A8R8G8B8,
1597 D3DPOOL_DEFAULT, &texture, NULL);
1598 ok(SUCCEEDED(hr), "CreateCubeTexture failed (0x%08x)\n", hr);
1600 hr = IDirect3DSurface9_LockRect(surface, &locked_rect, NULL, 0);
1601 ok(SUCCEEDED(hr), "LockRect failed (0x%08x)\n", hr);
1603 for (y = 0; y < 128; ++y)
1605 DWORD *ptr = (DWORD *)(((BYTE *)locked_rect.pBits) + (y * locked_rect.Pitch));
1606 for (x = 0; x < 64; ++x)
1608 *ptr++ = 0xff0000ff;
1610 for (x = 64; x < 128; ++x)
1612 *ptr++ = 0xffff0000;
1616 hr = IDirect3DSurface9_UnlockRect(surface);
1617 ok(SUCCEEDED(hr), "UnlockRect failed (0x%08x)\n", hr);
1619 hr= IDirect3DCubeTexture9_GetCubeMapSurface(texture, 0, 0, &face_surface);
1620 ok(SUCCEEDED(hr), "GetCubeMapSurface failed (0x%08x)\n", hr);
1622 hr = IDirect3DDevice9_UpdateSurface(device, surface, NULL, face_surface, NULL);
1623 ok(SUCCEEDED(hr), "UpdateSurface failed (0x%08x)\n", hr);
1625 IDirect3DSurface9_Release(face_surface);
1627 hr = IDirect3DSurface9_LockRect(surface, &locked_rect, NULL, 0);
1628 ok(SUCCEEDED(hr), "LockRect failed (0x%08x)\n", hr);
1630 for (y = 0; y < 128; ++y)
1632 DWORD *ptr = (DWORD *)(((BYTE *)locked_rect.pBits) + (y * locked_rect.Pitch));
1633 for (x = 0; x < 64; ++x)
1635 *ptr++ = 0xffff0000;
1637 for (x = 64; x < 128; ++x)
1639 *ptr++ = 0xff0000ff;
1643 hr = IDirect3DSurface9_UnlockRect(surface);
1644 ok(SUCCEEDED(hr), "UnlockRect failed (0x%08x)\n", hr);
1646 /* Create cube faces */
1647 for (face = 1; face < 6; ++face)
1649 hr= IDirect3DCubeTexture9_GetCubeMapSurface(texture, face, 0, &face_surface);
1650 ok(SUCCEEDED(hr), "GetCubeMapSurface failed (0x%08x)\n", hr);
1652 hr = IDirect3DDevice9_UpdateSurface(device, surface, NULL, face_surface, NULL);
1653 ok(SUCCEEDED(hr), "UpdateSurface failed (0x%08x)\n", hr);
1655 IDirect3DSurface9_Release(face_surface);
1658 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)texture);
1659 ok(SUCCEEDED(hr), "SetTexture failed (0x%08x)\n", hr);
1661 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MINFILTER, D3DTEXF_LINEAR);
1662 ok(SUCCEEDED(hr), "SetSamplerState D3DSAMP_MINFILTER failed (0x%08x)\n", hr);
1663 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAGFILTER, D3DTEXF_LINEAR);
1664 ok(SUCCEEDED(hr), "SetSamplerState D3DSAMP_MAGFILTER failed (0x%08x)\n", hr);
1665 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_BORDERCOLOR, 0xff00ff00);
1666 ok(SUCCEEDED(hr), "SetSamplerState D3DSAMP_BORDERCOLOR failed (0x%08x)\n", hr);
1668 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
1669 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
1671 for (x = 0; x < (sizeof(address_modes) / sizeof(*address_modes)); ++x)
1673 DWORD color;
1675 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_ADDRESSU, address_modes[x].mode);
1676 ok(SUCCEEDED(hr), "SetSamplerState D3DSAMP_ADDRESSU (%s) failed (0x%08x)\n", address_modes[x].name, hr);
1677 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_ADDRESSV, address_modes[x].mode);
1678 ok(SUCCEEDED(hr), "SetSamplerState D3DSAMP_ADDRESSV (%s) failed (0x%08x)\n", address_modes[x].name, hr);
1680 hr = IDirect3DDevice9_BeginScene(device);
1681 ok(SUCCEEDED(hr), "BeginScene failed (0x%08x)\n", hr);
1683 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quad[0], sizeof(quad[0]));
1684 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed (0x%08x)\n", hr);
1686 hr = IDirect3DDevice9_EndScene(device);
1687 ok(SUCCEEDED(hr), "EndScene failed (0x%08x)\n", hr);
1689 color = getPixelColor(device, 320, 240);
1690 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x00, 0x00, 0xff), 1),
1691 "Got color 0x%08x for addressing mode %s, expected 0x000000ff.\n",
1692 color, address_modes[x].name);
1694 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
1695 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
1697 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0, 0.0f, 0);
1698 ok(SUCCEEDED(hr), "Clear failed (0x%08x)\n", hr);
1701 IDirect3DVertexDeclaration9_Release(vertex_declaration);
1702 IDirect3DCubeTexture9_Release(texture);
1703 IDirect3DSurface9_Release(surface);
1704 refcount = IDirect3DDevice9_Release(device);
1705 ok(!refcount, "Device has %u references left.\n", refcount);
1706 done:
1707 IDirect3D9_Release(d3d);
1708 DestroyWindow(window);
1711 static void offscreen_test(void)
1713 IDirect3DSurface9 *backbuffer, *offscreen;
1714 IDirect3DTexture9 *offscreenTexture;
1715 IDirect3DDevice9 *device;
1716 IDirect3D9 *d3d;
1717 D3DCOLOR color;
1718 ULONG refcount;
1719 HWND window;
1720 HRESULT hr;
1722 static const float quad[][5] =
1724 {-0.5f, -0.5f, 0.1f, 0.0f, 0.0f},
1725 {-0.5f, 0.5f, 0.1f, 0.0f, 1.0f},
1726 { 0.5f, -0.5f, 0.1f, 1.0f, 0.0f},
1727 { 0.5f, 0.5f, 0.1f, 1.0f, 1.0f},
1730 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
1731 0, 0, 640, 480, NULL, NULL, NULL, NULL);
1732 d3d = Direct3DCreate9(D3D_SDK_VERSION);
1733 ok(!!d3d, "Failed to create a D3D object.\n");
1734 if (!(device = create_device(d3d, window, window, TRUE)))
1736 skip("Failed to create a D3D device, skipping tests.\n");
1737 goto done;
1740 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffff0000, 1.0f, 0);
1741 ok(hr == D3D_OK, "Clear failed, hr = %08x\n", hr);
1743 hr = IDirect3DDevice9_CreateTexture(device, 128, 128, 1, D3DUSAGE_RENDERTARGET,
1744 D3DFMT_X8R8G8B8, D3DPOOL_DEFAULT, &offscreenTexture, NULL);
1745 ok(hr == D3D_OK || hr == D3DERR_INVALIDCALL, "Creating the offscreen render target failed, hr = %08x\n", hr);
1746 if (!offscreenTexture)
1748 trace("Failed to create an X8R8G8B8 offscreen texture, trying R5G6B5.\n");
1749 hr = IDirect3DDevice9_CreateTexture(device, 128, 128, 1, D3DUSAGE_RENDERTARGET,
1750 D3DFMT_R5G6B5, D3DPOOL_DEFAULT, &offscreenTexture, NULL);
1751 ok(hr == D3D_OK || hr == D3DERR_INVALIDCALL, "Creating the offscreen render target failed, hr = %08x\n", hr);
1752 if (!offscreenTexture)
1754 skip("Cannot create an offscreen render target.\n");
1755 IDirect3DDevice9_Release(device);
1756 goto done;
1760 hr = IDirect3DDevice9_GetBackBuffer(device, 0, 0, D3DBACKBUFFER_TYPE_MONO, &backbuffer);
1761 ok(hr == D3D_OK, "Can't get back buffer, hr = %08x\n", hr);
1763 hr = IDirect3DTexture9_GetSurfaceLevel(offscreenTexture, 0, &offscreen);
1764 ok(hr == D3D_OK, "Can't get offscreen surface, hr = %08x\n", hr);
1766 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1);
1767 ok(hr == D3D_OK, "SetFVF failed, hr = %08x\n", hr);
1769 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
1770 ok(hr == D3D_OK, "SetTextureStageState failed, hr = %08x\n", hr);
1771 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
1772 ok(hr == D3D_OK, "SetTextureStageState failed, hr = %08x\n", hr);
1773 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MINFILTER, D3DTEXF_POINT);
1774 ok(SUCCEEDED(hr), "SetSamplerState D3DSAMP_MINFILTER failed (0x%08x)\n", hr);
1775 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAGFILTER, D3DTEXF_POINT);
1776 ok(SUCCEEDED(hr), "SetSamplerState D3DSAMP_MAGFILTER failed (0x%08x)\n", hr);
1777 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
1778 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
1780 hr = IDirect3DDevice9_BeginScene(device);
1781 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
1783 hr = IDirect3DDevice9_SetRenderTarget(device, 0, offscreen);
1784 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
1785 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffff00ff, 1.0f, 0);
1786 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
1788 /* Draw without textures - Should result in a white quad. */
1789 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(quad[0]));
1790 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
1792 hr = IDirect3DDevice9_SetRenderTarget(device, 0, backbuffer);
1793 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
1794 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)offscreenTexture);
1795 ok(SUCCEEDED(hr), "Failed to set texture, hr %#x.\n", hr);
1797 /* This time with the texture. */
1798 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(quad[0]));
1799 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
1801 hr = IDirect3DDevice9_EndScene(device);
1802 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
1804 /* Center quad - should be white */
1805 color = getPixelColor(device, 320, 240);
1806 ok(color == 0x00ffffff, "Offscreen failed: Got color 0x%08x, expected 0x00ffffff.\n", color);
1807 /* Some quad in the cleared part of the texture */
1808 color = getPixelColor(device, 170, 240);
1809 ok(color == 0x00ff00ff, "Offscreen failed: Got color 0x%08x, expected 0x00ff00ff.\n", color);
1810 /* Part of the originally cleared back buffer */
1811 color = getPixelColor(device, 10, 10);
1812 ok(color == 0x00ff0000, "Offscreen failed: Got color 0x%08x, expected 0x00ff0000.\n", color);
1813 color = getPixelColor(device, 10, 470);
1814 ok(color == 0x00ff0000, "Offscreen failed: Got color 0x%08x, expected 0x00ff0000.\n", color);
1816 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
1818 IDirect3DSurface9_Release(backbuffer);
1819 IDirect3DTexture9_Release(offscreenTexture);
1820 IDirect3DSurface9_Release(offscreen);
1821 refcount = IDirect3DDevice9_Release(device);
1822 ok(!refcount, "Device has %u references left.\n", refcount);
1823 done:
1824 IDirect3D9_Release(d3d);
1825 DestroyWindow(window);
1828 /* This test tests fog in combination with shaders.
1829 * What's tested: linear fog (vertex and table) with pixel shader
1830 * linear table fog with non foggy vertex shader
1831 * vertex fog with foggy vertex shader, non-linear
1832 * fog with shader, non-linear fog with foggy shader,
1833 * linear table fog with foggy shader */
1834 static void fog_with_shader_test(void)
1836 IDirect3DVertexShader9 *vertex_shader[4] = {NULL, NULL, NULL, NULL};
1837 IDirect3DPixelShader9 *pixel_shader[3] = {NULL, NULL, NULL};
1838 IDirect3DVertexDeclaration9 *vertex_declaration = NULL;
1839 IDirect3DDevice9 *device;
1840 unsigned int i, j;
1841 IDirect3D9 *d3d;
1842 ULONG refcount;
1843 D3DCAPS9 caps;
1844 DWORD color;
1845 HWND window;
1846 HRESULT hr;
1847 union
1849 float f;
1850 DWORD i;
1851 } start, end;
1853 /* basic vertex shader without fog computation ("non foggy") */
1854 static const DWORD vertex_shader_code1[] =
1856 0xfffe0101, /* vs_1_1 */
1857 0x0000001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
1858 0x0000001f, 0x8000000a, 0x900f0001, /* dcl_color0 v1 */
1859 0x00000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
1860 0x00000001, 0xd00f0000, 0x90e40001, /* mov oD0, v1 */
1861 0x0000ffff
1863 /* basic vertex shader with reversed fog computation ("foggy") */
1864 static const DWORD vertex_shader_code2[] =
1866 0xfffe0101, /* vs_1_1 */
1867 0x0000001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
1868 0x0000001f, 0x8000000a, 0x900f0001, /* dcl_color0 v1 */
1869 0x00000051, 0xa00f0000, 0xbfa00000, 0x00000000, 0xbf666666, 0x00000000, /* def c0, -1.25, 0.0, -0.9, 0.0 */
1870 0x00000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
1871 0x00000001, 0xd00f0000, 0x90e40001, /* mov oD0, v1 */
1872 0x00000002, 0x800f0000, 0x90aa0000, 0xa0aa0000, /* add r0, v0.z, c0.z */
1873 0x00000005, 0xc00f0001, 0x80000000, 0xa0000000, /* mul oFog, r0.x, c0.x */
1874 0x0000ffff
1876 /* basic vertex shader with reversed fog computation ("foggy"), vs_2_0 */
1877 static const DWORD vertex_shader_code3[] =
1879 0xfffe0200, /* vs_2_0 */
1880 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
1881 0x0200001f, 0x8000000a, 0x900f0001, /* dcl_color0 v1 */
1882 0x05000051, 0xa00f0000, 0xbfa00000, 0x00000000, 0xbf666666, 0x00000000, /* def c0, -1.25, 0.0, -0.9, 0.0 */
1883 0x02000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
1884 0x02000001, 0xd00f0000, 0x90e40001, /* mov oD0, v1 */
1885 0x03000002, 0x800f0000, 0x90aa0000, 0xa0aa0000, /* add r0, v0.z, c0.z */
1886 0x03000005, 0xc00f0001, 0x80000000, 0xa0000000, /* mul oFog, r0.x, c0.x */
1887 0x0000ffff
1889 /* basic pixel shader */
1890 static const DWORD pixel_shader_code[] =
1892 0xffff0101, /* ps_1_1 */
1893 0x00000001, 0x800f0000, 0x90e40000, /* mov r0, v0 */
1894 0x0000ffff
1896 static const DWORD pixel_shader_code2[] =
1898 0xffff0200, /* ps_2_0 */
1899 0x0200001f, 0x80000000, 0x900f0000, /* dcl v0 */
1900 0x02000001, 0x800f0800, 0x90e40000, /* mov oC0, v0 */
1901 0x0000ffff
1903 struct
1905 struct vec3 position;
1906 DWORD diffuse;
1908 quad[] =
1910 {{-1.0f, -1.0f, 0.0f}, 0xffff0000},
1911 {{-1.0f, 1.0f, 0.0f}, 0xffff0000},
1912 {{ 1.0f, -1.0f, 0.0f}, 0xffff0000},
1913 {{ 1.0f, 1.0f, 0.0f}, 0xffff0000},
1915 static const D3DVERTEXELEMENT9 decl_elements[] =
1917 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
1918 {0, 12, D3DDECLTYPE_D3DCOLOR, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR, 0},
1919 D3DDECL_END()
1921 /* This reference data was collected on a nVidia GeForce 7600GS driver
1922 * version 84.19 DirectX version 9.0c on Windows XP. */
1923 static const struct test_data_t
1925 int vshader;
1926 int pshader;
1927 D3DFOGMODE vfog;
1928 D3DFOGMODE tfog;
1929 unsigned int color[11];
1931 test_data[] =
1933 /* only pixel shader: */
1934 {0, 1, D3DFOG_NONE, D3DFOG_LINEAR,
1935 {0x00ff0000, 0x00ff0000, 0x00df2000, 0x00bf4000, 0x009f6000, 0x007f8000,
1936 0x005fa000, 0x0040bf00, 0x0020df00, 0x0000ff00, 0x0000ff00}},
1937 {0, 1, D3DFOG_EXP, D3DFOG_LINEAR,
1938 {0x00ff0000, 0x00ff0000, 0x00df2000, 0x00bf4000, 0x009f6000, 0x007f8000,
1939 0x005fa000, 0x0040bf00, 0x0020df00, 0x0000ff00, 0x0000ff00}},
1940 {0, 1, D3DFOG_EXP2, D3DFOG_LINEAR,
1941 {0x00ff0000, 0x00ff0000, 0x00df2000, 0x00bf4000, 0x009f6000, 0x007f8000,
1942 0x005fa000, 0x0040bf00, 0x0020df00, 0x0000ff00, 0x0000ff00}},
1943 {0, 1, D3DFOG_LINEAR, D3DFOG_NONE,
1944 {0x00ff0000, 0x00ff0000, 0x00df2000, 0x00bf4000, 0x009f6000, 0x007f8000,
1945 0x005fa000, 0x0040bf00, 0x0020df00, 0x0000ff00, 0x0000ff00}},
1946 {0, 1, D3DFOG_LINEAR, D3DFOG_LINEAR,
1947 {0x00ff0000, 0x00ff0000, 0x00df2000, 0x00bf4000, 0x009f6000, 0x007f8000,
1948 0x005fa000, 0x0040bf00, 0x0020df00, 0x0000ff00, 0x0000ff00}},
1950 /* vertex shader */
1951 {1, 0, D3DFOG_NONE, D3DFOG_NONE,
1952 {0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00,
1953 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00}},
1954 {1, 0, D3DFOG_NONE, D3DFOG_LINEAR,
1955 {0x00ff0000, 0x00ff0000, 0x00df2000, 0x00bf4000, 0x009f6000, 0x007f8000,
1956 0x005fa000, 0x0040bf00, 0x0020df00, 0x0000ff00, 0x0000ff00}},
1957 {1, 0, D3DFOG_EXP, D3DFOG_LINEAR,
1958 {0x00ff0000, 0x00ff0000, 0x00df2000, 0x00bf4000, 0x009f6000, 0x007f8000,
1959 0x005fa000, 0x0040bf00, 0x0020df00, 0x0000ff00, 0x0000ff00}},
1961 {1, 0, D3DFOG_EXP2, D3DFOG_LINEAR,
1962 {0x00ff0000, 0x00ff0000, 0x00df2000, 0x00bf4000, 0x009f6000, 0x007f8000,
1963 0x005fa000, 0x0040bf00, 0x0020df00, 0x0000ff00, 0x0000ff00}},
1964 {1, 0, D3DFOG_LINEAR, D3DFOG_LINEAR,
1965 {0x00ff0000, 0x00ff0000, 0x00df2000, 0x00bf4000, 0x009f6000, 0x007f8000,
1966 0x005fa000, 0x0040bf00, 0x0020df00, 0x0000ff00, 0x0000ff00}},
1968 /* vertex shader and pixel shader */
1969 /* The next 4 tests would read the fog coord output, but it isn't available.
1970 * The result is a fully fogged quad, no matter what the Z coord is. This is on
1971 * a geforce 7400, 97.52 driver, Windows Vista, but probably hardware dependent.
1972 * These tests should be disabled if some other hardware behaves differently
1974 {1, 1, D3DFOG_NONE, D3DFOG_NONE,
1975 {0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00,
1976 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00}},
1977 {1, 1, D3DFOG_LINEAR, D3DFOG_NONE,
1978 {0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00,
1979 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00}},
1980 {1, 1, D3DFOG_EXP, D3DFOG_NONE,
1981 {0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00,
1982 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00}},
1983 {1, 1, D3DFOG_EXP2, D3DFOG_NONE,
1984 {0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00,
1985 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00, 0x0000ff00}},
1987 /* These use the Z coordinate with linear table fog */
1988 {1, 1, D3DFOG_NONE, D3DFOG_LINEAR,
1989 {0x00ff0000, 0x00ff0000, 0x00df2000, 0x00bf4000, 0x009f6000, 0x007f8000,
1990 0x005fa000, 0x0040bf00, 0x0020df00, 0x0000ff00, 0x0000ff00}},
1991 {1, 1, D3DFOG_EXP, D3DFOG_LINEAR,
1992 {0x00ff0000, 0x00ff0000, 0x00df2000, 0x00bf4000, 0x009f6000, 0x007f8000,
1993 0x005fa000, 0x0040bf00, 0x0020df00, 0x0000ff00, 0x0000ff00}},
1994 {1, 1, D3DFOG_EXP2, D3DFOG_LINEAR,
1995 {0x00ff0000, 0x00ff0000, 0x00df2000, 0x00bf4000, 0x009f6000, 0x007f8000,
1996 0x005fa000, 0x0040bf00, 0x0020df00, 0x0000ff00, 0x0000ff00}},
1997 {1, 1, D3DFOG_LINEAR, D3DFOG_LINEAR,
1998 {0x00ff0000, 0x00ff0000, 0x00df2000, 0x00bf4000, 0x009f6000, 0x007f8000,
1999 0x005fa000, 0x0040bf00, 0x0020df00, 0x0000ff00, 0x0000ff00}},
2001 /* Non-linear table fog without fog coord */
2002 {1, 1, D3DFOG_NONE, D3DFOG_EXP,
2003 {0x00ff0000, 0x00e71800, 0x00d12e00, 0x00bd4200, 0x00ab5400, 0x009b6400,
2004 0x008d7200, 0x007f8000, 0x00738c00, 0x00689700, 0x005ea100}},
2005 {1, 1, D3DFOG_NONE, D3DFOG_EXP2,
2006 {0x00fd0200, 0x00f50200, 0x00f50a00, 0x00e91600, 0x00d92600, 0x00c73800,
2007 0x00b24d00, 0x009c6300, 0x00867900, 0x00728d00, 0x005ea100}},
2009 /* These tests fail on older Nvidia drivers */
2010 /* foggy vertex shader */
2011 {2, 0, D3DFOG_NONE, D3DFOG_NONE,
2012 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2013 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2014 {2, 0, D3DFOG_EXP, D3DFOG_NONE,
2015 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2016 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2017 {2, 0, D3DFOG_EXP2, D3DFOG_NONE,
2018 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2019 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2020 {2, 0, D3DFOG_LINEAR, D3DFOG_NONE,
2021 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2022 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2024 {3, 0, D3DFOG_NONE, D3DFOG_NONE,
2025 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2026 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2027 {3, 0, D3DFOG_EXP, D3DFOG_NONE,
2028 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2029 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2030 {3, 0, D3DFOG_EXP2, D3DFOG_NONE,
2031 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2032 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2033 {3, 0, D3DFOG_LINEAR, D3DFOG_NONE,
2034 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2035 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2037 /* foggy vertex shader and pixel shader. First 4 tests with vertex fog,
2038 * all using the fixed fog-coord linear fog
2040 /* vs_1_1 with ps_1_1 */
2041 {2, 1, D3DFOG_NONE, D3DFOG_NONE,
2042 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2043 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2044 {2, 1, D3DFOG_EXP, D3DFOG_NONE,
2045 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2046 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2047 {2, 1, D3DFOG_EXP2, D3DFOG_NONE,
2048 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2049 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2050 {2, 1, D3DFOG_LINEAR, D3DFOG_NONE,
2051 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2052 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2054 /* vs_2_0 with ps_1_1 */
2055 {3, 1, D3DFOG_NONE, D3DFOG_NONE,
2056 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2057 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2058 {3, 1, D3DFOG_EXP, D3DFOG_NONE,
2059 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2060 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2061 {3, 1, D3DFOG_EXP2, D3DFOG_NONE,
2062 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2063 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2064 {3, 1, D3DFOG_LINEAR, D3DFOG_NONE,
2065 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2066 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2068 /* vs_1_1 with ps_2_0 */
2069 {2, 2, D3DFOG_NONE, D3DFOG_NONE,
2070 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2071 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2072 {2, 2, D3DFOG_EXP, D3DFOG_NONE,
2073 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2074 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2075 {2, 2, D3DFOG_EXP2, D3DFOG_NONE,
2076 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2077 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2078 {2, 2, D3DFOG_LINEAR, D3DFOG_NONE,
2079 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2080 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2082 /* vs_2_0 with ps_2_0 */
2083 {3, 2, D3DFOG_NONE, D3DFOG_NONE,
2084 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2085 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2086 {3, 2, D3DFOG_EXP, D3DFOG_NONE,
2087 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2088 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2089 {3, 2, D3DFOG_EXP2, D3DFOG_NONE,
2090 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2091 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2092 {3, 2, D3DFOG_LINEAR, D3DFOG_NONE,
2093 {0x00ff0000, 0x00fe0100, 0x00de2100, 0x00bf4000, 0x009f6000, 0x007f8000,
2094 0x005fa000, 0x003fc000, 0x001fe000, 0x0000ff00, 0x0000ff00}},
2096 /* These use table fog. Here the shader-provided fog coordinate is
2097 * ignored and the z coordinate used instead
2099 {2, 1, D3DFOG_NONE, D3DFOG_EXP,
2100 {0x00ff0000, 0x00e71800, 0x00d12e00, 0x00bd4200, 0x00ab5400, 0x009b6400,
2101 0x008d7200, 0x007f8000, 0x00738c00, 0x00689700, 0x005ea100}},
2102 {2, 1, D3DFOG_NONE, D3DFOG_EXP2,
2103 {0x00fd0200, 0x00f50200, 0x00f50a00, 0x00e91600, 0x00d92600, 0x00c73800,
2104 0x00b24d00, 0x009c6300, 0x00867900, 0x00728d00, 0x005ea100}},
2105 {2, 1, D3DFOG_NONE, D3DFOG_LINEAR,
2106 {0x00ff0000, 0x00ff0000, 0x00df2000, 0x00bf4000, 0x009f6000, 0x007f8000,
2107 0x005fa000, 0x0040bf00, 0x0020df00, 0x0000ff00, 0x0000ff00}},
2109 static const D3DMATRIX identity =
2111 1.0f, 0.0f, 0.0f, 0.0f,
2112 0.0f, 1.0f, 0.0f, 0.0f,
2113 0.0f, 0.0f, 1.0f, 0.0f,
2114 0.0f, 0.0f, 0.0f, 1.0f,
2115 }}};
2117 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
2118 0, 0, 640, 480, NULL, NULL, NULL, NULL);
2119 d3d = Direct3DCreate9(D3D_SDK_VERSION);
2120 ok(!!d3d, "Failed to create a D3D object.\n");
2121 if (!(device = create_device(d3d, window, window, TRUE)))
2123 skip("Failed to create a D3D device, skipping tests.\n");
2124 goto done;
2127 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
2128 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
2129 if (caps.VertexShaderVersion < D3DVS_VERSION(2, 0) || caps.PixelShaderVersion < D3DPS_VERSION(2, 0))
2131 skip("No shader model 2 support, skipping tests.\n");
2132 IDirect3DDevice9_Release(device);
2133 goto done;
2136 /* NOTE: Changing these values will not affect the tests with foggy vertex
2137 * shader, as the values are hardcoded in the shader. */
2138 start.f = 0.1f;
2139 end.f = 0.9f;
2141 /* Some of the tests seem to depend on the projection matrix explicitly
2142 * being set to an identity matrix, even though that's the default.
2143 * (AMD Radeon HD 6310, Windows 7) */
2144 hr = IDirect3DDevice9_SetTransform(device, D3DTS_PROJECTION, &identity);
2145 ok(SUCCEEDED(hr), "Failed to set projection transform, hr %#x.\n", hr);
2147 hr = IDirect3DDevice9_CreateVertexShader(device, vertex_shader_code1, &vertex_shader[1]);
2148 ok(SUCCEEDED(hr), "CreateVertexShader failed (%08x)\n", hr);
2149 hr = IDirect3DDevice9_CreateVertexShader(device, vertex_shader_code2, &vertex_shader[2]);
2150 ok(SUCCEEDED(hr), "CreateVertexShader failed (%08x)\n", hr);
2151 hr = IDirect3DDevice9_CreateVertexShader(device, vertex_shader_code3, &vertex_shader[3]);
2152 ok(SUCCEEDED(hr), "CreateVertexShader failed (%08x)\n", hr);
2153 hr = IDirect3DDevice9_CreatePixelShader(device, pixel_shader_code, &pixel_shader[1]);
2154 ok(SUCCEEDED(hr), "CreatePixelShader failed (%08x)\n", hr);
2155 hr = IDirect3DDevice9_CreatePixelShader(device, pixel_shader_code2, &pixel_shader[2]);
2156 ok(SUCCEEDED(hr), "CreatePixelShader failed (%08x)\n", hr);
2157 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements, &vertex_declaration);
2158 ok(SUCCEEDED(hr), "CreateVertexDeclaration failed (%08x)\n", hr);
2160 /* Setup initial states: No lighting, fog on, fog color */
2161 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
2162 ok(hr == D3D_OK, "Turning off lighting failed (%08x)\n", hr);
2163 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGENABLE, TRUE);
2164 ok(hr == D3D_OK, "Turning on fog calculations failed (%08x)\n", hr);
2165 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGCOLOR, 0xff00ff00 /* A nice green */);
2166 ok(hr == D3D_OK, "Setting fog color failed (%08x)\n", hr);
2167 hr = IDirect3DDevice9_SetVertexDeclaration(device, vertex_declaration);
2168 ok(SUCCEEDED(hr), "SetVertexDeclaration failed (%08x)\n", hr);
2170 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGTABLEMODE, D3DFOG_NONE);
2171 ok(hr == D3D_OK, "Turning off table fog failed (%08x)\n", hr);
2172 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGVERTEXMODE, D3DFOG_NONE);
2173 ok(hr == D3D_OK, "Turning off vertex fog failed (%08x)\n", hr);
2175 /* Use fogtart = 0.1 and end = 0.9 to test behavior outside the fog transition phase, too*/
2176 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGSTART, start.i);
2177 ok(hr == D3D_OK, "Setting fog start failed (%08x)\n", hr);
2178 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGEND, end.i);
2179 ok(hr == D3D_OK, "Setting fog end failed (%08x)\n", hr);
2181 for (i = 0; i < sizeof(test_data)/sizeof(test_data[0]); i++)
2183 hr = IDirect3DDevice9_SetVertexShader(device, vertex_shader[test_data[i].vshader]);
2184 ok(SUCCEEDED(hr), "SetVertexShader failed (%08x)\n", hr);
2185 hr = IDirect3DDevice9_SetPixelShader(device, pixel_shader[test_data[i].pshader]);
2186 ok(SUCCEEDED(hr), "SetPixelShader failed (%08x)\n", hr);
2187 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGVERTEXMODE, test_data[i].vfog);
2188 ok( hr == D3D_OK, "Setting fog vertex mode to D3DFOG_LINEAR failed (%08x)\n", hr);
2189 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGTABLEMODE, test_data[i].tfog);
2190 ok( hr == D3D_OK, "Setting fog table mode to D3DFOG_LINEAR failed (%08x)\n", hr);
2192 for(j=0; j < 11; j++)
2194 /* Don't use the whole zrange to prevent rounding errors */
2195 quad[0].position.z = 0.001f + (float)j / 10.02f;
2196 quad[1].position.z = 0.001f + (float)j / 10.02f;
2197 quad[2].position.z = 0.001f + (float)j / 10.02f;
2198 quad[3].position.z = 0.001f + (float)j / 10.02f;
2200 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffff00ff, 1.0f, 0);
2201 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed (%08x)\n", hr);
2203 hr = IDirect3DDevice9_BeginScene(device);
2204 ok( hr == D3D_OK, "BeginScene returned failed (%08x)\n", hr);
2206 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quad[0], sizeof(quad[0]));
2207 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed (%08x)\n", hr);
2209 hr = IDirect3DDevice9_EndScene(device);
2210 ok(hr == D3D_OK, "EndScene failed (%08x)\n", hr);
2212 /* As the red and green component are the result of blending use 5% tolerance on the expected value */
2213 color = getPixelColor(device, 128, 240);
2214 ok(color_match(color, test_data[i].color[j], 13),
2215 "fog vs%i ps%i fvm%i ftm%i %d: got color %08x, expected %08x +-5%%\n",
2216 test_data[i].vshader, test_data[i].pshader, test_data[i].vfog, test_data[i].tfog, j, color, test_data[i].color[j]);
2218 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
2222 IDirect3DVertexShader9_Release(vertex_shader[1]);
2223 IDirect3DVertexShader9_Release(vertex_shader[2]);
2224 IDirect3DVertexShader9_Release(vertex_shader[3]);
2225 IDirect3DPixelShader9_Release(pixel_shader[1]);
2226 IDirect3DPixelShader9_Release(pixel_shader[2]);
2227 IDirect3DVertexDeclaration9_Release(vertex_declaration);
2228 refcount = IDirect3DDevice9_Release(device);
2229 ok(!refcount, "Device has %u references left.\n", refcount);
2230 done:
2231 IDirect3D9_Release(d3d);
2232 DestroyWindow(window);
2235 static void generate_bumpmap_textures(IDirect3DDevice9 *device) {
2236 unsigned int i, x, y;
2237 HRESULT hr;
2238 IDirect3DTexture9 *texture[2] = {NULL, NULL};
2239 D3DLOCKED_RECT locked_rect;
2241 /* Generate the textures */
2242 for(i=0; i<2; i++)
2244 hr = IDirect3DDevice9_CreateTexture(device, 128, 128, 1, 0, i?D3DFMT_A8R8G8B8:D3DFMT_V8U8,
2245 D3DPOOL_MANAGED, &texture[i], NULL);
2246 ok(SUCCEEDED(hr), "CreateTexture failed (0x%08x)\n", hr);
2248 hr = IDirect3DTexture9_LockRect(texture[i], 0, &locked_rect, NULL, 0);
2249 ok(SUCCEEDED(hr), "LockRect failed (0x%08x)\n", hr);
2250 for (y = 0; y < 128; ++y)
2252 if(i)
2253 { /* Set up black texture with 2x2 texel white spot in the middle */
2254 DWORD *ptr = (DWORD *)(((BYTE *)locked_rect.pBits) + (y * locked_rect.Pitch));
2255 for (x = 0; x < 128; ++x)
2257 *ptr++ = D3DCOLOR_ARGB(0xff, x * 2, y * 2, 0);
2260 else
2261 { /* Set up a displacement map which points away from the center parallel to the closest axis.
2262 * (if multiplied with bumpenvmat)
2264 WORD *ptr = (WORD *)(((BYTE *)locked_rect.pBits) + (y * locked_rect.Pitch));
2265 for (x = 0; x < 128; ++x)
2267 if(abs(x-64)>abs(y-64))
2269 if(x < 64)
2270 *ptr++ = 0xc000;
2271 else
2272 *ptr++ = 0x4000;
2274 else
2276 if(y < 64)
2277 *ptr++ = 0x0040;
2278 else
2279 *ptr++ = 0x00c0;
2284 hr = IDirect3DTexture9_UnlockRect(texture[i], 0);
2285 ok(SUCCEEDED(hr), "UnlockRect failed (0x%08x)\n", hr);
2287 hr = IDirect3DDevice9_SetTexture(device, i, (IDirect3DBaseTexture9 *)texture[i]);
2288 ok(SUCCEEDED(hr), "SetTexture failed (0x%08x)\n", hr);
2290 /* Disable texture filtering */
2291 hr = IDirect3DDevice9_SetSamplerState(device, i, D3DSAMP_MINFILTER, D3DTEXF_POINT);
2292 ok(SUCCEEDED(hr), "SetSamplerState D3DSAMP_MINFILTER failed (0x%08x)\n", hr);
2293 hr = IDirect3DDevice9_SetSamplerState(device, i, D3DSAMP_MAGFILTER, D3DTEXF_POINT);
2294 ok(SUCCEEDED(hr), "SetSamplerState D3DSAMP_MAGFILTER failed (0x%08x)\n", hr);
2296 hr = IDirect3DDevice9_SetSamplerState(device, i, D3DSAMP_ADDRESSU, D3DTADDRESS_CLAMP);
2297 ok(SUCCEEDED(hr), "SetSamplerState D3DSAMP_ADDRESSU failed (0x%08x)\n", hr);
2298 hr = IDirect3DDevice9_SetSamplerState(device, i, D3DSAMP_ADDRESSV, D3DTADDRESS_CLAMP);
2299 ok(SUCCEEDED(hr), "SetSamplerState D3DSAMP_ADDRESSV failed (0x%08x)\n", hr);
2303 /* Test the behavior of the texbem instruction with normal 2D and projective
2304 * 2D textures. */
2305 static void texbem_test(void)
2307 IDirect3DVertexDeclaration9 *vertex_declaration = NULL;
2308 /* Use asymmetric matrix to test loading. */
2309 float bumpenvmat[4] = {0.0f, 0.5f, -0.5f, 0.0f};
2310 IDirect3DPixelShader9 *pixel_shader = NULL;
2311 IDirect3DTexture9 *texture1, *texture2;
2312 IDirect3DTexture9 *texture = NULL;
2313 D3DLOCKED_RECT locked_rect;
2314 IDirect3DDevice9 *device;
2315 IDirect3D9 *d3d;
2316 ULONG refcount;
2317 D3DCAPS9 caps;
2318 DWORD color;
2319 HWND window;
2320 HRESULT hr;
2321 int i;
2323 static const DWORD pixel_shader_code[] =
2325 0xffff0101, /* ps_1_1*/
2326 0x00000042, 0xb00f0000, /* tex t0*/
2327 0x00000043, 0xb00f0001, 0xb0e40000, /* texbem t1, t0*/
2328 0x00000001, 0x800f0000, 0xb0e40001, /* mov r0, t1*/
2329 0x0000ffff
2331 static const DWORD double_texbem_code[] =
2333 0xffff0103, /* ps_1_3 */
2334 0x00000042, 0xb00f0000, /* tex t0 */
2335 0x00000043, 0xb00f0001, 0xb0e40000, /* texbem t1, t0 */
2336 0x00000042, 0xb00f0002, /* tex t2 */
2337 0x00000043, 0xb00f0003, 0xb0e40002, /* texbem t3, t2 */
2338 0x00000002, 0x800f0000, 0xb0e40001, 0xb0e40003, /* add r0, t1, t3 */
2339 0x0000ffff /* end */
2341 static const float quad[][7] =
2343 {-1.0f, -1.0f, 0.1f, 0.0f, 0.0f, 0.0f, 0.0f},
2344 {-1.0f, 1.0f, 0.1f, 0.0f, 1.0f, 0.0f, 1.0f},
2345 { 1.0f, -1.0f, 0.1f, 1.0f, 0.0f, 1.0f, 0.0f},
2346 { 1.0f, 1.0f, 0.1f, 1.0f, 1.0f, 1.0f, 1.0f},
2348 static const float quad_proj[][9] =
2350 {-1.0f, -1.0f, 0.1f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 128.0f},
2351 {-1.0f, 1.0f, 0.1f, 0.0f, 1.0f, 0.0f, 128.0f, 0.0f, 128.0f},
2352 { 1.0f, -1.0f, 0.1f, 1.0f, 0.0f, 128.0f, 0.0f, 0.0f, 128.0f},
2353 { 1.0f, 1.0f, 0.1f, 1.0f, 1.0f, 128.0f, 128.0f, 0.0f, 128.0f},
2355 static const float double_quad[] =
2357 -1.0f, -1.0f, 0.0f, 0.0f, 0.0f, 0.5f, 0.5f, 0.0f, 0.0f, 0.5f, 0.5f,
2358 -1.0f, 1.0f, 0.0f, 0.0f, 0.0f, 0.5f, 0.5f, 0.0f, 0.0f, 0.5f, 0.5f,
2359 1.0f, -1.0f, 0.0f, 0.0f, 0.0f, 0.5f, 0.5f, 0.0f, 0.0f, 0.5f, 0.5f,
2360 1.0f, 1.0f, 0.0f, 0.0f, 0.0f, 0.5f, 0.5f, 0.0f, 0.0f, 0.5f, 0.5f,
2362 static const D3DVERTEXELEMENT9 decl_elements[][4] =
2365 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
2366 {0, 12, D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
2367 {0, 20, D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 1},
2368 D3DDECL_END()
2371 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
2372 {0, 12, D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
2373 {0, 20, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 1},
2374 D3DDECL_END()
2378 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
2379 0, 0, 640, 480, NULL, NULL, NULL, NULL);
2380 d3d = Direct3DCreate9(D3D_SDK_VERSION);
2381 ok(!!d3d, "Failed to create a D3D object.\n");
2382 if (!(device = create_device(d3d, window, window, TRUE)))
2384 skip("Failed to create a D3D device, skipping tests.\n");
2385 goto done;
2388 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
2389 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
2390 if (caps.PixelShaderVersion < D3DPS_VERSION(1, 1))
2392 skip("No ps_1_1 support, skipping tests.\n");
2393 IDirect3DDevice9_Release(device);
2394 goto done;
2397 generate_bumpmap_textures(device);
2399 IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_BUMPENVMAT00, *(LPDWORD)&bumpenvmat[0]);
2400 IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_BUMPENVMAT01, *(LPDWORD)&bumpenvmat[1]);
2401 IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_BUMPENVMAT10, *(LPDWORD)&bumpenvmat[2]);
2402 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_BUMPENVMAT11, *(LPDWORD)&bumpenvmat[3]);
2403 ok(SUCCEEDED(hr), "SetTextureStageState failed (%08x)\n", hr);
2405 hr = IDirect3DDevice9_SetVertexShader(device, NULL);
2406 ok(SUCCEEDED(hr), "SetVertexShader failed (%08x)\n", hr);
2408 for(i=0; i<2; i++)
2410 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff0000ff, 1.0f, 0);
2411 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed (%08x)\n", hr);
2413 if(i)
2415 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_TEXTURETRANSFORMFLAGS, D3DTTFF_COUNT4|D3DTTFF_PROJECTED);
2416 ok(SUCCEEDED(hr), "SetTextureStageState D3DTSS_TEXTURETRANSFORMFLAGS failed (0x%08x)\n", hr);
2419 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements[i], &vertex_declaration);
2420 ok(SUCCEEDED(hr), "CreateVertexDeclaration failed (0x%08x)\n", hr);
2421 hr = IDirect3DDevice9_SetVertexDeclaration(device, vertex_declaration);
2422 ok(SUCCEEDED(hr), "SetVertexDeclaration failed (0x%08x)\n", hr);
2424 hr = IDirect3DDevice9_CreatePixelShader(device, pixel_shader_code, &pixel_shader);
2425 ok(SUCCEEDED(hr), "CreatePixelShader failed (%08x)\n", hr);
2426 hr = IDirect3DDevice9_SetPixelShader(device, pixel_shader);
2427 ok(SUCCEEDED(hr), "SetPixelShader failed (%08x)\n", hr);
2429 hr = IDirect3DDevice9_BeginScene(device);
2430 ok(SUCCEEDED(hr), "BeginScene failed (0x%08x)\n", hr);
2432 if(!i)
2433 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quad[0], sizeof(quad[0]));
2434 else
2435 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quad_proj[0], sizeof(quad_proj[0]));
2436 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed (0x%08x)\n", hr);
2438 hr = IDirect3DDevice9_EndScene(device);
2439 ok(SUCCEEDED(hr), "EndScene failed (0x%08x)\n", hr);
2441 /* The Window 8 testbot (WARP) seems to use the transposed
2442 * D3DTSS_BUMPENVMAT matrix. */
2443 color = getPixelColor(device, 160, 240);
2444 ok(color_match(color, 0x007e8000, 4) || broken(color_match(color, 0x00007e00, 4)),
2445 "Got unexpected color 0x%08x.\n", color);
2446 color = getPixelColor(device, 480, 240);
2447 ok(color_match(color, 0x007e8000, 4) || broken(color_match(color, 0x00fe7e00, 4)),
2448 "Got unexpected color 0x%08x.\n", color);
2449 color = getPixelColor(device, 320, 120);
2450 ok(color_match(color, 0x007e8000, 4) || broken(color_match(color, 0x0080fe00, 4)),
2451 "Got unexpected color 0x%08x.\n", color);
2452 color = getPixelColor(device, 320, 360);
2453 ok(color_match(color, 0x007e8000, 4) || broken(color_match(color, 0x00800000, 4)),
2454 "Got unexpected color 0x%08x.\n", color);
2456 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
2457 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
2459 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
2460 ok(SUCCEEDED(hr), "SetPixelShader failed (%08x)\n", hr);
2461 IDirect3DPixelShader9_Release(pixel_shader);
2463 hr = IDirect3DDevice9_SetVertexDeclaration(device, NULL);
2464 ok(SUCCEEDED(hr), "SetVertexDeclaration failed (%08x)\n", hr);
2465 IDirect3DVertexDeclaration9_Release(vertex_declaration);
2468 /* clean up */
2469 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0, 0.0f, 0);
2470 ok(SUCCEEDED(hr), "Clear failed (0x%08x)\n", hr);
2472 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_TEXTURETRANSFORMFLAGS, D3DTTFF_COUNT2);
2473 ok(SUCCEEDED(hr), "SetTextureStageState D3DTSS_TEXTURETRANSFORMFLAGS failed (0x%08x)\n", hr);
2475 for(i=0; i<2; i++)
2477 hr = IDirect3DDevice9_GetTexture(device, i, (IDirect3DBaseTexture9 **) &texture);
2478 ok(SUCCEEDED(hr), "IDirect3DDevice9_GetTexture failed (0x%08x)\n", hr);
2479 IDirect3DTexture9_Release(texture); /* For the GetTexture */
2480 hr = IDirect3DDevice9_SetTexture(device, i, NULL);
2481 ok(SUCCEEDED(hr), "SetTexture failed (0x%08x)\n", hr);
2482 IDirect3DTexture9_Release(texture);
2485 /* Test double texbem */
2486 hr = IDirect3DDevice9_CreateTexture(device, 1, 1, 1, 0, D3DFMT_V8U8, D3DPOOL_MANAGED, &texture, NULL);
2487 ok(SUCCEEDED(hr), "IDirect3DDevice9_CreateTexture failed (0x%08x)\n", hr);
2488 hr = IDirect3DDevice9_CreateTexture(device, 1, 1, 1, 0, D3DFMT_V8U8, D3DPOOL_MANAGED, &texture1, NULL);
2489 ok(SUCCEEDED(hr), "IDirect3DDevice9_CreateTexture failed (0x%08x)\n", hr);
2490 hr = IDirect3DDevice9_CreateTexture(device, 8, 8, 1, 0, D3DFMT_A8R8G8B8, D3DPOOL_MANAGED, &texture2, NULL);
2491 ok(SUCCEEDED(hr), "IDirect3DDevice9_CreateTexture failed (0x%08x)\n", hr);
2492 hr = IDirect3DDevice9_CreatePixelShader(device, double_texbem_code, &pixel_shader);
2493 ok(SUCCEEDED(hr), "CreatePixelShader failed (%08x)\n", hr);
2495 hr = IDirect3DTexture9_LockRect(texture, 0, &locked_rect, NULL, 0);
2496 ok(SUCCEEDED(hr), "LockRect failed (0x%08x)\n", hr);
2497 ((signed char *) locked_rect.pBits)[0] = (-1.0 / 8.0) * 127;
2498 ((signed char *) locked_rect.pBits)[1] = ( 1.0 / 8.0) * 127;
2500 hr = IDirect3DTexture9_UnlockRect(texture, 0);
2501 ok(SUCCEEDED(hr), "LockRect failed (0x%08x)\n", hr);
2503 hr = IDirect3DTexture9_LockRect(texture1, 0, &locked_rect, NULL, 0);
2504 ok(SUCCEEDED(hr), "LockRect failed (0x%08x)\n", hr);
2505 ((signed char *) locked_rect.pBits)[0] = (-2.0 / 8.0) * 127;
2506 ((signed char *) locked_rect.pBits)[1] = (-4.0 / 8.0) * 127;
2507 hr = IDirect3DTexture9_UnlockRect(texture1, 0);
2508 ok(SUCCEEDED(hr), "LockRect failed (0x%08x)\n", hr);
2511 /* Some data without any meaning, just to have an 8x8 array to see which element is picked */
2512 #define tex 0x00ff0000
2513 #define tex1 0x0000ff00
2514 #define origin 0x000000ff
2515 static const DWORD pixel_data[] = {
2516 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff,
2517 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff,
2518 0x000000ff, tex1 , 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff,
2519 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff,
2520 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, origin, 0x000000ff, tex , 0x000000ff,
2521 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff,
2522 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff,
2523 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff, 0x000000ff,
2525 #undef tex1
2526 #undef tex2
2527 #undef origin
2529 hr = IDirect3DTexture9_LockRect(texture2, 0, &locked_rect, NULL, 0);
2530 ok(SUCCEEDED(hr), "LockRect failed (0x%08x)\n", hr);
2531 for(i = 0; i < 8; i++) {
2532 memcpy(((char *) locked_rect.pBits) + i * locked_rect.Pitch, pixel_data + 8 * i, 8 * sizeof(DWORD));
2534 hr = IDirect3DTexture9_UnlockRect(texture2, 0);
2535 ok(SUCCEEDED(hr), "LockRect failed (0x%08x)\n", hr);
2538 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *) texture);
2539 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTexture failed (0x%08x)\n", hr);
2540 hr = IDirect3DDevice9_SetTexture(device, 1, (IDirect3DBaseTexture9 *) texture2);
2541 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTexture failed (0x%08x)\n", hr);
2542 hr = IDirect3DDevice9_SetTexture(device, 2, (IDirect3DBaseTexture9 *) texture1);
2543 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTexture failed (0x%08x)\n", hr);
2544 hr = IDirect3DDevice9_SetTexture(device, 3, (IDirect3DBaseTexture9 *) texture2);
2545 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTexture failed (0x%08x)\n", hr);
2546 hr = IDirect3DDevice9_SetPixelShader(device, pixel_shader);
2547 ok(SUCCEEDED(hr), "Direct3DDevice9_SetPixelShader failed (0x%08x)\n", hr);
2548 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX4);
2549 ok(SUCCEEDED(hr), "Direct3DDevice9_SetPixelShader failed (0x%08x)\n", hr);
2551 bumpenvmat[0] =-1.0; bumpenvmat[2] = 2.0;
2552 bumpenvmat[1] = 0.0; bumpenvmat[3] = 0.0;
2553 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_BUMPENVMAT00, *(LPDWORD)&bumpenvmat[0]);
2554 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTextureStageState returned %#x.\n", hr);
2555 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_BUMPENVMAT01, *(LPDWORD)&bumpenvmat[1]);
2556 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTextureStageState returned %#x.\n", hr);
2557 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_BUMPENVMAT10, *(LPDWORD)&bumpenvmat[2]);
2558 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTextureStageState returned %#x.\n", hr);
2559 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_BUMPENVMAT11, *(LPDWORD)&bumpenvmat[3]);
2560 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTextureStageState returned %#x.\n", hr);
2562 bumpenvmat[0] = 1.5; bumpenvmat[2] = 0.0;
2563 bumpenvmat[1] = 0.0; bumpenvmat[3] = 0.5;
2564 hr = IDirect3DDevice9_SetTextureStageState(device, 3, D3DTSS_BUMPENVMAT00, *(LPDWORD)&bumpenvmat[0]);
2565 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTextureStageState returned %#x.\n", hr);
2566 hr = IDirect3DDevice9_SetTextureStageState(device, 3, D3DTSS_BUMPENVMAT01, *(LPDWORD)&bumpenvmat[1]);
2567 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTextureStageState returned %#x.\n", hr);
2568 hr = IDirect3DDevice9_SetTextureStageState(device, 3, D3DTSS_BUMPENVMAT10, *(LPDWORD)&bumpenvmat[2]);
2569 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTextureStageState returned %#x.\n", hr);
2570 hr = IDirect3DDevice9_SetTextureStageState(device, 3, D3DTSS_BUMPENVMAT11, *(LPDWORD)&bumpenvmat[3]);
2571 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTextureStageState returned %#x.\n", hr);
2573 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_ADDRESSU, D3DTADDRESS_CLAMP);
2574 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetSamplerState returned %#x.\n", hr);
2575 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_ADDRESSV, D3DTADDRESS_CLAMP);
2576 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetSamplerState returned %#x.\n", hr);
2577 hr = IDirect3DDevice9_SetSamplerState(device, 1, D3DSAMP_ADDRESSU, D3DTADDRESS_CLAMP);
2578 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetSamplerState returned %#x.\n", hr);
2579 hr = IDirect3DDevice9_SetSamplerState(device, 1, D3DSAMP_ADDRESSV, D3DTADDRESS_CLAMP);
2580 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetSamplerState returned %#x.\n", hr);
2581 hr = IDirect3DDevice9_SetSamplerState(device, 2, D3DSAMP_ADDRESSU, D3DTADDRESS_CLAMP);
2582 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetSamplerState returned %#x.\n", hr);
2583 hr = IDirect3DDevice9_SetSamplerState(device, 2, D3DSAMP_ADDRESSV, D3DTADDRESS_CLAMP);
2584 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetSamplerState returned %#x.\n", hr);
2585 hr = IDirect3DDevice9_SetSamplerState(device, 3, D3DSAMP_ADDRESSU, D3DTADDRESS_CLAMP);
2586 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetSamplerState returned %#x.\n", hr);
2587 hr = IDirect3DDevice9_SetSamplerState(device, 3, D3DSAMP_ADDRESSV, D3DTADDRESS_CLAMP);
2588 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetSamplerState returned %#x.\n", hr);
2590 hr = IDirect3DDevice9_BeginScene(device);
2591 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
2592 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, double_quad, sizeof(float) * 11);
2593 ok(SUCCEEDED(hr), "Failed to draw primitive, hr %#x.\n", hr);
2594 hr = IDirect3DDevice9_EndScene(device);
2595 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
2596 /* The Window 8 testbot (WARP) seems to use the transposed
2597 * D3DTSS_BUMPENVMAT matrix. */
2598 color = getPixelColor(device, 320, 240);
2599 ok(color_match(color, 0x00ffff00, 1) || broken(color_match(color, 0x0000ffff, 1)),
2600 "Got unexpected color 0x%08x.\n", color);
2602 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
2603 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
2605 IDirect3DPixelShader9_Release(pixel_shader);
2606 IDirect3DTexture9_Release(texture);
2607 IDirect3DTexture9_Release(texture1);
2608 IDirect3DTexture9_Release(texture2);
2609 refcount = IDirect3DDevice9_Release(device);
2610 ok(!refcount, "Device has %u references left.\n", refcount);
2611 done:
2612 IDirect3D9_Release(d3d);
2613 DestroyWindow(window);
2616 static void z_range_test(void)
2618 IDirect3DVertexShader9 *shader;
2619 IDirect3DDevice9 *device;
2620 IDirect3D9 *d3d;
2621 ULONG refcount;
2622 D3DCAPS9 caps;
2623 DWORD color;
2624 HWND window;
2625 HRESULT hr;
2627 static const struct
2629 struct vec3 position;
2630 DWORD diffuse;
2632 quad[] =
2634 {{-1.0f, 0.0f, 1.1f}, 0xffff0000},
2635 {{-1.0f, 1.0f, 1.1f}, 0xffff0000},
2636 {{ 1.0f, 0.0f, -1.1f}, 0xffff0000},
2637 {{ 1.0f, 1.0f, -1.1f}, 0xffff0000},
2639 quad2[] =
2641 {{-1.0f, 0.0f, 1.1f}, 0xff0000ff},
2642 {{-1.0f, 1.0f, 1.1f}, 0xff0000ff},
2643 {{ 1.0f, 0.0f, -1.1f}, 0xff0000ff},
2644 {{ 1.0f, 1.0f, -1.1f}, 0xff0000ff},
2646 static const struct
2648 struct vec4 position;
2649 DWORD diffuse;
2651 quad3[] =
2653 {{640.0f, 240.0f, -1.1f, 1.0f}, 0xffffff00},
2654 {{640.0f, 480.0f, -1.1f, 1.0f}, 0xffffff00},
2655 {{ 0.0f, 240.0f, 1.1f, 1.0f}, 0xffffff00},
2656 {{ 0.0f, 480.0f, 1.1f, 1.0f}, 0xffffff00},
2658 quad4[] =
2660 {{640.0f, 240.0f, -1.1f, 1.0f}, 0xff00ff00},
2661 {{640.0f, 480.0f, -1.1f, 1.0f}, 0xff00ff00},
2662 {{ 0.0f, 240.0f, 1.1f, 1.0f}, 0xff00ff00},
2663 {{ 0.0f, 480.0f, 1.1f, 1.0f}, 0xff00ff00},
2665 static const DWORD shader_code[] =
2667 0xfffe0101, /* vs_1_1 */
2668 0x0000001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
2669 0x00000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
2670 0x00000001, 0xd00f0000, 0xa0e40000, /* mov oD0, c0 */
2671 0x0000ffff /* end */
2673 static const float color_const_1[] = {1.0f, 0.0f, 0.0f, 1.0f};
2674 static const float color_const_2[] = {0.0f, 0.0f, 1.0f, 1.0f};
2676 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
2677 0, 0, 640, 480, NULL, NULL, NULL, NULL);
2678 d3d = Direct3DCreate9(D3D_SDK_VERSION);
2679 ok(!!d3d, "Failed to create a D3D object.\n");
2680 if (!(device = create_device(d3d, window, window, TRUE)))
2682 skip("Failed to create a D3D device, skipping tests.\n");
2683 goto done;
2686 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
2687 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
2689 /* Does the Present clear the depth stencil? Clear the depth buffer with some value != 0,
2690 * then call Present. Then clear the color buffer to make sure it has some defined content
2691 * after the Present with D3DSWAPEFFECT_DISCARD. After that draw a plane that is somewhere cut
2692 * by the depth value. */
2693 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffffffff, 0.75f, 0);
2694 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
2695 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
2696 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
2697 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffffffff, 0.0f, 0);
2698 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
2700 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
2701 ok(SUCCEEDED(hr), "Failed to disable lighting, hr %#x.\n", hr);
2702 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_CLIPPING, TRUE);
2703 ok(SUCCEEDED(hr), "Failed to enable clipping, hr %#x.\n", hr);
2704 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, D3DZB_TRUE);
2705 ok(SUCCEEDED(hr), "Failed to enable z test, hr %#x.\n", hr);
2706 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, FALSE);
2707 ok(SUCCEEDED(hr), "Failed to disable z writes, hr %#x.\n", hr);
2708 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZFUNC, D3DCMP_GREATER);
2709 ok(SUCCEEDED(hr), "Failed to set z function, hr %#x.\n", hr);
2710 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
2711 ok(SUCCEEDED(hr), "Failed set FVF, hr %#x.\n", hr);
2713 hr = IDirect3DDevice9_BeginScene(device);
2714 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
2716 /* Test the untransformed vertex path */
2717 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(quad[0]));
2718 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
2719 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZFUNC, D3DCMP_LESS);
2720 ok(SUCCEEDED(hr), "Failed to set z function, hr %#x.\n", hr);
2721 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, sizeof(quad2[0]));
2722 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
2724 /* Test the transformed vertex path */
2725 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZRHW | D3DFVF_DIFFUSE);
2726 ok(SUCCEEDED(hr), "Failed set FVF, hr %#x.\n", hr);
2728 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad4, sizeof(quad4[0]));
2729 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
2730 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZFUNC, D3DCMP_GREATER);
2731 ok(SUCCEEDED(hr), "Failed to set z function, hr %#x.\n", hr);
2732 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad3, sizeof(quad3[0]));
2733 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
2735 hr = IDirect3DDevice9_EndScene(device);
2736 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
2738 /* Do not test the exact corner pixels, but go pretty close to them */
2740 /* Clipped because z > 1.0 */
2741 color = getPixelColor(device, 28, 238);
2742 ok(color_match(color, 0x00ffffff, 0), "Z range failed: Got color 0x%08x, expected 0x00ffffff.\n", color);
2743 color = getPixelColor(device, 28, 241);
2744 if (caps.PrimitiveMiscCaps & D3DPMISCCAPS_CLIPTLVERTS)
2745 ok(color_match(color, 0x00ffffff, 0), "Z range failed: Got color 0x%08x, expected 0x00ffffff.\n", color);
2746 else
2747 ok(color_match(color, 0x00ffff00, 0), "Z range failed: Got color 0x%08x, expected 0x00ffff00.\n", color);
2749 /* Not clipped, > z buffer clear value(0.75).
2751 * On the r500 driver on Windows D3DCMP_GREATER and D3DCMP_GREATEREQUAL are broken for depth
2752 * values > 0.5. The range appears to be distorted, apparently an incoming value of ~0.875 is
2753 * equal to a stored depth buffer value of 0.5. */
2754 color = getPixelColor(device, 31, 238);
2755 ok(color_match(color, 0x00ff0000, 0), "Z range failed: Got color 0x%08x, expected 0x00ff0000.\n", color);
2756 color = getPixelColor(device, 31, 241);
2757 ok(color_match(color, 0x00ffff00, 0), "Z range failed: Got color 0x%08x, expected 0x00ffff00.\n", color);
2758 color = getPixelColor(device, 100, 238);
2759 ok(color_match(color, 0x00ff0000, 0) || broken(color_match(color, 0x00ffffff, 0)),
2760 "Z range failed: Got color 0x%08x, expected 0x00ff0000.\n", color);
2761 color = getPixelColor(device, 100, 241);
2762 ok(color_match(color, 0x00ffff00, 0) || broken(color_match(color, 0x00ffffff, 0)),
2763 "Z range failed: Got color 0x%08x, expected 0x00ffff00.\n", color);
2765 /* Not clipped, < z buffer clear value */
2766 color = getPixelColor(device, 104, 238);
2767 ok(color_match(color, 0x000000ff, 0), "Z range failed: Got color 0x%08x, expected 0x000000ff.\n", color);
2768 color = getPixelColor(device, 104, 241);
2769 ok(color_match(color, 0x0000ff00, 0), "Z range failed: Got color 0x%08x, expected 0x0000ff00.\n", color);
2770 color = getPixelColor(device, 318, 238);
2771 ok(color_match(color, 0x000000ff, 0), "Z range failed: Got color 0x%08x, expected 0x000000ff.\n", color);
2772 color = getPixelColor(device, 318, 241);
2773 ok(color_match(color, 0x0000ff00, 0), "Z range failed: Got color 0x%08x, expected 0x0000ff00.\n", color);
2775 /* Clipped because z < 0.0 */
2776 color = getPixelColor(device, 321, 238);
2777 ok(color_match(color, 0x00ffffff, 0), "Z range failed: Got color 0x%08x, expected 0x00ffffff.\n", color);
2778 color = getPixelColor(device, 321, 241);
2779 if (caps.PrimitiveMiscCaps & D3DPMISCCAPS_CLIPTLVERTS)
2780 ok(color_match(color, 0x00ffffff, 0), "Z range failed: Got color 0x%08x, expected 0x00ffffff.\n", color);
2781 else
2782 ok(color_match(color, 0x0000ff00, 0), "Z range failed: Got color 0x%08x, expected 0x00ffffff.\n", color);
2784 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
2785 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
2787 /* Test the shader path */
2788 if (caps.VertexShaderVersion < D3DVS_VERSION(1, 1))
2790 skip("Vertex shaders not supported, skipping tests.\n");
2791 IDirect3DDevice9_Release(device);
2792 goto done;
2794 hr = IDirect3DDevice9_CreateVertexShader(device, shader_code, &shader);
2795 ok(SUCCEEDED(hr), "Failed to create vertex shader, hr %#x.\n", hr);
2797 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffffffff, 0.0f, 0);
2798 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
2800 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ);
2801 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
2802 hr = IDirect3DDevice9_SetVertexShader(device, shader);
2803 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
2805 hr = IDirect3DDevice9_BeginScene(device);
2806 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
2808 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 0, color_const_1, 1);
2809 ok(SUCCEEDED(hr), "Failed to set vs constant 0, hr %#x.\n", hr);
2810 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(quad[0]));
2811 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
2813 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZFUNC, D3DCMP_LESS);
2814 ok(SUCCEEDED(hr), "Failed to set z function, hr %#x.\n", hr);
2815 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 0, color_const_2, 1);
2816 ok(SUCCEEDED(hr), "Failed to set vs constant 0, hr %#x.\n", hr);
2817 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, sizeof(quad2[0]));
2818 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
2820 hr = IDirect3DDevice9_EndScene(device);
2821 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
2823 IDirect3DVertexShader9_Release(shader);
2825 /* Z < 1.0 */
2826 color = getPixelColor(device, 28, 238);
2827 ok(color_match(color, 0x00ffffff, 0), "Z range failed: Got color 0x%08x, expected 0x00ffffff.\n", color);
2829 /* 1.0 < z < 0.75 */
2830 color = getPixelColor(device, 31, 238);
2831 ok(color_match(color, 0x00ff0000, 0), "Z range failed: Got color 0x%08x, expected 0x00ff0000.\n", color);
2832 color = getPixelColor(device, 100, 238);
2833 ok(color_match(color, 0x00ff0000, 0) || broken(color_match(color, 0x00ffffff, 0)),
2834 "Z range failed: Got color 0x%08x, expected 0x00ff0000.\n", color);
2836 /* 0.75 < z < 0.0 */
2837 color = getPixelColor(device, 104, 238);
2838 ok(color_match(color, 0x000000ff, 0), "Z range failed: Got color 0x%08x, expected 0x000000ff.\n", color);
2839 color = getPixelColor(device, 318, 238);
2840 ok(color_match(color, 0x000000ff, 0), "Z range failed: Got color 0x%08x, expected 0x000000ff.\n", color);
2842 /* 0.0 < z */
2843 color = getPixelColor(device, 321, 238);
2844 ok(color_match(color, 0x00ffffff, 0), "Z range failed: Got color 0x%08x, expected 0x00ffffff.\n", color);
2846 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
2847 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
2849 refcount = IDirect3DDevice9_Release(device);
2850 ok(!refcount, "Device has %u references left.\n", refcount);
2851 done:
2852 IDirect3D9_Release(d3d);
2853 DestroyWindow(window);
2856 static void fill_surface(IDirect3DSurface9 *surface, DWORD color, DWORD flags)
2858 D3DSURFACE_DESC desc;
2859 D3DLOCKED_RECT l;
2860 HRESULT hr;
2861 unsigned int x, y;
2862 DWORD *mem;
2864 memset(&desc, 0, sizeof(desc));
2865 memset(&l, 0, sizeof(l));
2866 hr = IDirect3DSurface9_GetDesc(surface, &desc);
2867 ok(hr == D3D_OK, "IDirect3DSurface9_GetDesc failed with %08x\n", hr);
2868 hr = IDirect3DSurface9_LockRect(surface, &l, NULL, flags);
2869 ok(hr == D3D_OK, "IDirect3DSurface9_LockRect failed with %08x\n", hr);
2870 if(FAILED(hr)) return;
2872 for(y = 0; y < desc.Height; y++)
2874 mem = (DWORD *) ((BYTE *) l.pBits + y * l.Pitch);
2875 for(x = 0; x < l.Pitch / sizeof(DWORD); x++)
2877 mem[x] = color;
2880 hr = IDirect3DSurface9_UnlockRect(surface);
2881 ok(hr == D3D_OK, "IDirect3DSurface9_UnlockRect failed with %08x\n", hr);
2884 static void stretchrect_test(void)
2886 IDirect3DSurface9 *surf_tex_rt32, *surf_tex_rt64, *surf_tex_rt_dest64, *surf_tex_rt_dest640_480;
2887 IDirect3DSurface9 *surf_offscreen32, *surf_offscreen64, *surf_offscreen_dest64;
2888 IDirect3DTexture9 *tex_rt32, *tex_rt64, *tex_rt_dest64, *tex_rt_dest640_480;
2889 IDirect3DSurface9 *surf_tex32, *surf_tex64, *surf_tex_dest64;
2890 IDirect3DSurface9 *surf_rt32, *surf_rt64, *surf_rt_dest64;
2891 IDirect3DTexture9 *tex32, *tex64, *tex_dest64;
2892 IDirect3DSurface9 *surf_temp32, *surf_temp64;
2893 IDirect3DSurface9 *backbuffer;
2894 IDirect3DDevice9 *device;
2895 IDirect3D9 *d3d;
2896 D3DCOLOR color;
2897 ULONG refcount;
2898 HWND window;
2899 HRESULT hr;
2901 static const RECT src_rect = {0, 0, 640, 480};
2902 static const RECT src_rect_flipy = {0, 480, 640, 0};
2903 static const RECT dst_rect = {0, 0, 640, 480};
2904 static const RECT dst_rect_flipy = {0, 480, 640, 0};
2905 static const RECT src_rect64 = {0, 0, 64, 64};
2906 static const RECT src_rect64_flipy = {0, 64, 64, 0};
2907 static const RECT dst_rect64 = {0, 0, 64, 64};
2908 static const RECT dst_rect64_flipy = {0, 64, 64, 0};
2910 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
2911 0, 0, 640, 480, NULL, NULL, NULL, NULL);
2912 d3d = Direct3DCreate9(D3D_SDK_VERSION);
2913 ok(!!d3d, "Failed to create a D3D object.\n");
2914 if (!(device = create_device(d3d, window, window, TRUE)))
2916 skip("Failed to create a D3D device, skipping tests.\n");
2917 goto done;
2920 /* Create our temporary surfaces in system memory. */
2921 hr = IDirect3DDevice9_CreateOffscreenPlainSurface(device, 32, 32,
2922 D3DFMT_A8R8G8B8, D3DPOOL_SYSTEMMEM, &surf_temp32, NULL);
2923 ok(SUCCEEDED(hr), "Failed to create surface, hr %#x.\n", hr);
2924 hr = IDirect3DDevice9_CreateOffscreenPlainSurface(device, 64, 64,
2925 D3DFMT_A8R8G8B8, D3DPOOL_SYSTEMMEM, &surf_temp64, NULL);
2926 ok(SUCCEEDED(hr), "Failed to create surface, hr %#x.\n", hr);
2928 /* Create offscreen plain surfaces in D3DPOOL_DEFAULT. */
2929 hr = IDirect3DDevice9_CreateOffscreenPlainSurface(device, 32, 32,
2930 D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &surf_offscreen32, NULL);
2931 ok(SUCCEEDED(hr), "Failed to create surface, hr %#x.\n", hr);
2932 hr = IDirect3DDevice9_CreateOffscreenPlainSurface(device, 64, 64,
2933 D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &surf_offscreen64, NULL);
2934 ok(SUCCEEDED(hr), "Failed to create surface, hr %#x.\n", hr);
2935 hr = IDirect3DDevice9_CreateOffscreenPlainSurface(device, 64, 64,
2936 D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &surf_offscreen_dest64, NULL);
2937 ok(SUCCEEDED(hr), "Failed to create surface, hr %#x.\n", hr);
2939 /* Create render target surfaces. */
2940 hr = IDirect3DDevice9_CreateRenderTarget(device, 32, 32,
2941 D3DFMT_A8R8G8B8, D3DMULTISAMPLE_NONE, 0, TRUE, &surf_rt32, NULL );
2942 ok(SUCCEEDED(hr), "Failed to create render target, hr %#x.\n", hr);
2943 hr = IDirect3DDevice9_CreateRenderTarget(device, 64, 64,
2944 D3DFMT_A8R8G8B8, D3DMULTISAMPLE_NONE, 0, TRUE, &surf_rt64, NULL );
2945 ok(SUCCEEDED(hr), "Failed to create render target, hr %#x.\n", hr);
2946 hr = IDirect3DDevice9_CreateRenderTarget(device, 64, 64,
2947 D3DFMT_A8R8G8B8, D3DMULTISAMPLE_NONE, 0, TRUE, &surf_rt_dest64, NULL );
2948 ok(SUCCEEDED(hr), "Failed to create render target, hr %#x.\n", hr);
2949 hr = IDirect3DDevice9_GetBackBuffer(device, 0, 0, D3DBACKBUFFER_TYPE_MONO, &backbuffer);
2950 ok(SUCCEEDED(hr), "Failed to get back buffer, hr %#x.\n", hr);
2952 /* Create render target textures. */
2953 hr = IDirect3DDevice9_CreateTexture(device, 32, 32, 1, D3DUSAGE_RENDERTARGET,
2954 D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &tex_rt32, NULL);
2955 ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);
2956 hr = IDirect3DDevice9_CreateTexture(device, 64, 64, 1, D3DUSAGE_RENDERTARGET,
2957 D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &tex_rt64, NULL);
2958 ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);
2959 hr = IDirect3DDevice9_CreateTexture(device, 64, 64, 1, D3DUSAGE_RENDERTARGET,
2960 D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &tex_rt_dest64, NULL);
2961 ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);
2962 hr = IDirect3DDevice9_CreateTexture(device, 640, 480, 1, D3DUSAGE_RENDERTARGET,
2963 D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &tex_rt_dest640_480, NULL);
2964 ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);
2965 hr = IDirect3DTexture9_GetSurfaceLevel(tex_rt32, 0, &surf_tex_rt32);
2966 ok(SUCCEEDED(hr), "Failed to get surface level, hr %#x.\n", hr);
2967 hr = IDirect3DTexture9_GetSurfaceLevel(tex_rt64, 0, &surf_tex_rt64);
2968 ok(SUCCEEDED(hr), "Failed to get surface level, hr %#x.\n", hr);
2969 hr = IDirect3DTexture9_GetSurfaceLevel(tex_rt_dest64, 0, &surf_tex_rt_dest64);
2970 ok(SUCCEEDED(hr), "Failed to get surface level, hr %#x.\n", hr);
2971 hr = IDirect3DTexture9_GetSurfaceLevel(tex_rt_dest640_480, 0, &surf_tex_rt_dest640_480);
2972 ok(SUCCEEDED(hr), "Failed to get surface level, hr %#x.\n", hr);
2974 /* Create regular textures in D3DPOOL_DEFAULT. */
2975 hr = IDirect3DDevice9_CreateTexture(device, 32, 32, 1, 0, D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &tex32, NULL);
2976 ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);
2977 hr = IDirect3DDevice9_CreateTexture(device, 64, 64, 1, 0, D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &tex64, NULL);
2978 ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);
2979 hr = IDirect3DDevice9_CreateTexture(device, 64, 64, 1, 0, D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &tex_dest64, NULL);
2980 ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);
2981 hr = IDirect3DTexture9_GetSurfaceLevel(tex32, 0, &surf_tex32);
2982 ok(SUCCEEDED(hr), "Failed to get surface level, hr %#x.\n", hr);
2983 hr = IDirect3DTexture9_GetSurfaceLevel(tex64, 0, &surf_tex64);
2984 ok(SUCCEEDED(hr), "Failed to get surface level, hr %#x.\n", hr);
2985 hr = IDirect3DTexture9_GetSurfaceLevel(tex_dest64, 0, &surf_tex_dest64);
2986 ok(SUCCEEDED(hr), "Failed to get surface level, hr %#x.\n", hr);
2988 /**********************************************************************
2989 * Tests for when the source parameter is an offscreen plain surface. *
2990 **********************************************************************/
2992 /* Fill the offscreen 64x64 surface with green. */
2993 fill_surface(surf_offscreen64, 0xff00ff00, 0);
2995 /* offscreenplain ==> offscreenplain, same size. */
2996 hr = IDirect3DDevice9_StretchRect(device, surf_offscreen64, NULL, surf_offscreen_dest64, NULL, D3DTEXF_NONE);
2997 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
2998 color = getPixelColorFromSurface(surf_offscreen_dest64, 32, 32);
2999 ok(color == 0xff00ff00, "Got unexpected color 0x%08x.\n", color);
3000 /* Blit without scaling. */
3001 hr = IDirect3DDevice9_StretchRect(device, surf_offscreen64, &src_rect64,
3002 surf_offscreen_dest64, &dst_rect64, D3DTEXF_NONE);
3003 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3004 /* Flipping in y-direction through src_rect, no scaling (not allowed). */
3005 hr = IDirect3DDevice9_StretchRect(device, surf_offscreen64, &src_rect64_flipy,
3006 surf_offscreen_dest64, &dst_rect64, D3DTEXF_NONE);
3007 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3008 /* Flipping in y-direction through dst_rect, no scaling (not allowed). */
3009 hr = IDirect3DDevice9_StretchRect(device, surf_offscreen64, &src_rect64,
3010 surf_offscreen_dest64, &dst_rect64_flipy, D3DTEXF_NONE);
3011 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3013 /* offscreenplain ==> rendertarget texture, same size. */
3014 hr = IDirect3DDevice9_StretchRect(device, surf_offscreen64, NULL, surf_tex_rt_dest64, NULL, D3DTEXF_NONE);
3015 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3016 /* We can't lock rendertarget textures, so copy to our temp surface first. */
3017 hr = IDirect3DDevice9_GetRenderTargetData(device, surf_tex_rt_dest64, surf_temp64);
3018 ok(SUCCEEDED(hr), "Failed to get render target data, hr %#x.\n", hr);
3019 color = getPixelColorFromSurface(surf_temp64, 32, 32);
3020 ok(color == 0xff00ff00, "Got unexpected color 0x%08x.\n", color);
3021 /* Blit without scaling. */
3022 hr = IDirect3DDevice9_StretchRect(device, surf_offscreen64, &src_rect64,
3023 surf_tex_rt_dest64, &dst_rect64, D3DTEXF_NONE);
3024 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3025 /* Flipping in y-direction through src_rect, no scaling (not allowed). */
3026 hr = IDirect3DDevice9_StretchRect(device, surf_offscreen64, &src_rect64_flipy,
3027 surf_tex_rt_dest64, &dst_rect64, D3DTEXF_NONE);
3028 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3029 /* Flipping in y-direction through dst_rect, no scaling (not allowed). */
3030 hr = IDirect3DDevice9_StretchRect(device, surf_offscreen64, &src_rect64,
3031 surf_tex_rt_dest64, &dst_rect64_flipy, D3DTEXF_NONE);
3032 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3034 /* offscreenplain ==> rendertarget surface, same size. */
3035 hr = IDirect3DDevice9_StretchRect(device, surf_offscreen64, NULL, surf_rt_dest64, NULL, D3DTEXF_NONE);
3036 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3037 color = getPixelColorFromSurface(surf_rt_dest64, 32, 32);
3038 ok(color == 0xff00ff00, "Got unexpected color 0x%08x.\n", color);
3039 /* Blit without scaling. */
3040 hr = IDirect3DDevice9_StretchRect(device, surf_offscreen64, &src_rect64,
3041 surf_rt_dest64, &dst_rect64, D3DTEXF_NONE);
3042 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3043 /* Flipping in y-direction through src_rect, no scaling (not allowed). */
3044 hr = IDirect3DDevice9_StretchRect(device, surf_offscreen64, &src_rect64_flipy,
3045 surf_rt_dest64, &dst_rect64, D3DTEXF_NONE);
3046 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3047 /* Flipping in y-direction through dst_rect, no scaling (not allowed). */
3048 hr = IDirect3DDevice9_StretchRect(device, surf_offscreen64, &src_rect64,
3049 surf_rt_dest64, &dst_rect64_flipy, D3DTEXF_NONE);
3050 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3052 /* offscreenplain ==> texture, same size (should fail). */
3053 hr = IDirect3DDevice9_StretchRect(device, surf_offscreen64, NULL, surf_tex_dest64, NULL, D3DTEXF_NONE);
3054 todo_wine ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3056 /* Fill the smaller offscreen surface with red. */
3057 fill_surface(surf_offscreen32, 0xffff0000, 0);
3059 /* offscreenplain ==> offscreenplain, scaling (should fail). */
3060 hr = IDirect3DDevice9_StretchRect(device, surf_offscreen32, NULL, surf_offscreen64, NULL, D3DTEXF_NONE);
3061 todo_wine ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3063 /* offscreenplain ==> rendertarget texture, scaling. */
3064 hr = IDirect3DDevice9_StretchRect(device, surf_offscreen32, NULL, surf_tex_rt_dest64, NULL, D3DTEXF_NONE);
3065 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3066 /* We can't lock rendertarget textures, so copy to our temp surface first. */
3067 hr = IDirect3DDevice9_GetRenderTargetData(device, surf_tex_rt_dest64, surf_temp64);
3068 ok(SUCCEEDED(hr), "Failed to get render target data, hr %#x.\n", hr);
3069 color = getPixelColorFromSurface(surf_temp64, 48, 48);
3070 ok(color == 0xffff0000, "Got unexpected color 0x%08x.\n", color);
3072 /* offscreenplain ==> rendertarget surface, scaling. */
3073 hr = IDirect3DDevice9_StretchRect(device, surf_offscreen32, NULL, surf_rt_dest64, NULL, D3DTEXF_NONE);
3074 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3075 color = getPixelColorFromSurface(surf_rt_dest64, 48, 48);
3076 ok(color == 0xffff0000, "Got unexpected color 0x%08x.\n", color);
3078 /* offscreenplain ==> texture, scaling (should fail). */
3079 hr = IDirect3DDevice9_StretchRect(device, surf_offscreen32, NULL, surf_tex_dest64, NULL, D3DTEXF_NONE);
3080 todo_wine ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3082 /*************************************************************
3083 * Tests for when the source parameter is a regular texture. *
3084 *************************************************************/
3086 /* Fill the surface of the regular texture with blue. */
3087 /* Can't fill the surf_tex directly because it's created in D3DPOOL_DEFAULT. */
3088 fill_surface(surf_temp64, 0xff0000ff, 0);
3089 hr = IDirect3DDevice9_UpdateSurface(device, surf_temp64, NULL, surf_tex64, NULL);
3090 ok(SUCCEEDED(hr), "Failed to update surface, hr %#x.\n", hr);
3092 /* texture ==> offscreenplain, same size. */
3093 hr = IDirect3DDevice9_StretchRect(device, surf_tex64, NULL, surf_offscreen64, NULL, D3DTEXF_NONE);
3094 todo_wine ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3096 /* texture ==> rendertarget texture, same size. */
3097 hr = IDirect3DDevice9_StretchRect(device, surf_tex64, NULL, surf_tex_rt_dest64, NULL, D3DTEXF_NONE);
3098 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3099 /* We can't lock rendertarget textures, so copy to our temp surface first. */
3100 hr = IDirect3DDevice9_GetRenderTargetData(device, surf_tex_rt_dest64, surf_temp64);
3101 ok(SUCCEEDED(hr), "Failed to get render target data, hr %#x.\n", hr);
3102 color = getPixelColorFromSurface(surf_temp64, 32, 32);
3103 ok(color == 0xff0000ff, "Got unexpected color 0x%08x.\n", color);
3104 /* Blit without scaling. */
3105 hr = IDirect3DDevice9_StretchRect(device, surf_tex64, &src_rect64,
3106 surf_tex_rt_dest64, &dst_rect64, D3DTEXF_NONE);
3107 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3108 /* Flipping in y-direction through src_rect, no scaling (not allowed). */
3109 hr = IDirect3DDevice9_StretchRect(device, surf_tex64, &src_rect64_flipy,
3110 surf_tex_rt_dest64, &dst_rect64, D3DTEXF_NONE);
3111 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3112 /* Flipping in y-direction through dst_rect, no scaling (not allowed). */
3113 hr = IDirect3DDevice9_StretchRect(device, surf_tex64, &src_rect64,
3114 surf_tex_rt_dest64, &dst_rect64_flipy, D3DTEXF_NONE);
3115 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3117 /* texture ==> rendertarget surface, same size. */
3118 hr = IDirect3DDevice9_StretchRect(device, surf_tex64, NULL, surf_rt_dest64, NULL, D3DTEXF_NONE);
3119 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3120 color = getPixelColorFromSurface(surf_rt_dest64, 32, 32);
3121 ok(color == 0xff0000ff, "Got unexpected color 0x%08x.\n", color);
3122 /* Blit without scaling. */
3123 hr = IDirect3DDevice9_StretchRect(device, surf_tex64, &src_rect64,
3124 surf_rt_dest64, &dst_rect64, D3DTEXF_NONE);
3125 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3126 /* Flipping in y-direction through src_rect, no scaling (not allowed). */
3127 hr = IDirect3DDevice9_StretchRect(device, surf_tex64, &src_rect64_flipy,
3128 surf_rt_dest64, &dst_rect64, D3DTEXF_NONE);
3129 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3130 /* Flipping in y-direction through dst_rect, no scaling (not allowed). */
3131 hr = IDirect3DDevice9_StretchRect(device, surf_tex64, &src_rect64,
3132 surf_rt_dest64, &dst_rect64_flipy, D3DTEXF_NONE);
3133 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3135 /* texture ==> texture, same size (should fail). */
3136 hr = IDirect3DDevice9_StretchRect(device, surf_tex64, NULL, surf_tex_dest64, NULL, D3DTEXF_NONE);
3137 todo_wine ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3139 /* Fill the surface of the smaller regular texture with red. */
3140 /* Can't fill the surf_tex directly because it's created in D3DPOOL_DEFAULT. */
3141 fill_surface(surf_temp32, 0xffff0000, 0);
3142 hr = IDirect3DDevice9_UpdateSurface(device, surf_temp32, NULL, surf_tex32, NULL);
3143 ok(SUCCEEDED(hr), "Failed to update surface, hr %#x.\n", hr);
3145 /* texture ==> offscreenplain, scaling (should fail). */
3146 hr = IDirect3DDevice9_StretchRect(device, surf_tex32, NULL, surf_offscreen64, NULL, D3DTEXF_NONE);
3147 todo_wine ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3149 /* texture ==> rendertarget texture, scaling. */
3150 hr = IDirect3DDevice9_StretchRect(device, surf_tex32, NULL, surf_tex_rt_dest64, NULL, D3DTEXF_NONE);
3151 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3152 /* We can't lock rendertarget textures, so copy to our temp surface first. */
3153 hr = IDirect3DDevice9_GetRenderTargetData(device, surf_tex_rt_dest64, surf_temp64);
3154 ok(SUCCEEDED(hr), "Failed to get render target data, hr %#x.\n", hr);
3155 color = getPixelColorFromSurface(surf_temp64, 48, 48);
3156 ok(color == 0xffff0000, "Got unexpected color 0x%08x.\n", color);
3158 /* texture ==> rendertarget surface, scaling. */
3159 hr = IDirect3DDevice9_StretchRect(device, surf_tex32, NULL, surf_rt_dest64, NULL, D3DTEXF_NONE);
3160 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3161 color = getPixelColorFromSurface(surf_rt_dest64, 48, 48);
3162 ok(color == 0xffff0000, "Got unexpected color 0x%08x.\n", color);
3164 /* texture ==> texture, scaling (should fail). */
3165 hr = IDirect3DDevice9_StretchRect(device, surf_tex32, NULL, surf_tex_dest64, NULL, D3DTEXF_NONE);
3166 todo_wine ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3168 /******************************************************************
3169 * Tests for when the source parameter is a rendertarget texture. *
3170 ******************************************************************/
3172 /* Fill the surface of the rendertarget texture with white. */
3173 /* Can't fill the surf_tex_rt directly because it's created in D3DPOOL_DEFAULT. */
3174 fill_surface(surf_temp64, 0xffffffff, 0);
3175 hr = IDirect3DDevice9_UpdateSurface(device, surf_temp64, NULL, surf_tex_rt64, NULL);
3176 ok(SUCCEEDED(hr), "Failed to update surface, hr %#x.\n", hr);
3178 /* rendertarget texture ==> offscreenplain, same size. */
3179 hr = IDirect3DDevice9_StretchRect(device, surf_tex_rt64, NULL, surf_offscreen64, NULL, D3DTEXF_NONE);
3180 todo_wine ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3182 /* rendertarget texture ==> rendertarget texture, same size. */
3183 hr = IDirect3DDevice9_StretchRect(device, surf_tex_rt64, NULL, surf_tex_rt_dest64, NULL, D3DTEXF_NONE);
3184 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3185 /* We can't lock rendertarget textures, so copy to our temp surface first. */
3186 hr = IDirect3DDevice9_GetRenderTargetData(device, surf_tex_rt_dest64, surf_temp64);
3187 ok(SUCCEEDED(hr), "Failed to get render target data, hr %#x.\n", hr);
3188 color = getPixelColorFromSurface(surf_temp64, 32, 32);
3189 ok(color == 0xffffffff, "Got unexpected color 0x%08x.\n", color);
3190 /* Blit without scaling. */
3191 hr = IDirect3DDevice9_StretchRect(device, surf_tex_rt64, &src_rect64,
3192 surf_tex_rt_dest64, &dst_rect64, D3DTEXF_NONE);
3193 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3194 /* Flipping in y-direction through src_rect, no scaling (not allowed). */
3195 hr = IDirect3DDevice9_StretchRect(device, surf_tex_rt64, &src_rect64_flipy,
3196 surf_tex_rt_dest64, &dst_rect64, D3DTEXF_NONE);
3197 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3198 /* Flipping in y-direction through dst_rect, no scaling (not allowed). */
3199 hr = IDirect3DDevice9_StretchRect(device, surf_tex_rt64, &src_rect64,
3200 surf_tex_rt_dest64, &dst_rect64_flipy, D3DTEXF_NONE);
3201 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3203 /* rendertarget texture ==> rendertarget surface, same size. */
3204 hr = IDirect3DDevice9_StretchRect(device, surf_tex_rt64, NULL, surf_rt_dest64, NULL, D3DTEXF_NONE);
3205 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3206 color = getPixelColorFromSurface(surf_rt_dest64, 32, 32);
3207 ok(color == 0xffffffff, "Got unexpected color 0x%08x.\n", color);
3208 /* Blit without scaling. */
3209 hr = IDirect3DDevice9_StretchRect(device, surf_tex_rt64, &src_rect64,
3210 surf_rt_dest64, &dst_rect64, D3DTEXF_NONE);
3211 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3212 /* Flipping in y-direction through src_rect, no scaling (not allowed). */
3213 hr = IDirect3DDevice9_StretchRect(device, surf_tex_rt64, &src_rect64_flipy,
3214 surf_rt_dest64, &dst_rect64, D3DTEXF_NONE);
3215 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3216 /* Flipping in y-direction through dst_rect, no scaling (not allowed). */
3217 hr = IDirect3DDevice9_StretchRect(device, surf_tex_rt64, &src_rect64,
3218 surf_rt_dest64, &dst_rect64_flipy, D3DTEXF_NONE);
3219 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3221 /* rendertarget texture ==> texture, same size (should fail). */
3222 hr = IDirect3DDevice9_StretchRect(device, surf_tex_rt64, NULL, surf_tex_dest64, NULL, D3DTEXF_NONE);
3223 todo_wine ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3225 /* Fill the surface of the smaller rendertarget texture with red. */
3226 /* Can't fill the surf_tex_rt directly because it's created in D3DPOOL_DEFAULT. */
3227 fill_surface(surf_temp32, 0xffff0000, 0);
3228 hr = IDirect3DDevice9_UpdateSurface(device, surf_temp32, NULL, surf_tex_rt32, NULL);
3229 ok(SUCCEEDED(hr), "Failed to update surface, hr %#x.\n", hr);
3231 /* rendertarget texture ==> offscreenplain, scaling (should fail). */
3232 hr = IDirect3DDevice9_StretchRect(device, surf_tex_rt32, NULL, surf_offscreen64, NULL, D3DTEXF_NONE);
3233 todo_wine ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3235 /* rendertarget texture ==> rendertarget texture, scaling. */
3236 hr = IDirect3DDevice9_StretchRect(device, surf_tex_rt32, NULL, surf_tex_rt_dest64, NULL, D3DTEXF_NONE);
3237 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3238 /* We can't lock rendertarget textures, so copy to our temp surface first. */
3239 hr = IDirect3DDevice9_GetRenderTargetData(device, surf_tex_rt_dest64, surf_temp64);
3240 ok(SUCCEEDED(hr), "Failed to get render target data, hr %#x.\n", hr);
3241 color = getPixelColorFromSurface(surf_temp64, 48, 48);
3242 ok(color == 0xffff0000, "Got unexpected color 0x%08x.\n", color);
3244 /* rendertarget texture ==> rendertarget surface, scaling. */
3245 hr = IDirect3DDevice9_StretchRect(device, surf_tex_rt32, NULL, surf_rt_dest64, NULL, D3DTEXF_NONE);
3246 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3247 color = getPixelColorFromSurface(surf_rt_dest64, 48, 48);
3248 ok(color == 0xffff0000, "Got unexpected color 0x%08x.\n", color);
3250 /* rendertarget texture ==> texture, scaling (should fail). */
3251 hr = IDirect3DDevice9_StretchRect(device, surf_tex_rt32, NULL, surf_tex_dest64, NULL, D3DTEXF_NONE);
3252 todo_wine ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3254 /******************************************************************
3255 * Tests for when the source parameter is a rendertarget surface. *
3256 ******************************************************************/
3258 /* Fill the surface of the rendertarget surface with black. */
3259 fill_surface(surf_rt64, 0xff000000, 0);
3261 /* rendertarget texture ==> offscreenplain, same size. */
3262 hr = IDirect3DDevice9_StretchRect(device, surf_rt64, NULL, surf_offscreen64, NULL, D3DTEXF_NONE);
3263 todo_wine ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3265 /* rendertarget surface ==> rendertarget texture, same size. */
3266 hr = IDirect3DDevice9_StretchRect(device, surf_rt64, NULL, surf_tex_rt_dest64, NULL, D3DTEXF_NONE);
3267 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3268 /* We can't lock rendertarget textures, so copy to our temp surface first. */
3269 hr = IDirect3DDevice9_GetRenderTargetData(device, surf_tex_rt_dest64, surf_temp64);
3270 ok(SUCCEEDED(hr), "Failed to get render target data, hr %#x.\n", hr);
3271 color = getPixelColorFromSurface(surf_temp64, 32, 32);
3272 ok(color == 0xff000000, "Got unexpected color 0x%08x.\n", color);
3273 /* Blit without scaling. */
3274 hr = IDirect3DDevice9_StretchRect(device, surf_rt64, &src_rect64,
3275 surf_tex_rt_dest64, &dst_rect64, D3DTEXF_NONE);
3276 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3277 /* Flipping in y-direction through src_rect, no scaling (not allowed). */
3278 hr = IDirect3DDevice9_StretchRect(device, surf_rt64, &src_rect64_flipy,
3279 surf_tex_rt_dest64, &dst_rect64, D3DTEXF_NONE);
3280 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3281 /* Flipping in y-direction through dst_rect, no scaling (not allowed). */
3282 hr = IDirect3DDevice9_StretchRect(device, surf_rt64, &src_rect64,
3283 surf_tex_rt_dest64, &dst_rect64_flipy, D3DTEXF_NONE);
3284 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3286 /* rendertarget surface ==> rendertarget surface, same size. */
3287 hr = IDirect3DDevice9_StretchRect(device, surf_rt64, NULL, surf_rt_dest64, NULL, D3DTEXF_NONE);
3288 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3289 color = getPixelColorFromSurface(surf_rt_dest64, 32, 32);
3290 ok(color == 0xff000000, "Got unexpected color 0x%08x.\n", color);
3291 /* Blit without scaling. */
3292 hr = IDirect3DDevice9_StretchRect(device, surf_rt64, &src_rect64,
3293 surf_rt_dest64, &dst_rect64, D3DTEXF_NONE);
3294 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3295 /* Flipping in y-direction through src_rect, no scaling (not allowed). */
3296 hr = IDirect3DDevice9_StretchRect(device, surf_rt64, &src_rect64_flipy,
3297 surf_rt_dest64, &dst_rect64_flipy, D3DTEXF_NONE);
3298 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3299 /* Flipping in y-direction through dst_rect, no scaling (not allowed). */
3300 hr = IDirect3DDevice9_StretchRect(device, surf_rt64, &src_rect64,
3301 surf_rt_dest64, &dst_rect64_flipy, D3DTEXF_NONE);
3302 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3304 /* rendertarget surface ==> texture, same size (should fail). */
3305 hr = IDirect3DDevice9_StretchRect(device, surf_rt64, NULL, surf_tex_dest64, NULL, D3DTEXF_NONE);
3306 todo_wine ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3308 /* Fill the surface of the smaller rendertarget texture with red. */
3309 fill_surface(surf_rt32, 0xffff0000, 0);
3311 /* rendertarget surface ==> offscreenplain, scaling (should fail). */
3312 hr = IDirect3DDevice9_StretchRect(device, surf_rt32, NULL, surf_offscreen64, NULL, D3DTEXF_NONE);
3313 todo_wine ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3315 /* rendertarget surface ==> rendertarget texture, scaling. */
3316 hr = IDirect3DDevice9_StretchRect(device, surf_rt32, NULL, surf_tex_rt_dest64, NULL, D3DTEXF_NONE);
3317 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3318 /* We can't lock rendertarget textures, so copy to our temp surface first. */
3319 hr = IDirect3DDevice9_GetRenderTargetData(device, surf_tex_rt_dest64, surf_temp64);
3320 ok(SUCCEEDED(hr), "Failed to get render target data, hr %#x.\n", hr);
3321 color = getPixelColorFromSurface(surf_temp64, 48, 48);
3322 ok(color == 0xffff0000, "Got unexpected color 0x%08x.\n", color);
3324 /* rendertarget surface ==> rendertarget surface, scaling. */
3325 hr = IDirect3DDevice9_StretchRect(device, surf_rt32, NULL, surf_rt_dest64, NULL, D3DTEXF_NONE);
3326 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3327 color = getPixelColorFromSurface(surf_rt_dest64, 48, 48);
3328 ok(color == 0xffff0000, "Got unexpected color 0x%08x.\n", color);
3330 /* rendertarget surface ==> texture, scaling (should fail). */
3331 hr = IDirect3DDevice9_StretchRect(device, surf_rt32, NULL, surf_tex_dest64, NULL, D3DTEXF_NONE);
3332 todo_wine ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3334 /* backbuffer ==> surface tests (no scaling). */
3335 /* Blit with NULL rectangles. */
3336 hr = IDirect3DDevice9_StretchRect(device, backbuffer, NULL, surf_tex_rt_dest640_480, NULL, D3DTEXF_NONE);
3337 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3338 /* Blit without scaling. */
3339 hr = IDirect3DDevice9_StretchRect(device, backbuffer, &src_rect,
3340 surf_tex_rt_dest640_480, &dst_rect, D3DTEXF_NONE);
3341 ok(hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
3342 /* Flipping in y-direction through src_rect, no scaling (not allowed). */
3343 hr = IDirect3DDevice9_StretchRect(device, backbuffer, &src_rect_flipy,
3344 surf_tex_rt_dest640_480, &dst_rect, D3DTEXF_NONE);
3345 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3346 /* Flipping in y-direction through dst_rect, no scaling (not allowed). */
3347 hr = IDirect3DDevice9_StretchRect(device, backbuffer, &src_rect,
3348 surf_tex_rt_dest640_480, &dst_rect_flipy, D3DTEXF_NONE);
3349 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
3351 /* TODO: Test format conversions. */
3353 IDirect3DSurface9_Release(backbuffer);
3354 IDirect3DSurface9_Release(surf_rt32);
3355 IDirect3DSurface9_Release(surf_rt64);
3356 IDirect3DSurface9_Release(surf_rt_dest64);
3357 IDirect3DSurface9_Release(surf_temp32);
3358 IDirect3DSurface9_Release(surf_temp64);
3359 IDirect3DSurface9_Release(surf_offscreen32);
3360 IDirect3DSurface9_Release(surf_offscreen64);
3361 IDirect3DSurface9_Release(surf_offscreen_dest64);
3362 IDirect3DSurface9_Release(surf_tex_rt32);
3363 IDirect3DTexture9_Release(tex_rt32);
3364 IDirect3DSurface9_Release(surf_tex_rt64);
3365 IDirect3DTexture9_Release(tex_rt64);
3366 IDirect3DSurface9_Release(surf_tex_rt_dest64);
3367 IDirect3DTexture9_Release(tex_rt_dest64);
3368 IDirect3DSurface9_Release(surf_tex_rt_dest640_480);
3369 IDirect3DTexture9_Release(tex_rt_dest640_480);
3370 IDirect3DSurface9_Release(surf_tex32);
3371 IDirect3DTexture9_Release(tex32);
3372 IDirect3DSurface9_Release(surf_tex64);
3373 IDirect3DTexture9_Release(tex64);
3374 IDirect3DSurface9_Release(surf_tex_dest64);
3375 IDirect3DTexture9_Release(tex_dest64);
3376 refcount = IDirect3DDevice9_Release(device);
3377 ok(!refcount, "Device has %u references left.\n", refcount);
3378 done:
3379 IDirect3D9_Release(d3d);
3380 DestroyWindow(window);
3383 static void maxmip_test(void)
3385 IDirect3DTexture9 *texture;
3386 IDirect3DSurface9 *surface;
3387 IDirect3DDevice9 *device;
3388 IDirect3D9 *d3d;
3389 D3DCOLOR color;
3390 ULONG refcount;
3391 D3DCAPS9 caps;
3392 HWND window;
3393 HRESULT hr;
3394 DWORD ret;
3396 static const struct
3398 struct
3400 float x, y, z;
3401 float s, t;
3403 v[4];
3405 quads[] =
3408 {-1.0, -1.0, 0.0, 0.0, 0.0},
3409 {-1.0, 0.0, 0.0, 0.0, 1.0},
3410 { 0.0, -1.0, 0.0, 1.0, 0.0},
3411 { 0.0, 0.0, 0.0, 1.0, 1.0},
3414 { 0.0, -1.0, 0.0, 0.0, 0.0},
3415 { 0.0, 0.0, 0.0, 0.0, 1.0},
3416 { 1.0, -1.0, 0.0, 1.0, 0.0},
3417 { 1.0, 0.0, 0.0, 1.0, 1.0},
3420 { 0.0, 0.0, 0.0, 0.0, 0.0},
3421 { 0.0, 1.0, 0.0, 0.0, 1.0},
3422 { 1.0, 0.0, 0.0, 1.0, 0.0},
3423 { 1.0, 1.0, 0.0, 1.0, 1.0},
3426 {-1.0, 0.0, 0.0, 0.0, 0.0},
3427 {-1.0, 1.0, 0.0, 0.0, 1.0},
3428 { 0.0, 0.0, 0.0, 1.0, 0.0},
3429 { 0.0, 1.0, 0.0, 1.0, 1.0},
3433 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
3434 0, 0, 640, 480, NULL, NULL, NULL, NULL);
3435 d3d = Direct3DCreate9(D3D_SDK_VERSION);
3436 ok(!!d3d, "Failed to create a D3D object.\n");
3437 if (!(device = create_device(d3d, window, window, TRUE)))
3439 skip("Failed to create a D3D device, skipping tests.\n");
3440 goto done;
3443 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
3444 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
3445 if (!(caps.TextureCaps & D3DPTEXTURECAPS_MIPMAP))
3447 skip("No mipmap support, skipping tests.\n");
3448 IDirect3DDevice9_Release(device);
3449 goto done;
3452 hr = IDirect3DDevice9_CreateTexture(device, 128, 128, 3, 0,
3453 D3DFMT_A8R8G8B8, D3DPOOL_MANAGED, &texture, NULL);
3454 ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);
3456 hr = IDirect3DTexture9_GetSurfaceLevel(texture, 0, &surface);
3457 ok(SUCCEEDED(hr), "IDirect3DTexture9_GetSurfaceLevel returned %#x.\n", hr);
3458 fill_surface(surface, 0xffff0000, 0);
3459 IDirect3DSurface9_Release(surface);
3460 hr = IDirect3DTexture9_GetSurfaceLevel(texture, 1, &surface);
3461 ok(SUCCEEDED(hr), "IDirect3DTexture9_GetSurfaceLevel returned %#x.\n", hr);
3462 fill_surface(surface, 0xff00ff00, 0);
3463 IDirect3DSurface9_Release(surface);
3464 hr = IDirect3DTexture9_GetSurfaceLevel(texture, 2, &surface);
3465 ok(SUCCEEDED(hr), "IDirect3DTexture9_GetSurfaceLevel returned %#x.\n", hr);
3466 fill_surface(surface, 0xff0000ff, 0);
3467 IDirect3DSurface9_Release(surface);
3469 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *) texture);
3470 ok(hr == D3D_OK, "IDirect3DDevice9_SetTexture failed with %08x\n", hr);
3471 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1);
3472 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed with %08x\n", hr);
3474 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
3475 ok(SUCCEEDED(hr), "Failed to disable lighting, hr %#x.\n", hr);
3476 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MIPFILTER, D3DTEXF_NONE);
3477 ok(hr == D3D_OK, "IDirect3DDevice9_SetSamplerState failed with %08x\n", hr);
3479 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffffffff, 0.0, 0);
3480 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
3482 hr = IDirect3DDevice9_BeginScene(device);
3483 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
3485 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAXMIPLEVEL, 0);
3486 ok(SUCCEEDED(hr), "Failed to set sampler state, hr %#x.\n", hr);
3487 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quads[0], sizeof(*quads->v));
3488 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
3490 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAXMIPLEVEL, 1);
3491 ok(SUCCEEDED(hr), "Failed to set sampler state, hr %#x.\n", hr);
3492 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quads[1], sizeof(*quads->v));
3493 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
3495 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAXMIPLEVEL, 2);
3496 ok(SUCCEEDED(hr), "Failed to set sampler state, hr %#x.\n", hr);
3497 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quads[2], sizeof(*quads->v));
3498 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
3500 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAXMIPLEVEL, 3);
3501 ok(SUCCEEDED(hr), "Failed to set sampler state, hr %#x.\n", hr);
3502 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quads[3], sizeof(*quads->v));
3503 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
3505 hr = IDirect3DDevice9_EndScene(device);
3506 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
3508 /* With mipmapping disabled, the max mip level is ignored, only level 0 is used */
3509 color = getPixelColor(device, 160, 360);
3510 ok(color == 0x00ff0000, "MaxMip 0, no mipfilter has color 0x%08x.\n", color);
3511 color = getPixelColor(device, 480, 360);
3512 ok(color == 0x00ff0000, "MaxMip 1, no mipfilter has color 0x%08x.\n", color);
3513 color = getPixelColor(device, 480, 120);
3514 ok(color == 0x00ff0000, "MaxMip 2, no mipfilter has color 0x%08x.\n", color);
3515 color = getPixelColor(device, 160, 120);
3516 ok(color == 0x00ff0000, "MaxMip 3, no mipfilter has color 0x%08x.\n", color);
3517 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
3518 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
3520 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MIPFILTER, D3DTEXF_POINT);
3521 ok(hr == D3D_OK, "IDirect3DDevice9_SetSamplerState failed with %08x\n", hr);
3523 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffffffff, 0.0, 0);
3524 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
3526 hr = IDirect3DDevice9_BeginScene(device);
3527 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
3529 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAXMIPLEVEL, 0);
3530 ok(SUCCEEDED(hr), "Failed to set sampler state, hr %#x.\n", hr);
3531 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quads[0], sizeof(*quads->v));
3532 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
3534 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAXMIPLEVEL, 1);
3535 ok(SUCCEEDED(hr), "Failed to set sampler state, hr %#x.\n", hr);
3536 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quads[1], sizeof(*quads->v));
3537 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
3539 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAXMIPLEVEL, 2);
3540 ok(SUCCEEDED(hr), "Failed to set sampler state, hr %#x.\n", hr);
3541 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quads[2], sizeof(*quads->v));
3542 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
3544 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAXMIPLEVEL, 3);
3545 ok(SUCCEEDED(hr), "Failed to set sampler state, hr %#x.\n", hr);
3546 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quads[3], sizeof(*quads->v));
3547 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
3549 hr = IDirect3DDevice9_EndScene(device);
3550 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
3552 /* Max Mip level 0-2 sample from the specified texture level, Max Mip
3553 * level 3 (> levels in texture) samples from the highest level in the
3554 * texture (level 2). */
3555 color = getPixelColor(device, 160, 360);
3556 ok(color == 0x00ff0000, "MaxMip 0, point mipfilter has color 0x%08x.\n", color);
3557 color = getPixelColor(device, 480, 360);
3558 ok(color == 0x0000ff00, "MaxMip 1, point mipfilter has color 0x%08x.\n", color);
3559 color = getPixelColor(device, 480, 120);
3560 ok(color == 0x000000ff, "MaxMip 2, point mipfilter has color 0x%08x.\n", color);
3561 color = getPixelColor(device, 160, 120);
3562 ok(color == 0x000000ff, "MaxMip 3, point mipfilter has color 0x%08x.\n", color);
3563 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
3564 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
3566 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffffffff, 0.0, 0);
3567 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
3569 hr = IDirect3DDevice9_BeginScene(device);
3570 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
3572 /* Mipmapping OFF, LOD level smaller than MAXMIPLEVEL. LOD level limits */
3573 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MIPFILTER, D3DTEXF_NONE);
3574 ok(SUCCEEDED(hr), "Failed to set sampler state, hr %#x.\n", hr);
3575 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAXMIPLEVEL, 0);
3576 ok(SUCCEEDED(hr), "Failed to set sampler state, hr %#x.\n", hr);
3577 ret = IDirect3DTexture9_SetLOD(texture, 1);
3578 ok(ret == 0, "Got unexpected LOD %u.\n", ret);
3579 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quads[0], sizeof(*quads->v));
3580 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
3582 /* Mipmapping ON, LOD level smaller than max mip level. LOD level limits */
3583 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MIPFILTER, D3DTEXF_POINT);
3584 ok(SUCCEEDED(hr), "Failed to set sampler state, hr %#x.\n", hr);
3585 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAXMIPLEVEL, 1);
3586 ok(SUCCEEDED(hr), "Failed to set sampler state, hr %#x.\n", hr);
3587 ret = IDirect3DTexture9_SetLOD(texture, 2);
3588 ok(ret == 1, "Got unexpected LOD %u.\n", ret);
3589 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quads[1], sizeof(*quads->v));
3590 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
3592 /* Mipmapping ON, LOD level bigger than max mip level. MAXMIPLEVEL limits */
3593 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAXMIPLEVEL, 2);
3594 ok(SUCCEEDED(hr), "Failed to set sampler state, hr %#x.\n", hr);
3595 ret = IDirect3DTexture9_SetLOD(texture, 1);
3596 ok(ret == 2, "Got unexpected LOD %u.\n", ret);
3597 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quads[2], sizeof(*quads->v));
3598 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
3600 /* Mipmapping OFF, LOD level bigger than max mip level. LOD level limits */
3601 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MIPFILTER, D3DTEXF_NONE);
3602 ok(SUCCEEDED(hr), "Failed to set sampler state, hr %#x.\n", hr);
3603 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAXMIPLEVEL, 2);
3604 ok(SUCCEEDED(hr), "Failed to set sampler state, hr %#x.\n", hr);
3605 ret = IDirect3DTexture9_SetLOD(texture, 1);
3606 ok(ret == 1, "Got unexpected LOD %u.\n", ret);
3607 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quads[3], sizeof(*quads->v));
3608 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
3610 hr = IDirect3DDevice9_EndScene(device);
3611 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
3613 /* Max Mip level 0-2 sample from the specified texture level, Max Mip
3614 * level 3 (> levels in texture) samples from the highest level in the
3615 * texture (level 2). */
3616 color = getPixelColor(device, 160, 360);
3617 ok(color == 0x0000ff00, "MaxMip 0, LOD 1, none mipfilter has color 0x%08x.\n", color);
3618 color = getPixelColor(device, 480, 360);
3619 ok(color == 0x000000ff, "MaxMip 1, LOD 2, point mipfilter has color 0x%08x.\n", color);
3620 color = getPixelColor(device, 480, 120);
3621 ok(color == 0x000000ff, "MaxMip 2, LOD 1, point mipfilter has color 0x%08x.\n", color);
3622 color = getPixelColor(device, 160, 120);
3623 ok(color == 0x0000ff00, "MaxMip 2, LOD 1, none mipfilter has color 0x%08x.\n", color);
3625 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
3626 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
3628 IDirect3DTexture9_Release(texture);
3629 refcount = IDirect3DDevice9_Release(device);
3630 ok(!refcount, "Device has %u references left.\n", refcount);
3631 done:
3632 IDirect3D9_Release(d3d);
3633 DestroyWindow(window);
3636 static void release_buffer_test(void)
3638 IDirect3DVertexBuffer9 *vb;
3639 IDirect3DIndexBuffer9 *ib;
3640 IDirect3DDevice9 *device;
3641 IDirect3D9 *d3d;
3642 D3DCOLOR color;
3643 ULONG refcount;
3644 HWND window;
3645 HRESULT hr;
3646 BYTE *data;
3647 LONG ref;
3649 static const short indices[] = {3, 4, 5};
3650 static const struct
3652 struct vec3 position;
3653 DWORD diffuse;
3655 quad[] =
3657 {{-1.0f, -1.0f, 0.1f}, 0xffff0000},
3658 {{-1.0f, 1.0f, 0.1f}, 0xffff0000},
3659 {{ 1.0f, 1.0f, 0.1f}, 0xffff0000},
3661 {{-1.0f, -1.0f, 0.1f}, 0xff00ff00},
3662 {{-1.0f, 1.0f, 0.1f}, 0xff00ff00},
3663 {{ 1.0f, 1.0f, 0.1f}, 0xff00ff00},
3666 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
3667 0, 0, 640, 480, NULL, NULL, NULL, NULL);
3668 d3d = Direct3DCreate9(D3D_SDK_VERSION);
3669 ok(!!d3d, "Failed to create a D3D object.\n");
3670 if (!(device = create_device(d3d, window, window, TRUE)))
3672 skip("Failed to create a D3D device, skipping tests.\n");
3673 goto done;
3676 /* Index and vertex buffers should always be creatable */
3677 hr = IDirect3DDevice9_CreateVertexBuffer(device, sizeof(quad), 0,
3678 D3DFVF_XYZ | D3DFVF_DIFFUSE, D3DPOOL_MANAGED, &vb, NULL);
3679 ok(SUCCEEDED(hr), "Failed to create vertex buffer, hr %#x.\n", hr);
3680 hr = IDirect3DVertexBuffer9_Lock(vb, 0, sizeof(quad), (void **) &data, 0);
3681 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Lock failed with %08x\n", hr);
3682 memcpy(data, quad, sizeof(quad));
3683 hr = IDirect3DVertexBuffer9_Unlock(vb);
3684 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Unlock failed with %08x\n", hr);
3686 hr = IDirect3DDevice9_CreateIndexBuffer(device, sizeof(indices), 0,
3687 D3DFMT_INDEX16, D3DPOOL_DEFAULT, &ib, NULL);
3688 ok(SUCCEEDED(hr), "Failed to create index buffer, hr %#x.\n", hr);
3689 hr = IDirect3DIndexBuffer9_Lock(ib, 0, sizeof(indices), (void **) &data, 0);
3690 ok(hr == D3D_OK, "IDirect3DIndexBuffer9_Lock failed with %08x\n", hr);
3691 memcpy(data, indices, sizeof(indices));
3692 hr = IDirect3DIndexBuffer9_Unlock(ib);
3693 ok(hr == D3D_OK, "IDirect3DIndexBuffer9_Unlock failed with %08x\n", hr);
3695 hr = IDirect3DDevice9_SetIndices(device, ib);
3696 ok(hr == D3D_OK, "IDirect3DDevice9_SetIndices failed with %08x\n", hr);
3697 hr = IDirect3DDevice9_SetStreamSource(device, 0, vb, 0, sizeof(quad[0]));
3698 ok(hr == D3D_OK, "IDirect3DDevice9_SetStreamSource failed with %08x\n", hr);
3699 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
3700 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed with %08x\n", hr);
3701 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
3702 ok(SUCCEEDED(hr), "Failed to disable lighting, hr %#x.\n", hr);
3704 /* Now destroy the bound index buffer and draw again */
3705 ref = IDirect3DIndexBuffer9_Release(ib);
3706 ok(ref == 0, "Index Buffer reference count is %08d\n", ref);
3708 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff0000ff, 1.0f, 0);
3709 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
3711 hr = IDirect3DDevice9_BeginScene(device);
3712 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
3713 /* Deliberately using minvertexindex = 0 and numVertices = 6 to prevent
3714 * D3D from making assumptions about the indices or vertices. */
3715 hr = IDirect3DDevice9_DrawIndexedPrimitive(device, D3DPT_TRIANGLELIST, 0, 3, 3, 0, 1);
3716 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
3717 hr = IDirect3DDevice9_EndScene(device);
3718 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
3720 color = getPixelColor(device, 160, 120);
3721 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x00, 0xff, 0x00), 1), "Got unexpected color 0x%08x.\n", color);
3722 color = getPixelColor(device, 480, 360);
3723 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x00, 0x00, 0xff), 1), "Got unexpected color 0x%08x.\n", color);
3725 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
3726 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
3728 /* Index buffer was already destroyed as part of the test */
3729 IDirect3DVertexBuffer9_Release(vb);
3730 refcount = IDirect3DDevice9_Release(device);
3731 ok(!refcount, "Device has %u references left.\n", refcount);
3732 done:
3733 IDirect3D9_Release(d3d);
3734 DestroyWindow(window);
3737 static void float_texture_test(void)
3739 IDirect3DTexture9 *texture;
3740 IDirect3DDevice9 *device;
3741 D3DLOCKED_RECT lr;
3742 IDirect3D9 *d3d;
3743 ULONG refcount;
3744 float *data;
3745 DWORD color;
3746 HWND window;
3747 HRESULT hr;
3749 static const float quad[] =
3751 -1.0f, -1.0f, 0.1f, 0.0f, 0.0f,
3752 -1.0f, 1.0f, 0.1f, 0.0f, 1.0f,
3753 1.0f, -1.0f, 0.1f, 1.0f, 0.0f,
3754 1.0f, 1.0f, 0.1f, 1.0f, 1.0f,
3757 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
3758 0, 0, 640, 480, NULL, NULL, NULL, NULL);
3759 d3d = Direct3DCreate9(D3D_SDK_VERSION);
3760 ok(!!d3d, "Failed to create a D3D object.\n");
3761 if (!(device = create_device(d3d, window, window, TRUE)))
3763 skip("Failed to create a D3D device, skipping tests.\n");
3764 goto done;
3767 if (IDirect3D9_CheckDeviceFormat(d3d, 0, D3DDEVTYPE_HAL,
3768 D3DFMT_X8R8G8B8, 0, D3DRTYPE_TEXTURE, D3DFMT_R32F) != D3D_OK)
3770 skip("D3DFMT_R32F textures not supported\n");
3771 IDirect3DDevice9_Release(device);
3772 goto done;
3775 hr = IDirect3DDevice9_CreateTexture(device, 1, 1, 1, 0, D3DFMT_R32F, D3DPOOL_MANAGED, &texture, NULL);
3776 ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);
3778 memset(&lr, 0, sizeof(lr));
3779 hr = IDirect3DTexture9_LockRect(texture, 0, &lr, NULL, 0);
3780 ok(hr == D3D_OK, "IDirect3DTexture9_LockRect failed with %08x\n", hr);
3781 data = lr.pBits;
3782 *data = 0.0;
3783 hr = IDirect3DTexture9_UnlockRect(texture, 0);
3784 ok(hr == D3D_OK, "IDirect3DTexture9_UnlockRect failed with %08x\n", hr);
3786 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
3787 ok(SUCCEEDED(hr), "Failed to disable lighting, hr %#x.\n", hr);
3788 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)texture);
3789 ok(hr == D3D_OK, "IDirect3DDevice9_SetTexture failed with %08x\n", hr);
3791 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff0000ff, 1.0f, 0);
3792 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
3794 hr = IDirect3DDevice9_BeginScene(device);
3795 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
3796 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1);
3797 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
3798 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, 5 * sizeof(float));
3799 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
3800 hr = IDirect3DDevice9_EndScene(device);
3801 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
3803 color = getPixelColor(device, 240, 320);
3804 ok(color == 0x0000ffff, "R32F with value 0.0 has color %08x, expected 0x0000ffff\n", color);
3806 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
3807 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
3809 IDirect3DTexture9_Release(texture);
3810 refcount = IDirect3DDevice9_Release(device);
3811 ok(!refcount, "Device has %u references left.\n", refcount);
3812 done:
3813 IDirect3D9_Release(d3d);
3814 DestroyWindow(window);
3817 static void g16r16_texture_test(void)
3819 IDirect3DTexture9 *texture;
3820 IDirect3DDevice9 *device;
3821 D3DLOCKED_RECT lr;
3822 IDirect3D9 *d3d;
3823 ULONG refcount;
3824 DWORD *data;
3825 DWORD color;
3826 HWND window;
3827 HRESULT hr;
3829 static const float quad[] =
3831 -1.0f, -1.0f, 0.1f, 0.0f, 0.0f,
3832 -1.0f, 1.0f, 0.1f, 0.0f, 1.0f,
3833 1.0f, -1.0f, 0.1f, 1.0f, 0.0f,
3834 1.0f, 1.0f, 0.1f, 1.0f, 1.0f,
3837 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
3838 0, 0, 640, 480, NULL, NULL, NULL, NULL);
3839 d3d = Direct3DCreate9(D3D_SDK_VERSION);
3840 ok(!!d3d, "Failed to create a D3D object.\n");
3841 if (!(device = create_device(d3d, window, window, TRUE)))
3843 skip("Failed to create a D3D device, skipping tests.\n");
3844 goto done;
3847 if (IDirect3D9_CheckDeviceFormat(d3d, 0, D3DDEVTYPE_HAL,
3848 D3DFMT_X8R8G8B8, 0, D3DRTYPE_TEXTURE, D3DFMT_G16R16) != D3D_OK)
3850 skip("D3DFMT_G16R16 textures not supported\n");
3851 IDirect3DDevice9_Release(device);
3852 goto done;
3855 hr = IDirect3DDevice9_CreateTexture(device, 1, 1, 1, 0, D3DFMT_G16R16, D3DPOOL_MANAGED, &texture, NULL);
3856 ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);
3858 memset(&lr, 0, sizeof(lr));
3859 hr = IDirect3DTexture9_LockRect(texture, 0, &lr, NULL, 0);
3860 ok(hr == D3D_OK, "IDirect3DTexture9_LockRect failed with %08x\n", hr);
3861 data = lr.pBits;
3862 *data = 0x0f00f000;
3863 hr = IDirect3DTexture9_UnlockRect(texture, 0);
3864 ok(hr == D3D_OK, "IDirect3DTexture9_UnlockRect failed with %08x\n", hr);
3866 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
3867 ok(SUCCEEDED(hr), "Failed to disable lighting, hr %#x.\n", hr);
3868 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)texture);
3869 ok(hr == D3D_OK, "IDirect3DDevice9_SetTexture failed with %08x\n", hr);
3871 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff0000ff, 1.0f, 0);
3872 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
3874 hr = IDirect3DDevice9_BeginScene(device);
3875 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
3876 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1);
3877 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
3878 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, 5 * sizeof(float));
3879 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
3880 hr = IDirect3DDevice9_EndScene(device);
3881 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
3883 color = getPixelColor(device, 240, 320);
3884 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0xf0, 0x0f, 0xff), 1),
3885 "D3DFMT_G16R16 with value 0x00ffff00 has color %08x, expected 0x00f00fff\n", color);
3887 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
3888 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
3890 IDirect3DTexture9_Release(texture);
3891 refcount = IDirect3DDevice9_Release(device);
3892 ok(!refcount, "Device has %u references left.\n", refcount);
3893 done:
3894 IDirect3D9_Release(d3d);
3895 DestroyWindow(window);
3898 static void check_rect(IDirect3DDevice9 *device, RECT r, const char *message)
3900 LONG x_coords[2][2] =
3902 {r.left - 1, r.left + 1},
3903 {r.right + 1, r.right - 1},
3905 LONG y_coords[2][2] =
3907 {r.top - 1, r.top + 1},
3908 {r.bottom + 1, r.bottom - 1}
3910 unsigned int i, j, x_side, y_side;
3912 for (i = 0; i < 2; ++i)
3914 for (j = 0; j < 2; ++j)
3916 for (x_side = 0; x_side < 2; ++x_side)
3918 for (y_side = 0; y_side < 2; ++y_side)
3920 unsigned int x = x_coords[i][x_side], y = y_coords[j][y_side];
3921 DWORD color;
3922 DWORD expected = (x_side == 1 && y_side == 1) ? 0x00ffffff : 0;
3924 color = getPixelColor(device, x, y);
3925 ok(color == expected, "%s: Pixel (%d, %d) has color %08x, expected %08x\n",
3926 message, x, y, color, expected);
3933 struct projected_textures_test_run
3935 const char *message;
3936 DWORD flags;
3937 IDirect3DVertexDeclaration9 *decl;
3938 BOOL vs, ps;
3939 RECT rect;
3942 static void projected_textures_test(IDirect3DDevice9 *device,
3943 struct projected_textures_test_run tests[4])
3945 unsigned int i;
3947 static const DWORD vertex_shader[] =
3949 0xfffe0101, /* vs_1_1 */
3950 0x0000001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
3951 0x0000001f, 0x80000005, 0x900f0001, /* dcl_texcoord0 v1 */
3952 0x00000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
3953 0x00000001, 0xe00f0000, 0x90e40001, /* mov oT0, v1 */
3954 0x0000ffff /* end */
3956 static const DWORD pixel_shader[] =
3958 0xffff0103, /* ps_1_3 */
3959 0x00000042, 0xb00f0000, /* tex t0 */
3960 0x00000001, 0x800f0000, 0xb0e40000, /* mov r0, t0 */
3961 0x0000ffff /* end */
3963 IDirect3DVertexShader9 *vs = NULL;
3964 IDirect3DPixelShader9 *ps = NULL;
3965 IDirect3D9 *d3d;
3966 D3DCAPS9 caps;
3967 HRESULT hr;
3969 IDirect3DDevice9_GetDirect3D(device, &d3d);
3970 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
3971 ok(SUCCEEDED(hr), "GetDeviceCaps failed (%08x)\n", hr);
3972 IDirect3D9_Release(d3d);
3974 if (caps.VertexShaderVersion >= D3DVS_VERSION(1, 1))
3976 hr = IDirect3DDevice9_CreateVertexShader(device, vertex_shader, &vs);
3977 ok(SUCCEEDED(hr), "CreateVertexShader failed (%08x)\n", hr);
3979 if (caps.PixelShaderVersion >= D3DPS_VERSION(1, 3))
3981 hr = IDirect3DDevice9_CreatePixelShader(device, pixel_shader, &ps);
3982 ok(SUCCEEDED(hr), "CreatePixelShader failed (%08x)\n", hr);
3985 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff203040, 0.0f, 0);
3986 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
3988 hr = IDirect3DDevice9_BeginScene(device);
3989 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
3991 for (i = 0; i < 4; ++i)
3993 DWORD value = 0xdeadbeef;
3994 static const float proj_quads[] =
3996 -1.0f, -1.0f, 0.1f, 0.0f, 0.0f, 4.0f, 6.0f,
3997 -1.0f, 0.0f, 0.1f, 0.0f, 4.0f, 4.0f, 6.0f,
3998 0.0f, -1.0f, 0.1f, 4.0f, 0.0f, 4.0f, 6.0f,
3999 0.0f, 0.0f, 0.1f, 4.0f, 4.0f, 4.0f, 6.0f,
4001 0.0f, -1.0f, 0.1f, 0.0f, 0.0f, 4.0f, 6.0f,
4002 0.0f, 0.0f, 0.1f, 0.0f, 4.0f, 4.0f, 6.0f,
4003 1.0f, -1.0f, 0.1f, 4.0f, 0.0f, 4.0f, 6.0f,
4004 1.0f, 0.0f, 0.1f, 4.0f, 4.0f, 4.0f, 6.0f,
4006 -1.0f, 0.0f, 0.1f, 0.0f, 0.0f, 4.0f, 6.0f,
4007 -1.0f, 1.0f, 0.1f, 0.0f, 4.0f, 4.0f, 6.0f,
4008 0.0f, 0.0f, 0.1f, 4.0f, 0.0f, 4.0f, 6.0f,
4009 0.0f, 1.0f, 0.1f, 4.0f, 4.0f, 4.0f, 6.0f,
4011 0.0f, 0.0f, 0.1f, 0.0f, 0.0f, 4.0f, 6.0f,
4012 0.0f, 1.0f, 0.1f, 0.0f, 4.0f, 4.0f, 6.0f,
4013 1.0f, 0.0f, 0.1f, 4.0f, 0.0f, 4.0f, 6.0f,
4014 1.0f, 1.0f, 0.1f, 4.0f, 4.0f, 4.0f, 6.0f,
4017 if (tests[i].vs)
4019 if (!vs)
4021 skip("Vertex shaders not supported, skipping\n");
4022 continue;
4024 hr = IDirect3DDevice9_SetVertexShader(device, vs);
4026 else
4027 hr = IDirect3DDevice9_SetVertexShader(device, NULL);
4028 ok(SUCCEEDED(hr), "SetVertexShader failed (%08x)\n", hr);
4029 if (tests[i].ps)
4031 if (!ps)
4033 skip("Pixel shaders not supported, skipping\n");
4034 continue;
4036 hr = IDirect3DDevice9_SetPixelShader(device, ps);
4038 else
4039 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
4040 ok(SUCCEEDED(hr), "SetPixelShader failed (%08x)\n", hr);
4042 hr = IDirect3DDevice9_SetVertexDeclaration(device, tests[i].decl);
4043 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexDeclaration failed with %08x\n", hr);
4045 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_TEXTURETRANSFORMFLAGS, tests[i].flags);
4046 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTextureStageState failed (%08x)\n", hr);
4047 hr = IDirect3DDevice9_GetTextureStageState(device, 0, D3DTSS_TEXTURETRANSFORMFLAGS, &value);
4048 ok(SUCCEEDED(hr) && value == tests[i].flags,
4049 "GetTextureStageState returned: hr %08x, value %08x.\n", hr, value);
4051 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2,
4052 &proj_quads[i * 4 * 7], 7 * sizeof(float));
4053 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed (%08x)\n", hr);
4056 hr = IDirect3DDevice9_EndScene(device);
4057 ok(hr == D3D_OK, "IDirect3DDevice9_EndScene failed with %08x\n", hr);
4059 hr = IDirect3DDevice9_SetVertexShader(device, NULL);
4060 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
4061 if (vs) IDirect3DVertexShader9_Release(vs);
4062 if (ps) IDirect3DPixelShader9_Release(ps);
4064 for (i = 0; i < 4; ++i)
4066 if ((!tests[i].vs || vs) && (!tests[i].ps || ps))
4067 check_rect(device, tests[i].rect, tests[i].message);
4070 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
4071 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
4074 static void texture_transform_flags_test(void)
4076 HRESULT hr;
4077 IDirect3D9 *d3d;
4078 D3DFORMAT fmt = D3DFMT_X8R8G8B8;
4079 D3DCAPS9 caps;
4080 IDirect3DTexture9 *texture = NULL;
4081 IDirect3DVolumeTexture9 *volume = NULL;
4082 IDirect3DDevice9 *device;
4083 unsigned int x, y, z;
4084 D3DLOCKED_RECT lr;
4085 D3DLOCKED_BOX lb;
4086 D3DCOLOR color;
4087 ULONG refcount;
4088 HWND window;
4089 UINT w, h;
4090 IDirect3DVertexDeclaration9 *decl, *decl2, *decl3, *decl4;
4092 static const D3DVERTEXELEMENT9 decl_elements[] = {
4093 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
4094 {0, 12, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
4095 D3DDECL_END()
4097 static const D3DVERTEXELEMENT9 decl_elements2[] = {
4098 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
4099 {0, 12, D3DDECLTYPE_FLOAT1, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
4100 D3DDECL_END()
4102 static const D3DVERTEXELEMENT9 decl_elements3[] = {
4103 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
4104 {0, 12, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
4105 D3DDECL_END()
4107 static const D3DVERTEXELEMENT9 decl_elements4[] = {
4108 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
4109 {0, 12, D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
4110 D3DDECL_END()
4112 static const unsigned char proj_texdata[] = {0x00, 0x00, 0x00, 0x00,
4113 0x00, 0xff, 0x00, 0x00,
4114 0x00, 0x00, 0x00, 0x00,
4115 0x00, 0x00, 0x00, 0x00};
4116 static const D3DMATRIX identity =
4118 1.0f, 0.0f, 0.0f, 0.0f,
4119 0.0f, 1.0f, 0.0f, 0.0f,
4120 0.0f, 0.0f, 1.0f, 0.0f,
4121 0.0f, 0.0f, 0.0f, 1.0f,
4122 }}};
4124 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
4125 0, 0, 640, 480, NULL, NULL, NULL, NULL);
4126 d3d = Direct3DCreate9(D3D_SDK_VERSION);
4127 ok(!!d3d, "Failed to create a D3D object.\n");
4128 if (!(device = create_device(d3d, window, window, TRUE)))
4130 skip("Failed to create a D3D device, skipping tests.\n");
4131 goto done;
4134 memset(&lr, 0, sizeof(lr));
4135 memset(&lb, 0, sizeof(lb));
4136 if (IDirect3D9_CheckDeviceFormat(d3d, 0, D3DDEVTYPE_HAL,
4137 D3DFMT_X8R8G8B8, 0, D3DRTYPE_TEXTURE, D3DFMT_A16B16G16R16) == D3D_OK)
4138 fmt = D3DFMT_A16B16G16R16;
4140 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements, &decl);
4141 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexDeclaration returned %08x\n", hr);
4142 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements2, &decl2);
4143 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexDeclaration returned %08x\n", hr);
4144 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements3, &decl3);
4145 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexDeclaration returned %08x\n", hr);
4146 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements4, &decl4);
4147 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexDeclaration returned %08x\n", hr);
4148 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_SRGBTEXTURE, FALSE);
4149 ok(hr == D3D_OK, "IDirect3DDevice9_SetSamplerState(D3DSAMP_SRGBTEXTURE) returned %08x\n", hr);
4150 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAGFILTER, D3DTEXF_POINT);
4151 ok(hr == D3D_OK, "IDirect3DDevice9_SetSamplerState(D3DSAMP_MAGFILTER) returned %08x\n", hr);
4152 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MINFILTER, D3DTEXF_POINT);
4153 ok(hr == D3D_OK, "IDirect3DDevice9_SetSamplerState(D3DSAMP_MINFILTER) returned %08x\n", hr);
4154 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MIPFILTER, D3DTEXF_NONE);
4155 ok(hr == D3D_OK, "IDirect3DDevice9_SetSamplerState(D3DSAMP_MIPFILTER) returned %08x\n", hr);
4156 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_ADDRESSU, D3DTADDRESS_CLAMP);
4157 ok(hr == D3D_OK, "IDirect3DDevice9_SetSamplerState(D3DSAMP_ADDRESSU) returned %08x\n", hr);
4158 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_ADDRESSV, D3DTADDRESS_CLAMP);
4159 ok(hr == D3D_OK, "IDirect3DDevice9_SetSamplerState(D3DSAMP_ADDRESSV) returned %08x\n", hr);
4160 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_ADDRESSW, D3DTADDRESS_CLAMP);
4161 ok(hr == D3D_OK, "IDirect3DDevice9_SetSamplerState(D3DSAMP_ADDRESSW) returned %08x\n", hr);
4162 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
4163 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState(D3DTSS_COLOROP) returned %08x\n", hr);
4164 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
4165 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState(D3DTSS_COLORARG1) returned %08x\n", hr);
4166 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
4167 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState(D3DRS_LIGHTING) returned %08x\n", hr);
4168 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff0000ff, 1.0f, 0);
4169 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
4171 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
4172 ok(hr == D3D_OK, "IDirect3DDevice9_GetDeviceCaps returned %08x\n", hr);
4173 w = min(1024, caps.MaxTextureWidth);
4174 h = min(1024, caps.MaxTextureHeight);
4175 hr = IDirect3DDevice9_CreateTexture(device, w, h, 1,
4176 0, fmt, D3DPOOL_MANAGED, &texture, NULL);
4177 ok(hr == D3D_OK, "IDirect3DDevice9_CreateTexture returned %08x\n", hr);
4178 if (!texture)
4180 skip("Failed to create the test texture.\n");
4181 IDirect3DDevice9_Release(device);
4182 goto done;
4185 /* Unfortunately there is no easy way to set up a texture coordinate passthrough
4186 * in d3d fixed function pipeline, so create a texture that has a gradient from 0.0 to
4187 * 1.0 in red and green for the x and y coords
4189 hr = IDirect3DTexture9_LockRect(texture, 0, &lr, NULL, 0);
4190 ok(hr == D3D_OK, "IDirect3DTexture9_LockRect returned %08x\n", hr);
4191 for(y = 0; y < h; y++) {
4192 for(x = 0; x < w; x++) {
4193 double r_f = (double) y / (double) h;
4194 double g_f = (double) x / (double) w;
4195 if(fmt == D3DFMT_A16B16G16R16) {
4196 unsigned short r, g;
4197 unsigned short *dst = (unsigned short *) (((char *) lr.pBits) + y * lr.Pitch + x * 8);
4198 r = (unsigned short) (r_f * 65536.0);
4199 g = (unsigned short) (g_f * 65536.0);
4200 dst[0] = r;
4201 dst[1] = g;
4202 dst[2] = 0;
4203 dst[3] = 65535;
4204 } else {
4205 unsigned char *dst = ((unsigned char *) lr.pBits) + y * lr.Pitch + x * 4;
4206 unsigned char r = (unsigned char) (r_f * 255.0);
4207 unsigned char g = (unsigned char) (g_f * 255.0);
4208 dst[0] = 0;
4209 dst[1] = g;
4210 dst[2] = r;
4211 dst[3] = 255;
4215 hr = IDirect3DTexture9_UnlockRect(texture, 0);
4216 ok(hr == D3D_OK, "IDirect3DTexture9_UnlockRect returned %08x\n", hr);
4217 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *) texture);
4218 ok(hr == D3D_OK, "IDirect3DDevice9_SetTexture returned %08x\n", hr);
4220 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1);
4221 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed with %08x\n", hr);
4222 hr = IDirect3DDevice9_BeginScene(device);
4223 ok(hr == D3D_OK, "IDirect3DDevice9_BeginScene failed with %08x\n", hr);
4224 if(SUCCEEDED(hr))
4226 static const float quad1[] =
4228 -1.0f, -1.0f, 0.1f, 1.0f, 1.0f,
4229 -1.0f, 0.0f, 0.1f, 1.0f, 1.0f,
4230 0.0f, -1.0f, 0.1f, 1.0f, 1.0f,
4231 0.0f, 0.0f, 0.1f, 1.0f, 1.0f,
4233 static const float quad2[] =
4235 -1.0f, 0.0f, 0.1f, 1.0f, 1.0f,
4236 -1.0f, 1.0f, 0.1f, 1.0f, 1.0f,
4237 0.0f, 0.0f, 0.1f, 1.0f, 1.0f,
4238 0.0f, 1.0f, 0.1f, 1.0f, 1.0f,
4240 static const float quad3[] =
4242 0.0f, 0.0f, 0.1f, 0.5f, 0.5f,
4243 0.0f, 1.0f, 0.1f, 0.5f, 0.5f,
4244 1.0f, 0.0f, 0.1f, 0.5f, 0.5f,
4245 1.0f, 1.0f, 0.1f, 0.5f, 0.5f,
4247 static const float quad4[] =
4249 320.0f, 480.0f, 0.1f, 1.0f, 0.0f, 1.0f,
4250 320.0f, 240.0f, 0.1f, 1.0f, 0.0f, 1.0f,
4251 640.0f, 480.0f, 0.1f, 1.0f, 0.0f, 1.0f,
4252 640.0f, 240.0f, 0.1f, 1.0f, 0.0f, 1.0f,
4254 D3DMATRIX mat =
4256 0.0f, 0.0f, 0.0f, 0.0f,
4257 0.0f, 0.0f, 0.0f, 0.0f,
4258 0.0f, 0.0f, 0.0f, 0.0f,
4259 0.0f, 0.0f, 0.0f, 0.0f,
4260 }}};
4262 /* What happens with the texture matrix if D3DTSS_TEXTURETRANSFORMFLAGS is disabled? */
4263 hr = IDirect3DDevice9_SetTransform(device, D3DTS_TEXTURE0, &mat);
4264 ok(hr == D3D_OK, "IDirect3DDevice9_SetTransform failed with %08x\n", hr);
4265 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, 5 * sizeof(float));
4266 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed (%08x)\n", hr);
4268 /* What happens with transforms enabled? */
4269 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_TEXTURETRANSFORMFLAGS, D3DTTFF_COUNT2);
4270 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTextureStageState failed (%08x)\n", hr);
4271 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, 5 * sizeof(float));
4272 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed (%08x)\n", hr);
4274 /* What happens if 4 coords are used, but only 2 given ?*/
4275 U(mat).m[2][0] = 1.0f;
4276 U(mat).m[3][1] = 1.0f;
4277 hr = IDirect3DDevice9_SetTransform(device, D3DTS_TEXTURE0, &mat);
4278 ok(hr == D3D_OK, "IDirect3DDevice9_SetTransform failed with %08x\n", hr);
4279 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_TEXTURETRANSFORMFLAGS, D3DTTFF_COUNT4);
4280 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTextureStageState failed (%08x)\n", hr);
4281 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad3, 5 * sizeof(float));
4282 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed (%08x)\n", hr);
4284 /* What happens with transformed geometry? This setup lead to 0/0 coords with untransformed
4285 * geometry. If the same applies to transformed vertices, the quad will be black, otherwise red,
4286 * due to the coords in the vertices. (turns out red, indeed)
4288 memset(&mat, 0, sizeof(mat));
4289 hr = IDirect3DDevice9_SetTransform(device, D3DTS_TEXTURE0, &mat);
4290 ok(hr == D3D_OK, "IDirect3DDevice9_SetTransform failed with %08x\n", hr);
4291 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZRHW | D3DFVF_TEX1);
4292 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetFVF failed with %08x\n", hr);
4293 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_TEXTURETRANSFORMFLAGS, D3DTTFF_COUNT2);
4294 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTextureStageState failed (%08x)\n", hr);
4295 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad4, 6 * sizeof(float));
4296 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed (%08x)\n", hr);
4298 hr = IDirect3DDevice9_EndScene(device);
4299 ok(hr == D3D_OK, "IDirect3DDevice9_EndScene failed with %08x\n", hr);
4301 color = getPixelColor(device, 160, 360);
4302 ok(color_match(color, 0x00ffff00, 1), "quad 1 has color %08x, expected 0x00ffff00\n", color);
4303 color = getPixelColor(device, 160, 120);
4304 ok(color == 0x00000000, "quad 2 has color %08x, expected 0x0000000\n", color);
4305 color = getPixelColor(device, 480, 120);
4306 ok(color_match(color, 0x0000ff00, 1), "quad 3 has color %08x, expected 0x0000ff00\n", color);
4307 color = getPixelColor(device, 480, 360);
4308 ok(color_match(color, 0x00ff0000, 1), "quad 4 has color %08x, expected 0x00ff0000\n", color);
4309 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
4310 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
4312 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff0000ff, 0.0, 0);
4313 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
4315 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1);
4316 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed with %08x\n", hr);
4317 hr = IDirect3DDevice9_BeginScene(device);
4318 ok(hr == D3D_OK, "IDirect3DDevice9_BeginScene failed with %08x\n", hr);
4319 if(SUCCEEDED(hr))
4321 static const float quad1[] =
4323 -1.0f, -1.0f, 0.1f, 0.8f, 0.2f,
4324 -1.0f, 0.0f, 0.1f, 0.8f, 0.2f,
4325 0.0f, -1.0f, 0.1f, 0.8f, 0.2f,
4326 0.0f, 0.0f, 0.1f, 0.8f, 0.2f,
4328 static const float quad2[] =
4330 -1.0f, 0.0f, 0.1f, 0.5f, 1.0f,
4331 -1.0f, 1.0f, 0.1f, 0.5f, 1.0f,
4332 0.0f, 0.0f, 0.1f, 0.5f, 1.0f,
4333 0.0f, 1.0f, 0.1f, 0.5f, 1.0f,
4335 static const float quad3[] =
4337 0.0f, 0.0f, 0.1f, 0.5f, 1.0f,
4338 0.0f, 1.0f, 0.1f, 0.5f, 1.0f,
4339 1.0f, 0.0f, 0.1f, 0.5f, 1.0f,
4340 1.0f, 1.0f, 0.1f, 0.5f, 1.0f,
4342 static const float quad4[] =
4344 0.0f, -1.0f, 0.1f, 0.8f, 0.2f,
4345 0.0f, 0.0f, 0.1f, 0.8f, 0.2f,
4346 1.0f, -1.0f, 0.1f, 0.8f, 0.2f,
4347 1.0f, 0.0f, 0.1f, 0.8f, 0.2f,
4349 D3DMATRIX mat =
4351 0.0f, 0.0f, 0.0f, 0.0f,
4352 0.0f, 0.0f, 0.0f, 0.0f,
4353 0.0f, 1.0f, 0.0f, 0.0f,
4354 0.0f, 0.0f, 0.0f, 0.0f,
4355 }}};
4357 /* What happens to the default 1 in the 3rd coordinate if it is disabled? */
4358 hr = IDirect3DDevice9_SetTransform(device, D3DTS_TEXTURE0, &mat);
4359 ok(hr == D3D_OK, "IDirect3DDevice9_SetTransform failed with %08x\n", hr);
4360 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_TEXTURETRANSFORMFLAGS, D3DTTFF_COUNT2);
4361 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTextureStageState failed (%08x)\n", hr);
4363 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, 5 * sizeof(float));
4364 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed (%08x)\n", hr);
4366 /* D3DTFF_COUNT1 does not work on Nvidia drivers. It behaves like D3DTTFF_DISABLE. On ATI drivers
4367 * it behaves like COUNT2 because normal textures require 2 coords. */
4368 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_TEXTURETRANSFORMFLAGS, D3DTTFF_COUNT1);
4369 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTextureStageState failed (%08x)\n", hr);
4370 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad4, 5 * sizeof(float));
4371 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed (%08x)\n", hr);
4373 /* Just to be sure, the same as quad2 above */
4374 memset(&mat, 0, sizeof(mat));
4375 hr = IDirect3DDevice9_SetTransform(device, D3DTS_TEXTURE0, &mat);
4376 ok(hr == D3D_OK, "IDirect3DDevice9_SetTransform failed with %08x\n", hr);
4377 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_TEXTURETRANSFORMFLAGS, D3DTTFF_COUNT2);
4378 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTextureStageState failed (%08x)\n", hr);
4379 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, 5 * sizeof(float));
4380 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed (%08x)\n", hr);
4382 /* Now, what happens to the 2nd coordinate(that is disabled in the matrix) if it is not
4383 * used? And what happens to the first? */
4384 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_TEXTURETRANSFORMFLAGS, D3DTTFF_COUNT1);
4385 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTextureStageState failed (%08x)\n", hr);
4386 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad3, 5 * sizeof(float));
4387 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed (%08x)\n", hr);
4389 hr = IDirect3DDevice9_EndScene(device);
4390 ok(hr == D3D_OK, "IDirect3DDevice9_EndScene failed with %08x\n", hr);
4392 color = getPixelColor(device, 160, 360);
4393 ok(color_match(color, 0x00ff0000, 1), "quad 1 has color %08x, expected 0x00ff0000\n", color);
4394 color = getPixelColor(device, 160, 120);
4395 ok(color == 0x00000000, "quad 2 has color %08x, expected 0x0000000\n", color);
4396 color = getPixelColor(device, 480, 120);
4397 ok(color_match(color, 0x00ff8000, 1) || color == 0x00000000,
4398 "quad 3 has color %08x, expected 0x00ff8000\n", color);
4399 color = getPixelColor(device, 480, 360);
4400 ok(color_match(color, 0x0033cc00, 1) || color_match(color, 0x00ff0000, 1),
4401 "quad 4 has color %08x, expected 0x0033cc00\n", color);
4402 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
4403 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
4405 IDirect3DTexture9_Release(texture);
4407 /* Test projected textures, without any fancy matrices */
4408 hr = IDirect3DDevice9_CreateTexture(device, 4, 4, 1, 0, D3DFMT_L8, D3DPOOL_MANAGED, &texture, NULL);
4409 ok(hr == D3D_OK, "IDirect3DDevice9_CreateTexture returned %08x\n", hr);
4410 if (SUCCEEDED(hr))
4412 struct projected_textures_test_run projected_tests_1[4] =
4415 "D3DTTFF_COUNT4 | D3DTTFF_PROJECTED - bottom left",
4416 D3DTTFF_COUNT4 | D3DTTFF_PROJECTED,
4417 decl3,
4418 FALSE, TRUE,
4419 {120, 300, 240, 390},
4422 "D3DTTFF_COUNT3 | D3DTTFF_PROJECTED - bottom right",
4423 D3DTTFF_COUNT3 | D3DTTFF_PROJECTED,
4424 decl3,
4425 FALSE, TRUE,
4426 {400, 360, 480, 420},
4428 /* Try with some invalid values */
4430 "0xffffffff (draws like COUNT4 | PROJECTED) - top left",
4431 0xffffffff,
4432 decl3,
4433 FALSE, TRUE,
4434 {120, 60, 240, 150}
4437 "D3DTTFF_COUNT3 | D3DTTFF_PROJECTED (draws non-projected) - top right",
4438 D3DTTFF_COUNT3 | D3DTTFF_PROJECTED,
4439 decl4,
4440 FALSE, TRUE,
4441 {340, 210, 360, 225},
4444 struct projected_textures_test_run projected_tests_2[4] =
4447 "D3DTTFF_PROJECTED (like COUNT4 | PROJECTED, texcoord has 4 components) - bottom left",
4448 D3DTTFF_PROJECTED,
4449 decl3,
4450 FALSE, TRUE,
4451 {120, 300, 240, 390},
4454 "D3DTTFF_PROJECTED (like COUNT3 | PROJECTED, texcoord has only 3 components) - bottom right",
4455 D3DTTFF_PROJECTED,
4456 decl,
4457 FALSE, TRUE,
4458 {400, 360, 480, 420},
4461 "0xffffffff (like COUNT3 | PROJECTED, texcoord has only 3 components) - top left",
4462 0xffffffff,
4463 decl,
4464 FALSE, TRUE,
4465 {80, 120, 160, 180},
4468 "D3DTTFF_COUNT1 (draws non-projected) - top right",
4469 D3DTTFF_COUNT1,
4470 decl4,
4471 FALSE, TRUE,
4472 {340, 210, 360, 225},
4475 struct projected_textures_test_run projected_tests_3[4] =
4478 "D3DTTFF_COUNT3 | D3DTTFF_PROJECTED (like COUNT4 | PROJECTED) - bottom left",
4479 D3DTTFF_PROJECTED,
4480 decl3,
4481 TRUE, FALSE,
4482 {120, 300, 240, 390},
4485 "D3DTTFF_COUNT3 | D3DTTFF_PROJECTED (like COUNT4 | PROJECTED) - bottom right",
4486 D3DTTFF_COUNT3 | D3DTTFF_PROJECTED,
4487 decl3,
4488 TRUE, TRUE,
4489 {440, 300, 560, 390},
4492 "0xffffffff (like COUNT4 | PROJECTED) - top left",
4493 0xffffffff,
4494 decl3,
4495 TRUE, TRUE,
4496 {120, 60, 240, 150},
4499 "D3DTTFF_PROJECTED (like COUNT4 | PROJECTED) - top right",
4500 D3DTTFF_PROJECTED,
4501 decl3,
4502 FALSE, FALSE,
4503 {440, 60, 560, 150},
4507 hr = IDirect3DDevice9_SetTransform(device, D3DTS_TEXTURE0, &identity);
4508 ok(hr == D3D_OK, "IDirect3DDevice9_SetTransform failed with %08x\n", hr);
4510 hr = IDirect3DTexture9_LockRect(texture, 0, &lr, NULL, 0);
4511 ok(hr == D3D_OK, "IDirect3DTexture9_LockRect failed with %08x\n", hr);
4512 for(x = 0; x < 4; x++) {
4513 memcpy(((BYTE *) lr.pBits) + lr.Pitch * x, proj_texdata + 4 * x, 4 * sizeof(proj_texdata[0]));
4515 hr = IDirect3DTexture9_UnlockRect(texture, 0);
4516 ok(hr == D3D_OK, "IDirect3DTexture9_UnlockRect failed with %08x\n", hr);
4517 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *) texture);
4518 ok(hr == D3D_OK, "IDirect3DDevice9_SetTexture failed with %08x\n", hr);
4520 projected_textures_test(device, projected_tests_1);
4521 projected_textures_test(device, projected_tests_2);
4522 projected_textures_test(device, projected_tests_3);
4524 hr = IDirect3DDevice9_SetTexture(device, 0, NULL);
4525 ok(hr == D3D_OK, "IDirect3DDevice9_SetTexture failed with %08x\n", hr);
4526 IDirect3DTexture9_Release(texture);
4529 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff203040, 0.0, 0);
4530 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
4531 /* Use a smaller volume texture than the biggest possible size for memory and performance reasons
4532 * Thus watch out if sampling from texels between 0 and 1.
4534 hr = IDirect3DDevice9_CreateVolumeTexture(device, 32, 32, 32, 1, 0, fmt, D3DPOOL_MANAGED, &volume, 0);
4535 ok(hr == D3D_OK || hr == D3DERR_INVALIDCALL,
4536 "IDirect3DDevice9_CreateVolumeTexture failed with %08x\n", hr);
4537 if(!volume) {
4538 skip("Failed to create a volume texture\n");
4539 goto out;
4542 hr = IDirect3DVolumeTexture9_LockBox(volume, 0, &lb, NULL, 0);
4543 ok(hr == D3D_OK, "IDirect3DVolumeTexture9_LockBox failed with %08x\n", hr);
4544 for(z = 0; z < 32; z++) {
4545 for(y = 0; y < 32; y++) {
4546 for(x = 0; x < 32; x++) {
4547 char size = (fmt == D3DFMT_A16B16G16R16 ? 8 : 4);
4548 void *mem = ((char *) lb.pBits) + y * lb.RowPitch + z * lb.SlicePitch + x * size;
4549 float r_f = (float) x / 31.0;
4550 float g_f = (float) y / 31.0;
4551 float b_f = (float) z / 31.0;
4553 if(fmt == D3DFMT_A16B16G16R16) {
4554 unsigned short *mem_s = mem;
4555 mem_s[0] = r_f * 65535.0;
4556 mem_s[1] = g_f * 65535.0;
4557 mem_s[2] = b_f * 65535.0;
4558 mem_s[3] = 65535;
4559 } else {
4560 unsigned char *mem_c = mem;
4561 mem_c[0] = b_f * 255.0;
4562 mem_c[1] = g_f * 255.0;
4563 mem_c[2] = r_f * 255.0;
4564 mem_c[3] = 255;
4569 hr = IDirect3DVolumeTexture9_UnlockBox(volume, 0);
4570 ok(hr == D3D_OK, "IDirect3DVolumeTexture9_UnlockBox failed with %08x\n", hr);
4572 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *) volume);
4573 ok(hr == D3D_OK, "IDirect3DVolumeTexture9_UnlockBox failed with %08x\n", hr);
4575 hr = IDirect3DDevice9_BeginScene(device);
4576 ok(hr == D3D_OK, "IDirect3DDevice9_BeginScene failed with %08x\n", hr);
4577 if(SUCCEEDED(hr))
4579 static const float quad1[] =
4581 -1.0f, -1.0f, 0.1f, 1.0f, 1.0f, 1.0f,
4582 -1.0f, 0.0f, 0.1f, 1.0f, 1.0f, 1.0f,
4583 0.0f, -1.0f, 0.1f, 1.0f, 1.0f, 1.0f,
4584 0.0f, 0.0f, 0.1f, 1.0f, 1.0f, 1.0f,
4586 static const float quad2[] =
4588 -1.0f, 0.0f, 0.1f, 1.0f, 1.0f, 1.0f,
4589 -1.0f, 1.0f, 0.1f, 1.0f, 1.0f, 1.0f,
4590 0.0f, 0.0f, 0.1f, 1.0f, 1.0f, 1.0f,
4591 0.0f, 1.0f, 0.1f, 1.0f, 1.0f, 1.0f,
4593 static const float quad3[] =
4595 0.0f, 0.0f, 0.1f, 0.0f, 0.0f,
4596 0.0f, 1.0f, 0.1f, 0.0f, 0.0f,
4597 1.0f, 0.0f, 0.1f, 0.0f, 0.0f,
4598 1.0f, 1.0f, 0.1f, 0.0f, 0.0f,
4600 static const float quad4[] =
4602 0.0f, -1.0f, 0.1f, 1.0f, 1.0f, 1.0f,
4603 0.0f, 0.0f, 0.1f, 1.0f, 1.0f, 1.0f,
4604 1.0f, -1.0f, 0.1f, 1.0f, 1.0f, 1.0f,
4605 1.0f, 0.0f, 0.1f, 1.0f, 1.0f, 1.0f,
4607 D3DMATRIX mat =
4609 1.0f, 0.0f, 0.0f, 0.0f,
4610 0.0f, 0.0f, 1.0f, 0.0f,
4611 0.0f, 1.0f, 0.0f, 0.0f,
4612 0.0f, 0.0f, 0.0f, 1.0f,
4613 }}};
4614 hr = IDirect3DDevice9_SetVertexDeclaration(device, decl);
4615 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexDeclaration failed with %08x\n", hr);
4617 /* Draw a quad with all 3 coords enabled. Nothing fancy. v and w are swapped, but have the same
4618 * values
4620 hr = IDirect3DDevice9_SetTransform(device, D3DTS_TEXTURE0, &mat);
4621 ok(hr == D3D_OK, "IDirect3DDevice9_SetTransform failed with %08x\n", hr);
4622 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_TEXTURETRANSFORMFLAGS, D3DTTFF_COUNT3);
4623 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed (%08x)\n", hr);
4624 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, 6 * sizeof(float));
4625 ok(hr == D3D_OK, "DrawPrimitiveUP failed (%08x)\n", hr);
4627 /* Now disable the w coordinate. Does that change the input, or the output. The coordinates
4628 * are swapped by the matrix. If it changes the input, the v coord will be missing(green),
4629 * otherwise the w will be missing(blue).
4630 * turns out that on nvidia cards the blue color is missing, so it is an output modification.
4631 * On ATI cards the COUNT2 is ignored, and it behaves in the same way as COUNT3. */
4632 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_TEXTURETRANSFORMFLAGS, D3DTTFF_COUNT2);
4633 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed (%08x)\n", hr);
4634 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, 6 * sizeof(float));
4635 ok(hr == D3D_OK, "DrawPrimitiveUP failed (%08x)\n", hr);
4637 /* default values? Set up the identity matrix, pass in 2 vertex coords, and enable 3 */
4638 hr = IDirect3DDevice9_SetTransform(device, D3DTS_TEXTURE0, &identity);
4639 ok(hr == D3D_OK, "IDirect3DDevice9_SetTransform failed with %08x\n", hr);
4640 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_TEXTURETRANSFORMFLAGS, D3DTTFF_COUNT3);
4641 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed (%08x)\n", hr);
4642 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1);
4643 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed with %08x\n", hr);
4644 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad3, 5 * sizeof(float));
4645 ok(hr == D3D_OK, "DrawPrimitiveUP failed (%08x)\n", hr);
4647 /* D3DTTFF_COUNT1. Set a NULL matrix, and count1, pass in all values as 1.0. Nvidia has count1 ==
4648 * disable. ATI extends it up to the amount of values needed for the volume texture
4650 memset(&mat, 0, sizeof(mat));
4651 hr = IDirect3DDevice9_SetTransform(device, D3DTS_TEXTURE0, &mat);
4652 ok(hr == D3D_OK, "IDirect3DDevice9_SetTransform failed with %08x\n", hr);
4653 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_TEXTURETRANSFORMFLAGS, D3DTTFF_COUNT1);
4654 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed (%08x)\n", hr);
4655 hr = IDirect3DDevice9_SetVertexDeclaration(device, decl);
4656 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexDeclaration failed with %08x\n", hr);
4657 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad4, 6 * sizeof(float));
4658 ok(hr == D3D_OK, "DrawPrimitiveUP failed (%08x)\n", hr);
4660 hr = IDirect3DDevice9_EndScene(device);
4661 ok(hr == D3D_OK, "IDirect3DDevice9_EndScene failed with %08x\n", hr);
4664 color = getPixelColor(device, 160, 360);
4665 ok(color == 0x00ffffff, "quad 1 has color %08x, expected 0x00ffffff\n", color);
4666 color = getPixelColor(device, 160, 120);
4667 ok(color == 0x00ffff00 /* NV*/ || color == 0x00ffffff /* ATI */,
4668 "quad 2 has color %08x, expected 0x00ffff00\n", color);
4669 color = getPixelColor(device, 480, 120);
4670 ok(color == 0x000000ff, "quad 3 has color %08x, expected 0x000000ff\n", color);
4671 color = getPixelColor(device, 480, 360);
4672 ok(color == 0x00ffffff || color == 0x0000ff00, "quad 4 has color %08x, expected 0x00ffffff\n", color);
4674 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
4675 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
4677 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff303030, 0.0, 0);
4678 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
4679 hr = IDirect3DDevice9_BeginScene(device);
4680 ok(hr == D3D_OK, "IDirect3DDevice9_BeginScene failed with %08x\n", hr);
4681 if(SUCCEEDED(hr))
4683 static const float quad1[] =
4685 -1.0f, -1.0f, 0.1f, 1.0f, 1.0f, 1.0f,
4686 -1.0f, 0.0f, 0.1f, 1.0f, 1.0f, 1.0f,
4687 0.0f, -1.0f, 0.1f, 1.0f, 1.0f, 1.0f,
4688 0.0f, 0.0f, 0.1f, 1.0f, 1.0f, 1.0f,
4690 static const float quad2[] =
4692 -1.0f, 0.0f, 0.1f,
4693 -1.0f, 1.0f, 0.1f,
4694 0.0f, 0.0f, 0.1f,
4695 0.0f, 1.0f, 0.1f,
4697 static const float quad3[] =
4699 0.0f, 0.0f, 0.1f, 1.0f,
4700 0.0f, 1.0f, 0.1f, 1.0f,
4701 1.0f, 0.0f, 0.1f, 1.0f,
4702 1.0f, 1.0f, 0.1f, 1.0f,
4704 static const D3DMATRIX mat =
4706 0.0f, 0.0f, 0.0f, 0.0f,
4707 0.0f, 0.0f, 0.0f, 0.0f,
4708 0.0f, 0.0f, 0.0f, 0.0f,
4709 0.0f, 1.0f, 0.0f, 0.0f,
4710 }}};
4711 static const D3DMATRIX mat2 =
4713 0.0f, 0.0f, 0.0f, 1.0f,
4714 1.0f, 0.0f, 0.0f, 0.0f,
4715 0.0f, 1.0f, 0.0f, 0.0f,
4716 0.0f, 0.0f, 1.0f, 0.0f,
4717 }}};
4718 hr = IDirect3DDevice9_SetVertexDeclaration(device, decl);
4719 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexDeclaration failed with %08x\n", hr);
4721 /* Default values? 4 coords used, 3 passed. What happens to the 4th?
4722 * Use COUNT3 because newer Nvidia drivers return black when there are more (output) coords
4723 * than being used by the texture(volume tex -> 3). Again, as shown in earlier test the COUNTx
4724 * affects the post-transformation output, so COUNT3 plus the matrix above is OK for testing the
4725 * 4th *input* coordinate.
4727 hr = IDirect3DDevice9_SetTransform(device, D3DTS_TEXTURE0, &mat);
4728 ok(hr == D3D_OK, "IDirect3DDevice9_SetTransform failed with %08x\n", hr);
4729 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_TEXTURETRANSFORMFLAGS, D3DTTFF_COUNT3);
4730 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed (%08x)\n", hr);
4731 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, 6 * sizeof(float));
4732 ok(hr == D3D_OK, "DrawPrimitiveUP failed (%08x)\n", hr);
4734 /* None passed */
4735 hr = IDirect3DDevice9_SetTransform(device, D3DTS_TEXTURE0, &identity);
4736 ok(hr == D3D_OK, "IDirect3DDevice9_SetTransform failed with %08x\n", hr);
4737 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ);
4738 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed with %08x\n", hr);
4739 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, 3 * sizeof(float));
4740 ok(hr == D3D_OK, "DrawPrimitiveUP failed (%08x)\n", hr);
4742 /* 4 used, 1 passed */
4743 hr = IDirect3DDevice9_SetVertexDeclaration(device, decl2);
4744 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexDeclaration failed with %08x\n", hr);
4745 hr = IDirect3DDevice9_SetTransform(device, D3DTS_TEXTURE0, &mat2);
4746 ok(hr == D3D_OK, "IDirect3DDevice9_SetTransform failed with %08x\n", hr);
4747 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad3, 4 * sizeof(float));
4748 ok(hr == D3D_OK, "DrawPrimitiveUP failed (%08x)\n", hr);
4750 hr = IDirect3DDevice9_EndScene(device);
4751 ok(hr == D3D_OK, "IDirect3DDevice9_EndScene failed with %08x\n", hr);
4753 color = getPixelColor(device, 160, 360);
4754 ok(color == 0x0000ff00, "quad 1 has color %08x, expected 0x0000ff00\n", color);
4755 color = getPixelColor(device, 160, 120);
4756 ok(color == 0x00000000, "quad 2 has color %08x, expected 0x00000000\n", color);
4757 color = getPixelColor(device, 480, 120);
4758 ok(color == 0x00ff0000, "quad 3 has color %08x, expected 0x00ff0000\n", color);
4759 /* Quad4: unused */
4761 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
4762 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
4764 IDirect3DVolumeTexture9_Release(volume);
4766 out:
4767 IDirect3DVertexDeclaration9_Release(decl);
4768 IDirect3DVertexDeclaration9_Release(decl2);
4769 IDirect3DVertexDeclaration9_Release(decl3);
4770 IDirect3DVertexDeclaration9_Release(decl4);
4771 refcount = IDirect3DDevice9_Release(device);
4772 ok(!refcount, "Device has %u references left.\n", refcount);
4773 done:
4774 IDirect3D9_Release(d3d);
4775 DestroyWindow(window);
4778 static void texdepth_test(void)
4780 IDirect3DPixelShader9 *shader;
4781 IDirect3DDevice9 *device;
4782 IDirect3D9 *d3d;
4783 ULONG refcount;
4784 D3DCAPS9 caps;
4785 DWORD color;
4786 HWND window;
4787 HRESULT hr;
4789 static const float texdepth_test_data1[] = { 0.25f, 2.0f, 0.0f, 0.0f};
4790 static const float texdepth_test_data2[] = { 0.25f, 0.5f, 0.0f, 0.0f};
4791 static const float texdepth_test_data3[] = {-1.00f, 0.1f, 0.0f, 0.0f};
4792 static const float texdepth_test_data4[] = {-0.25f, -0.5f, 0.0f, 0.0f};
4793 static const float texdepth_test_data5[] = { 1.00f, -0.1f, 0.0f, 0.0f};
4794 static const float texdepth_test_data6[] = { 1.00f, 0.5f, 0.0f, 0.0f};
4795 static const float texdepth_test_data7[] = { 0.50f, 0.0f, 0.0f, 0.0f};
4796 static const DWORD shader_code[] =
4798 0xffff0104, /* ps_1_4 */
4799 0x00000051, 0xa00f0001, 0x00000000, 0x00000000, 0x3f800000, 0x3f800000, /* def c1, 0, 0, 1, 1 */
4800 0x00000001, 0x800f0005, 0xa0e40000, /* mov r5, c0 */
4801 0x0000fffd, /* phase */
4802 0x00000057, 0x800f0005, /* texdepth r5 */
4803 0x00000001, 0x800f0000, 0xa0e40001, /* mov r0, c1 */
4804 0x0000ffff /* end */
4806 static const float vertex[] =
4808 -1.0f, -1.0f, 0.0f,
4809 -1.0f, 1.0f, 0.0f,
4810 1.0f, -1.0f, 1.0f,
4811 1.0f, 1.0f, 1.0f,
4814 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
4815 0, 0, 640, 480, NULL, NULL, NULL, NULL);
4816 d3d = Direct3DCreate9(D3D_SDK_VERSION);
4817 ok(!!d3d, "Failed to create a D3D object.\n");
4818 if (!(device = create_device(d3d, window, window, TRUE)))
4820 skip("Failed to create a D3D device, skipping tests.\n");
4821 goto done;
4824 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
4825 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
4826 if (caps.PixelShaderVersion < D3DPS_VERSION(1, 1))
4828 skip("No ps_1_1 support, skipping tests.\n");
4829 IDirect3DDevice9_Release(device);
4830 goto done;
4833 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code, &shader);
4834 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
4836 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffffff00, 0.0, 0);
4837 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
4838 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
4839 ok(SUCCEEDED(hr), "Failed to disable lighting, hr %#x.\n", hr);
4840 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, D3DZB_TRUE);
4841 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
4842 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, TRUE);
4843 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
4844 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZFUNC, D3DCMP_ALWAYS);
4845 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
4846 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ);
4847 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetFVF returned %#x.\n", hr);
4849 /* Fill the depth buffer with a gradient */
4850 hr = IDirect3DDevice9_BeginScene(device);
4851 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
4852 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, vertex, 3 * sizeof(float));
4853 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
4854 hr = IDirect3DDevice9_EndScene(device);
4855 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
4857 /* Now perform the actual tests. Same geometry, but with the shader */
4858 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZFUNC, D3DCMP_GREATER);
4859 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
4860 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, FALSE);
4861 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
4862 hr = IDirect3DDevice9_SetPixelShader(device, shader);
4863 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShader failed (%08x)\n", hr);
4865 hr = IDirect3DDevice9_SetPixelShaderConstantF(device, 0, texdepth_test_data1, 1);
4866 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShaderConstantF returned %08x\n", hr);
4867 hr = IDirect3DDevice9_BeginScene(device);
4868 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
4869 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, vertex, 3 * sizeof(float));
4870 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
4871 hr = IDirect3DDevice9_EndScene(device);
4872 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
4874 color = getPixelColor(device, 158, 240);
4875 ok(color == 0x000000ff, "Pixel 158(25%% - 2 pixel) has color %08x, expected 0x000000ff\n", color);
4876 color = getPixelColor(device, 162, 240);
4877 ok(color == 0x00ffffff, "Pixel 158(25%% + 2 pixel) has color %08x, expected 0x00ffffff\n", color);
4879 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
4880 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
4882 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffffff00, 0.0, 0);
4883 ok(SUCCEEDED(hr), "IDirect3DDevice9_Clear returned %#x.\n", hr);
4885 hr = IDirect3DDevice9_SetPixelShaderConstantF(device, 0, texdepth_test_data2, 1);
4886 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShaderConstantF returned %08x\n", hr);
4887 hr = IDirect3DDevice9_BeginScene(device);
4888 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
4889 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, vertex, 3 * sizeof(float));
4890 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
4891 hr = IDirect3DDevice9_EndScene(device);
4892 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
4894 color = getPixelColor(device, 318, 240);
4895 ok(color == 0x000000ff, "Pixel 318(50%% - 2 pixel) has color %08x, expected 0x000000ff\n", color);
4896 color = getPixelColor(device, 322, 240);
4897 ok(color == 0x00ffff00, "Pixel 322(50%% + 2 pixel) has color %08x, expected 0x00ffff00\n", color);
4899 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
4900 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
4902 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffff0000, 0.0, 0);
4903 ok(SUCCEEDED(hr), "IDirect3DDevice9_Clear returned %#x.\n", hr);
4905 hr = IDirect3DDevice9_SetPixelShaderConstantF(device, 0, texdepth_test_data3, 1);
4906 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShaderConstantF returned %08x\n", hr);
4907 hr = IDirect3DDevice9_BeginScene(device);
4908 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
4909 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, vertex, 3 * sizeof(float));
4910 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
4911 hr = IDirect3DDevice9_EndScene(device);
4912 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
4914 color = getPixelColor(device, 1, 240);
4915 ok(color == 0x00ff0000, "Pixel 1(0%% + 2 pixel) has color %08x, expected 0x00ff0000\n", color);
4917 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
4918 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
4920 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff00ff00, 0.0, 0);
4921 ok(SUCCEEDED(hr), "IDirect3DDevice9_Clear returned %#x.\n", hr);
4923 hr = IDirect3DDevice9_SetPixelShaderConstantF(device, 0, texdepth_test_data4, 1);
4924 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShaderConstantF returned %08x\n", hr);
4925 hr = IDirect3DDevice9_BeginScene(device);
4926 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
4927 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, vertex, 3 * sizeof(float));
4928 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
4929 hr = IDirect3DDevice9_EndScene(device);
4930 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
4932 color = getPixelColor(device, 318, 240);
4933 ok(color == 0x000000ff, "Pixel 318(50%% - 2 pixel) has color %08x, expected 0x000000ff\n", color);
4934 color = getPixelColor(device, 322, 240);
4935 ok(color == 0x0000ff00, "Pixel 322(50%% + 2 pixel) has color %08x, expected 0x0000ff00\n", color);
4937 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
4938 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
4940 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffffff00, 0.0, 0);
4941 ok(SUCCEEDED(hr), "IDirect3DDevice9_Clear returned %#x.\n", hr);
4943 hr = IDirect3DDevice9_SetPixelShaderConstantF(device, 0, texdepth_test_data5, 1);
4944 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShaderConstantF returned %08x\n", hr);
4945 hr = IDirect3DDevice9_BeginScene(device);
4946 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
4947 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, vertex, 3 * sizeof(float));
4948 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
4949 hr = IDirect3DDevice9_EndScene(device);
4950 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
4952 color = getPixelColor(device, 1, 240);
4953 ok(color == 0x00ffff00, "Pixel 1(0%% + 2 pixel) has color %08x, expected 0x00ffff00\n", color);
4955 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
4956 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
4958 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff00ff00, 0.0, 0);
4959 ok(SUCCEEDED(hr), "IDirect3DDevice9_Clear returned %#x.\n", hr);
4961 hr = IDirect3DDevice9_SetPixelShaderConstantF(device, 0, texdepth_test_data6, 1);
4962 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShaderConstantF returned %08x\n", hr);
4963 hr = IDirect3DDevice9_BeginScene(device);
4964 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
4965 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, vertex, 3 * sizeof(float));
4966 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
4967 hr = IDirect3DDevice9_EndScene(device);
4968 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
4970 color = getPixelColor(device, 638, 240);
4971 ok(color == 0x000000ff, "Pixel 638(100%% + 2 pixel) has color %08x, expected 0x000000ff\n", color);
4973 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
4974 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
4976 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffff0000, 0.0, 0);
4977 ok(SUCCEEDED(hr), "IDirect3DDevice9_Clear returned %#x.\n", hr);
4979 hr = IDirect3DDevice9_SetPixelShaderConstantF(device, 0, texdepth_test_data7, 1);
4980 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShaderConstantF returned %08x\n", hr);
4981 hr = IDirect3DDevice9_BeginScene(device);
4982 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
4983 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, vertex, 3 * sizeof(float));
4984 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
4985 hr = IDirect3DDevice9_EndScene(device);
4986 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
4988 color = getPixelColor(device, 638, 240);
4989 ok(color == 0x000000ff, "Pixel 638(100%% + 2 pixel) has color %08x, expected 0x000000ff\n", color);
4991 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
4992 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
4994 IDirect3DPixelShader9_Release(shader);
4995 refcount = IDirect3DDevice9_Release(device);
4996 ok(!refcount, "Device has %u references left.\n", refcount);
4997 done:
4998 IDirect3D9_Release(d3d);
4999 DestroyWindow(window);
5002 static void texkill_test(void)
5004 IDirect3DPixelShader9 *shader;
5005 IDirect3DDevice9 *device;
5006 IDirect3D9 *d3d;
5007 ULONG refcount;
5008 D3DCAPS9 caps;
5009 DWORD color;
5010 HWND window;
5011 HRESULT hr;
5013 static const float vertex[] =
5015 /* bottom top right left */
5016 -1.0f, -1.0f, 1.0f, -0.1f, 0.9f, 0.9f, -0.1f,
5017 -1.0f, 1.0f, 1.0f, -0.1f, 0.9f, -0.1f, 0.9f,
5018 1.0f, -1.0f, 0.0f, 0.9f, -0.1f, 0.9f, -0.1f,
5019 1.0f, 1.0f, 0.0f, 0.9f, -0.1f, -0.1f, 0.9f,
5021 static const DWORD shader_code_11[] =
5023 0xffff0101, /* ps_1_1 */
5024 0x00000051, 0xa00f0000, 0x3f800000, 0x00000000, 0x00000000, 0x3f800000, /* def c0, 1.0, 0.0, 0.0, 1.0 */
5025 0x00000041, 0xb00f0000, /* texkill t0 */
5026 0x00000001, 0x800f0000, 0xa0e40000, /* mov r0, c0 */
5027 0x0000ffff /* end */
5029 static const DWORD shader_code_20[] =
5031 0xffff0200, /* ps_2_0 */
5032 0x0200001f, 0x80000000, 0xb00f0000, /* dcl t0 */
5033 0x05000051, 0xa00f0000, 0x00000000, 0x00000000, 0x3f800000, 0x3f800000, /* def c0, 0.0, 0.0, 1.0, 1.0 */
5034 0x01000041, 0xb00f0000, /* texkill t0 */
5035 0x02000001, 0x800f0800, 0xa0e40000, /* mov oC0, c0 */
5036 0x0000ffff /* end */
5039 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
5040 0, 0, 640, 480, NULL, NULL, NULL, NULL);
5041 d3d = Direct3DCreate9(D3D_SDK_VERSION);
5042 ok(!!d3d, "Failed to create a D3D object.\n");
5043 if (!(device = create_device(d3d, window, window, TRUE)))
5045 skip("Failed to create a D3D device, skipping tests.\n");
5046 goto done;
5049 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
5050 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
5051 if (caps.PixelShaderVersion < D3DPS_VERSION(1, 1))
5053 skip("No ps_1_1 support, skipping tests.\n");
5054 IDirect3DDevice9_Release(device);
5055 goto done;
5058 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff00ff00, 1.0f, 0);
5059 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
5060 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code_11, &shader);
5061 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
5063 hr = IDirect3DDevice9_SetPixelShader(device, shader);
5064 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShader returned %08x\n", hr);
5065 hr = IDirect3DDevice9_BeginScene(device);
5066 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
5067 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEXCOORDSIZE4(0) | D3DFVF_TEX1);
5068 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
5069 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, vertex, 7 * sizeof(float));
5070 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
5071 hr = IDirect3DDevice9_EndScene(device);
5072 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
5074 color = getPixelColor(device, 63, 46);
5075 ok(color == 0x0000ff00, "Pixel 63/46 has color %08x, expected 0x0000ff00\n", color);
5076 color = getPixelColor(device, 66, 46);
5077 ok(color == 0x0000ff00, "Pixel 66/64 has color %08x, expected 0x0000ff00\n", color);
5078 color = getPixelColor(device, 63, 49);
5079 ok(color == 0x0000ff00, "Pixel 63/49 has color %08x, expected 0x0000ff00\n", color);
5080 color = getPixelColor(device, 66, 49);
5081 ok(color == 0x00ff0000, "Pixel 66/49 has color %08x, expected 0x00ff0000\n", color);
5083 color = getPixelColor(device, 578, 46);
5084 ok(color == 0x0000ff00, "Pixel 578/46 has color %08x, expected 0x0000ff00\n", color);
5085 color = getPixelColor(device, 575, 46);
5086 ok(color == 0x0000ff00, "Pixel 575/64 has color %08x, expected 0x0000ff00\n", color);
5087 color = getPixelColor(device, 578, 49);
5088 ok(color == 0x0000ff00, "Pixel 578/49 has color %08x, expected 0x0000ff00\n", color);
5089 color = getPixelColor(device, 575, 49);
5090 ok(color == 0x00ff0000, "Pixel 575/49 has color %08x, expected 0x00ff0000\n", color);
5092 color = getPixelColor(device, 63, 430);
5093 ok(color == 0x0000ff00, "Pixel 578/46 has color %08x, expected 0x0000ff00\n", color);
5094 color = getPixelColor(device, 63, 433);
5095 ok(color == 0x0000ff00, "Pixel 575/64 has color %08x, expected 0x0000ff00\n", color);
5096 color = getPixelColor(device, 66, 433);
5097 ok(color == 0x00ff0000, "Pixel 578/49 has color %08x, expected 0x00ff0000\n", color);
5098 color = getPixelColor(device, 66, 430);
5099 ok(color == 0x00ff0000, "Pixel 575/49 has color %08x, expected 0x00ff0000\n", color);
5101 color = getPixelColor(device, 578, 430);
5102 ok(color == 0x0000ff00, "Pixel 578/46 has color %08x, expected 0x0000ff00\n", color);
5103 color = getPixelColor(device, 578, 433);
5104 ok(color == 0x0000ff00, "Pixel 575/64 has color %08x, expected 0x0000ff00\n", color);
5105 color = getPixelColor(device, 575, 433);
5106 ok(color == 0x00ff0000, "Pixel 578/49 has color %08x, expected 0x00ff0000\n", color);
5107 color = getPixelColor(device, 575, 430);
5108 ok(color == 0x00ff0000, "Pixel 575/49 has color %08x, expected 0x00ff0000\n", color);
5110 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
5111 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
5113 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
5114 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShader returned %08x\n", hr);
5115 IDirect3DPixelShader9_Release(shader);
5117 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffffff00, 0.0, 0);
5118 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
5119 if (FAILED(IDirect3DDevice9_CreatePixelShader(device, shader_code_20, &shader)))
5121 skip("Failed to create 2.0 test shader, most likely not supported.\n");
5122 IDirect3DDevice9_Release(device);
5123 goto done;
5126 hr = IDirect3DDevice9_SetPixelShader(device, shader);
5127 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShader returned %08x\n", hr);
5128 hr = IDirect3DDevice9_BeginScene(device);
5129 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
5130 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, vertex, 7 * sizeof(float));
5131 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
5132 hr = IDirect3DDevice9_EndScene(device);
5133 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
5135 color = getPixelColor(device, 63, 46);
5136 ok(color == 0x00ffff00, "Pixel 63/46 has color %08x, expected 0x00ffff00\n", color);
5137 color = getPixelColor(device, 66, 46);
5138 ok(color == 0x00ffff00, "Pixel 66/64 has color %08x, expected 0x00ffff00\n", color);
5139 color = getPixelColor(device, 63, 49);
5140 ok(color == 0x00ffff00, "Pixel 63/49 has color %08x, expected 0x00ffff00\n", color);
5141 color = getPixelColor(device, 66, 49);
5142 ok(color == 0x000000ff, "Pixel 66/49 has color %08x, expected 0x000000ff\n", color);
5144 color = getPixelColor(device, 578, 46);
5145 ok(color == 0x00ffff00, "Pixel 578/46 has color %08x, expected 0x00ffff00\n", color);
5146 color = getPixelColor(device, 575, 46);
5147 ok(color == 0x00ffff00, "Pixel 575/64 has color %08x, expected 0x00ffff00\n", color);
5148 color = getPixelColor(device, 578, 49);
5149 ok(color == 0x00ffff00, "Pixel 578/49 has color %08x, expected 0x00ffff00\n", color);
5150 color = getPixelColor(device, 575, 49);
5151 ok(color == 0x000000ff, "Pixel 575/49 has color %08x, expected 0x000000ff\n", color);
5153 color = getPixelColor(device, 63, 430);
5154 ok(color == 0x00ffff00, "Pixel 578/46 has color %08x, expected 0x00ffff00\n", color);
5155 color = getPixelColor(device, 63, 433);
5156 ok(color == 0x00ffff00, "Pixel 575/64 has color %08x, expected 0x00ffff00\n", color);
5157 color = getPixelColor(device, 66, 433);
5158 ok(color == 0x00ffff00, "Pixel 578/49 has color %08x, expected 0x00ffff00\n", color);
5159 color = getPixelColor(device, 66, 430);
5160 ok(color == 0x000000ff, "Pixel 575/49 has color %08x, expected 0x000000ff\n", color);
5162 color = getPixelColor(device, 578, 430);
5163 ok(color == 0x00ffff00, "Pixel 578/46 has color %08x, expected 0x00ffff00\n", color);
5164 color = getPixelColor(device, 578, 433);
5165 ok(color == 0x00ffff00, "Pixel 575/64 has color %08x, expected 0x00ffff00\n", color);
5166 color = getPixelColor(device, 575, 433);
5167 ok(color == 0x00ffff00, "Pixel 578/49 has color %08x, expected 0x00ffff00\n", color);
5168 color = getPixelColor(device, 575, 430);
5169 ok(color == 0x000000ff, "Pixel 575/49 has color %08x, expected 0x000000ff\n", color);
5171 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
5172 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
5174 IDirect3DPixelShader9_Release(shader);
5175 refcount = IDirect3DDevice9_Release(device);
5176 ok(!refcount, "Device has %u references left.\n", refcount);
5177 done:
5178 IDirect3D9_Release(d3d);
5179 DestroyWindow(window);
5182 static void x8l8v8u8_test(void)
5184 IDirect3DPixelShader9 *shader2;
5185 IDirect3DPixelShader9 *shader;
5186 IDirect3DTexture9 *texture;
5187 IDirect3DDevice9 *device;
5188 D3DLOCKED_RECT lr;
5189 IDirect3D9 *d3d;
5190 ULONG refcount;
5191 D3DCAPS9 caps;
5192 DWORD color;
5193 HWND window;
5194 HRESULT hr;
5196 static const DWORD shader_code[] =
5198 0xffff0101, /* ps_1_1 */
5199 0x00000042, 0xb00f0000, /* tex t0 */
5200 0x00000001, 0x800f0000, 0xb0e40000, /* mov r0, t0 */
5201 0x0000ffff /* end */
5203 static const DWORD shader_code2[] =
5205 0xffff0101, /* ps_1_1 */
5206 0x00000042, 0xb00f0000, /* tex t0 */
5207 0x00000001, 0x800f0000, 0xb0ff0000, /* mov r0, t0.w */
5208 0x0000ffff /* end */
5210 static const float quad[] =
5212 -1.0f, -1.0f, 0.1f, 0.5f, 0.5f,
5213 -1.0f, 1.0f, 0.1f, 0.5f, 0.5f,
5214 1.0f, -1.0f, 0.1f, 0.5f, 0.5f,
5215 1.0f, 1.0f, 0.1f, 0.5f, 0.5f,
5218 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
5219 0, 0, 640, 480, NULL, NULL, NULL, NULL);
5220 d3d = Direct3DCreate9(D3D_SDK_VERSION);
5221 ok(!!d3d, "Failed to create a D3D object.\n");
5222 if (!(device = create_device(d3d, window, window, TRUE)))
5224 skip("Failed to create a D3D device, skipping tests.\n");
5225 goto done;
5228 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
5229 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
5230 if (caps.PixelShaderVersion < D3DPS_VERSION(1, 1))
5232 skip("No ps_1_1 support, skipping tests.\n");
5233 IDirect3DDevice9_Release(device);
5234 goto done;
5236 if (FAILED(IDirect3D9_CheckDeviceFormat(d3d, 0, D3DDEVTYPE_HAL,
5237 D3DFMT_X8R8G8B8, 0, D3DRTYPE_TEXTURE, D3DFMT_X8L8V8U8)))
5239 skip("No D3DFMT_X8L8V8U8 support, skipping tests.\n");
5240 IDirect3DDevice9_Release(device);
5241 goto done;
5244 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffff0000, 1.0f, 0);
5245 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
5247 hr = IDirect3DDevice9_CreateTexture(device, 1, 1, 1, 0, D3DFMT_X8L8V8U8, D3DPOOL_MANAGED, &texture, NULL);
5248 ok(hr == D3D_OK, "IDirect3DDevice9_CreateTexture failed (%08x)\n", hr);
5249 memset(&lr, 0, sizeof(lr));
5250 hr = IDirect3DTexture9_LockRect(texture, 0, &lr, NULL, 0);
5251 ok(hr == D3D_OK, "IDirect3DTexture9_LockRect failed (%08x)\n", hr);
5252 *((DWORD *) lr.pBits) = 0x11ca3141;
5253 hr = IDirect3DTexture9_UnlockRect(texture, 0);
5254 ok(hr == D3D_OK, "IDirect3DTexture9_UnlockRect failed (%08x)\n", hr);
5256 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code, &shader);
5257 ok(hr == D3D_OK, "IDirect3DDevice9_CreateShader failed (%08x)\n", hr);
5258 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code2, &shader2);
5259 ok(hr == D3D_OK, "IDirect3DDevice9_CreateShader failed (%08x)\n", hr);
5261 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1);
5262 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed (%08x)\n", hr);
5263 hr = IDirect3DDevice9_SetPixelShader(device, shader);
5264 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShader failed (%08x)\n", hr);
5265 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *) texture);
5266 ok(hr == D3D_OK, "IDirect3DDevice9_SetTexture failed (%08x)\n", hr);
5268 hr = IDirect3DDevice9_BeginScene(device);
5269 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
5270 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, 5 * sizeof(float));
5271 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
5272 hr = IDirect3DDevice9_EndScene(device);
5273 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
5275 color = getPixelColor(device, 578, 430);
5276 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x82, 0x62, 0xca), 1),
5277 "D3DFMT_X8L8V8U8 = 0x112131ca returns color %08x, expected 0x008262ca\n", color);
5278 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
5279 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
5281 hr = IDirect3DDevice9_SetPixelShader(device, shader2);
5282 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShader failed (%08x)\n", hr);
5283 hr = IDirect3DDevice9_BeginScene(device);
5284 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
5285 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, 5 * sizeof(float));
5286 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
5287 hr = IDirect3DDevice9_EndScene(device);
5288 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
5290 color = getPixelColor(device, 578, 430);
5291 ok(color == 0x00ffffff, "w component of D3DFMT_X8L8V8U8 = 0x11ca3141 returns color %08x\n", color);
5292 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
5293 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
5295 IDirect3DPixelShader9_Release(shader);
5296 IDirect3DPixelShader9_Release(shader2);
5297 IDirect3DTexture9_Release(texture);
5298 refcount = IDirect3DDevice9_Release(device);
5299 ok(!refcount, "Device has %u references left.\n", refcount);
5300 done:
5301 IDirect3D9_Release(d3d);
5302 DestroyWindow(window);
5305 static void autogen_mipmap_test(void)
5307 IDirect3DTexture9 *texture = NULL;
5308 IDirect3DSurface9 *surface;
5309 IDirect3DDevice9 *device;
5310 unsigned int x, y;
5311 D3DLOCKED_RECT lr;
5312 IDirect3D9 *d3d;
5313 D3DCOLOR color;
5314 ULONG refcount;
5315 HWND window;
5316 HRESULT hr;
5318 static const RECT r1 = {256, 256, 512, 512};
5319 static const RECT r2 = {512, 256, 768, 512};
5320 static const RECT r3 = {256, 512, 512, 768};
5321 static const RECT r4 = {512, 512, 768, 768};
5322 static const float quad[] =
5324 -0.5f, -0.5f, 0.1f, 0.0f, 0.0f,
5325 -0.5f, 0.5f, 0.1f, 0.0f, 1.0f,
5326 0.5f, -0.5f, 0.1f, 1.0f, 0.0f,
5327 0.5f, 0.5f, 0.1f, 1.0f, 1.0f,
5330 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
5331 0, 0, 640, 480, NULL, NULL, NULL, NULL);
5332 d3d = Direct3DCreate9(D3D_SDK_VERSION);
5333 ok(!!d3d, "Failed to create a D3D object.\n");
5334 if (!(device = create_device(d3d, window, window, TRUE)))
5336 skip("Failed to create a D3D device, skipping tests.\n");
5337 goto done;
5340 if (IDirect3D9_CheckDeviceFormat(d3d, 0, D3DDEVTYPE_HAL,
5341 D3DFMT_X8R8G8B8, D3DUSAGE_AUTOGENMIPMAP, D3DRTYPE_TEXTURE, D3DFMT_X8R8G8B8) != D3D_OK)
5343 skip("No autogenmipmap support.\n");
5344 IDirect3DDevice9_Release(device);
5345 goto done;
5348 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffffff00, 1.0f, 0);
5349 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
5351 /* Make the mipmap big, so that a smaller mipmap is used
5353 hr = IDirect3DDevice9_CreateTexture(device, 1024, 1024, 0, D3DUSAGE_AUTOGENMIPMAP,
5354 D3DFMT_X8R8G8B8, D3DPOOL_MANAGED, &texture, 0);
5355 ok(hr == D3D_OK, "IDirect3DDevice9_CreateTexture returned %08x\n", hr);
5357 hr = IDirect3DTexture9_GetSurfaceLevel(texture, 0, &surface);
5358 ok(hr == D3D_OK, "IDirect3DTexture9_GetSurfaceLevel returned %08x\n", hr);
5359 memset(&lr, 0, sizeof(lr));
5360 hr = IDirect3DSurface9_LockRect(surface, &lr, NULL, 0);
5361 ok(hr == D3D_OK, "IDirect3DSurface9_LockRect returned %08x\n", hr);
5362 for(y = 0; y < 1024; y++) {
5363 for(x = 0; x < 1024; x++) {
5364 DWORD *dst = (DWORD *) (((BYTE *) lr.pBits) + y * lr.Pitch + x * 4);
5365 POINT pt;
5367 pt.x = x;
5368 pt.y = y;
5369 if(PtInRect(&r1, pt)) {
5370 *dst = 0xffff0000;
5371 } else if(PtInRect(&r2, pt)) {
5372 *dst = 0xff00ff00;
5373 } else if(PtInRect(&r3, pt)) {
5374 *dst = 0xff0000ff;
5375 } else if(PtInRect(&r4, pt)) {
5376 *dst = 0xff000000;
5377 } else {
5378 *dst = 0xffffffff;
5382 hr = IDirect3DSurface9_UnlockRect(surface);
5383 ok(hr == D3D_OK, "IDirect3DSurface9_UnlockRect returned %08x\n", hr);
5384 IDirect3DSurface9_Release(surface);
5386 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *) texture);
5387 ok(hr == D3D_OK, "IDirect3DDevice9_SetTexture returned %08x\n", hr);
5388 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MIPFILTER, D3DTEXF_POINT);
5389 ok(hr == D3D_OK, "IDirect3DDevice9_SetSamplerState failed with %08x\n", hr);
5390 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
5391 ok(SUCCEEDED(hr), "Failed to disable lighting, hr %#x.\n", hr);
5393 hr = IDirect3DDevice9_BeginScene(device);
5394 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
5395 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1);
5396 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
5397 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, 5 * sizeof(float));
5398 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
5399 hr = IDirect3DDevice9_EndScene(device);
5400 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
5401 IDirect3DTexture9_Release(texture);
5403 color = getPixelColor(device, 200, 200);
5404 ok(color == 0x00ffffff, "pixel 200/200 has color %08x, expected 0x00ffffff\n", color);
5405 color = getPixelColor(device, 280, 200);
5406 ok(color == 0x000000ff, "pixel 280/200 has color %08x, expected 0x000000ff\n", color);
5407 color = getPixelColor(device, 360, 200);
5408 ok(color == 0x00000000, "pixel 360/200 has color %08x, expected 0x00000000\n", color);
5409 color = getPixelColor(device, 440, 200);
5410 ok(color == 0x00ffffff, "pixel 440/200 has color %08x, expected 0x00ffffff\n", color);
5411 color = getPixelColor(device, 200, 270);
5412 ok(color == 0x00ffffff, "pixel 200/270 has color %08x, expected 0x00ffffff\n", color);
5413 color = getPixelColor(device, 280, 270);
5414 ok(color == 0x00ff0000, "pixel 280/270 has color %08x, expected 0x00ff0000\n", color);
5415 color = getPixelColor(device, 360, 270);
5416 ok(color == 0x0000ff00, "pixel 360/270 has color %08x, expected 0x0000ff00\n", color);
5417 color = getPixelColor(device, 440, 270);
5418 ok(color == 0x00ffffff, "pixel 440/200 has color %08x, expected 0x00ffffff\n", color);
5419 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
5420 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
5422 refcount = IDirect3DDevice9_Release(device);
5423 ok(!refcount, "Device has %u references left.\n", refcount);
5424 done:
5425 IDirect3D9_Release(d3d);
5426 DestroyWindow(window);
5429 static void test_constant_clamp_vs(void)
5431 IDirect3DVertexShader9 *shader_11, *shader_11_2, *shader_20, *shader_20_2;
5432 IDirect3DVertexDeclaration9 *decl;
5433 IDirect3DDevice9 *device;
5434 IDirect3D9 *d3d;
5435 D3DCOLOR color;
5436 ULONG refcount;
5437 D3DCAPS9 caps;
5438 HWND window;
5439 HRESULT hr;
5441 static const DWORD shader_code_11[] =
5443 0xfffe0101, /* vs_1_1 */
5444 0x0000001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
5445 0x00000001, 0x800f0001, 0xa0e40001, /* mov r1, c1 */
5446 0x00000002, 0xd00f0000, 0x80e40001, 0xa0e40002, /* add oD0, r1, c2 */
5447 0x00000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
5448 0x0000ffff /* end */
5450 static const DWORD shader_code_11_2[] =
5452 0xfffe0101, /* vs_1_1 */
5453 0x00000051, 0xa00f0001, 0x3fa00000, 0xbf000000, 0xbfc00000, 0x3f800000, /* dcl ... */
5454 0x00000051, 0xa00f0002, 0xbf000000, 0x3fa00000, 0x40000000, 0x3f800000, /* dcl ... */
5455 0x0000001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
5456 0x00000001, 0x800f0001, 0xa0e40001, /* mov r1, c1 */
5457 0x00000002, 0xd00f0000, 0x80e40001, 0xa0e40002, /* add oD0, r1, c2 */
5458 0x00000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
5459 0x0000ffff /* end */
5461 static const DWORD shader_code_20[] =
5463 0xfffe0200, /* vs_2_0 */
5464 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
5465 0x02000001, 0x800f0001, 0xa0e40001, /* mov r1, c1 */
5466 0x03000002, 0xd00f0000, 0x80e40001, 0xa0e40002, /* add oD0, r1, c2 */
5467 0x02000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
5468 0x0000ffff /* end */
5470 static const DWORD shader_code_20_2[] =
5472 0xfffe0200, /* vs_2_0 */
5473 0x05000051, 0xa00f0001, 0x3fa00000, 0xbf000000, 0xbfc00000, 0x3f800000,
5474 0x05000051, 0xa00f0002, 0xbf000000, 0x3fa00000, 0x40000000, 0x3f800000,
5475 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
5476 0x02000001, 0x800f0001, 0xa0e40001, /* mov r1, c1 */
5477 0x03000002, 0xd00f0000, 0x80e40001, 0xa0e40002, /* add oD0, r1, c2 */
5478 0x02000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
5479 0x0000ffff /* end */
5481 static const D3DVERTEXELEMENT9 decl_elements[] =
5483 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
5484 D3DDECL_END()
5486 static const float quad1[] =
5488 -1.0f, -1.0f, 0.1f,
5489 -1.0f, 0.0f, 0.1f,
5490 0.0f, -1.0f, 0.1f,
5491 0.0f, 0.0f, 0.1f,
5493 static const float quad2[] =
5495 0.0f, -1.0f, 0.1f,
5496 0.0f, 0.0f, 0.1f,
5497 1.0f, -1.0f, 0.1f,
5498 1.0f, 0.0f, 0.1f,
5500 static const float quad3[] =
5502 0.0f, 0.0f, 0.1f,
5503 0.0f, 1.0f, 0.1f,
5504 1.0f, 0.0f, 0.1f,
5505 1.0f, 1.0f, 0.1f,
5507 static const float quad4[] =
5509 -1.0f, 0.0f, 0.1f,
5510 -1.0f, 1.0f, 0.1f,
5511 0.0f, 0.0f, 0.1f,
5512 0.0f, 1.0f, 0.1f,
5514 static const float test_data_c1[4] = { 1.25f, -0.50f, -1.50f, 1.0f};
5515 static const float test_data_c2[4] = {-0.50f, 1.25f, 2.00f, 1.0f};
5517 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
5518 0, 0, 640, 480, NULL, NULL, NULL, NULL);
5519 d3d = Direct3DCreate9(D3D_SDK_VERSION);
5520 ok(!!d3d, "Failed to create a D3D object.\n");
5521 if (!(device = create_device(d3d, window, window, TRUE)))
5523 skip("Failed to create a D3D device, skipping tests.\n");
5524 goto done;
5527 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
5528 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
5529 if (caps.VertexShaderVersion < D3DVS_VERSION(1, 1))
5531 skip("No vs_1_1 support, skipping tests.\n");
5532 IDirect3DDevice9_Release(device);
5533 goto done;
5536 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff00ffff, 1.0f, 0);
5537 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
5539 hr = IDirect3DDevice9_CreateVertexShader(device, shader_code_11, &shader_11);
5540 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader returned %08x\n", hr);
5541 hr = IDirect3DDevice9_CreateVertexShader(device, shader_code_11_2, &shader_11_2);
5542 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader returned %08x\n", hr);
5543 hr = IDirect3DDevice9_CreateVertexShader(device, shader_code_20, &shader_20);
5544 if(FAILED(hr)) shader_20 = NULL;
5545 hr = IDirect3DDevice9_CreateVertexShader(device, shader_code_20_2, &shader_20_2);
5546 if(FAILED(hr)) shader_20_2 = NULL;
5547 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements, &decl);
5548 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexDeclaration returned %08x\n", hr);
5550 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 1, test_data_c1, 1);
5551 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexShaderConstantF returned %08x\n", hr);
5552 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 2, test_data_c2, 1);
5553 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexShaderConstantF returned %08x\n", hr);
5554 hr = IDirect3DDevice9_SetVertexDeclaration(device, decl);
5555 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexDeclaration returned %08x\n", hr);
5557 hr = IDirect3DDevice9_BeginScene(device);
5558 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
5560 hr = IDirect3DDevice9_SetVertexShader(device, shader_11);
5561 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
5562 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, 3 * sizeof(float));
5563 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
5565 hr = IDirect3DDevice9_SetVertexShader(device, shader_11_2);
5566 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
5567 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, 3 * sizeof(float));
5568 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
5570 if (shader_20)
5572 hr = IDirect3DDevice9_SetVertexShader(device, shader_20);
5573 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
5574 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad3, 3 * sizeof(float));
5575 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
5578 if (shader_20_2)
5580 hr = IDirect3DDevice9_SetVertexShader(device, shader_20_2);
5581 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
5582 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad4, 3 * sizeof(float));
5583 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
5586 hr = IDirect3DDevice9_EndScene(device);
5587 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
5589 color = getPixelColor(device, 160, 360);
5590 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0xbf, 0xbf, 0x80), 1),
5591 "quad 1 has color %08x, expected 0x00bfbf80\n", color);
5592 color = getPixelColor(device, 480, 360);
5593 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0xbf, 0xbf, 0x80), 1),
5594 "quad 2 has color %08x, expected 0x00bfbf80\n", color);
5595 if(shader_20) {
5596 color = getPixelColor(device, 480, 120);
5597 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0xbf, 0xbf, 0x80), 1),
5598 "quad 3 has color %08x, expected 0x00bfbf80\n", color);
5600 if(shader_20_2) {
5601 color = getPixelColor(device, 160, 120);
5602 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0xbf, 0xbf, 0x80), 1),
5603 "quad 4 has color %08x, expected 0x00bfbf80\n", color);
5605 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
5606 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
5608 IDirect3DVertexDeclaration9_Release(decl);
5609 if(shader_20_2) IDirect3DVertexShader9_Release(shader_20_2);
5610 if(shader_20) IDirect3DVertexShader9_Release(shader_20);
5611 IDirect3DVertexShader9_Release(shader_11_2);
5612 IDirect3DVertexShader9_Release(shader_11);
5613 refcount = IDirect3DDevice9_Release(device);
5614 ok(!refcount, "Device has %u references left.\n", refcount);
5615 done:
5616 IDirect3D9_Release(d3d);
5617 DestroyWindow(window);
5620 static void constant_clamp_ps_test(void)
5622 IDirect3DPixelShader9 *shader_11, *shader_12, *shader_14, *shader_20;
5623 IDirect3DDevice9 *device;
5624 IDirect3D9 *d3d;
5625 ULONG refcount;
5626 D3DCAPS9 caps;
5627 DWORD color;
5628 HWND window;
5629 HRESULT hr;
5631 static const DWORD shader_code_11[] =
5633 0xffff0101, /* ps_1_1 */
5634 0x00000001, 0x800f0001, 0xa0e40001, /* mov r1, c1 */
5635 0x00000002, 0x800f0000, 0x80e40001, 0xa0e40002, /* add r0, r1, c2 */
5636 0x0000ffff /* end */
5638 static const DWORD shader_code_12[] =
5640 0xffff0102, /* ps_1_2 */
5641 0x00000001, 0x800f0001, 0xa0e40001, /* mov r1, c1 */
5642 0x00000002, 0x800f0000, 0x80e40001, 0xa0e40002, /* add r0, r1, c2 */
5643 0x0000ffff /* end */
5645 /* Skip 1.3 shaders because we have only 4 quads (ok, could make them
5646 * smaller if needed). 1.2 and 1.4 shaders behave the same, so it's
5647 * unlikely that 1.3 shaders are different. During development of this
5648 * test, 1.3 shaders were verified too. */
5649 static const DWORD shader_code_14[] =
5651 0xffff0104, /* ps_1_4 */
5652 /* Try to make one constant local. It gets clamped too, although the
5653 * binary contains the bigger numbers. */
5654 0x00000051, 0xa00f0002, 0xbf000000, 0x3fa00000, 0x40000000, 0x3f800000, /* def c2, -0.5, 1.25, 2, 1 */
5655 0x00000001, 0x800f0001, 0xa0e40001, /* mov r1, c1 */
5656 0x00000002, 0x800f0000, 0x80e40001, 0xa0e40002, /* add r0, r1, c2 */
5657 0x0000ffff /* end */
5659 static const DWORD shader_code_20[] =
5661 0xffff0200, /* ps_2_0 */
5662 0x02000001, 0x800f0001, 0xa0e40001, /* mov r1, c1 */
5663 0x03000002, 0x800f0000, 0x80e40001, 0xa0e40002, /* add r0, r1, c2 */
5664 0x02000001, 0x800f0800, 0x80e40000, /* mov oC0, r0 */
5665 0x0000ffff /* end */
5667 static const float quad1[] =
5669 -1.0f, -1.0f, 0.1f,
5670 -1.0f, 0.0f, 0.1f,
5671 0.0f, -1.0f, 0.1f,
5672 0.0f, 0.0f, 0.1f,
5674 static const float quad2[] =
5676 0.0f, -1.0f, 0.1f,
5677 0.0f, 0.0f, 0.1f,
5678 1.0f, -1.0f, 0.1f,
5679 1.0f, 0.0f, 0.1f,
5681 static const float quad3[] =
5683 0.0f, 0.0f, 0.1f,
5684 0.0f, 1.0f, 0.1f,
5685 1.0f, 0.0f, 0.1f,
5686 1.0f, 1.0f, 0.1f,
5688 static const float quad4[] =
5690 -1.0f, 0.0f, 0.1f,
5691 -1.0f, 1.0f, 0.1f,
5692 0.0f, 0.0f, 0.1f,
5693 0.0f, 1.0f, 0.1f,
5695 static const float test_data_c1[4] = { 1.25f, -0.50f, -1.50f, 1.0f};
5696 static const float test_data_c2[4] = {-0.50f, 1.25f, 2.00f, 1.0f};
5698 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
5699 0, 0, 640, 480, NULL, NULL, NULL, NULL);
5700 d3d = Direct3DCreate9(D3D_SDK_VERSION);
5701 ok(!!d3d, "Failed to create a D3D object.\n");
5702 if (!(device = create_device(d3d, window, window, TRUE)))
5704 skip("Failed to create a D3D device, skipping tests.\n");
5705 goto done;
5708 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
5709 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
5710 if (caps.PixelShaderVersion < D3DPS_VERSION(1, 4))
5712 skip("No ps_1_4 support, skipping tests.\n");
5713 IDirect3DDevice9_Release(device);
5714 goto done;
5717 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff00ffff, 1.0f, 0);
5718 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
5720 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code_11, &shader_11);
5721 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
5722 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code_12, &shader_12);
5723 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
5724 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code_14, &shader_14);
5725 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
5726 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code_20, &shader_20);
5727 if(FAILED(hr)) shader_20 = NULL;
5729 hr = IDirect3DDevice9_SetPixelShaderConstantF(device, 1, test_data_c1, 1);
5730 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShaderConstantF returned %08x\n", hr);
5731 hr = IDirect3DDevice9_SetPixelShaderConstantF(device, 2, test_data_c2, 1);
5732 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShaderConstantF returned %08x\n", hr);
5733 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ);
5734 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF returned %08x\n", hr);
5736 hr = IDirect3DDevice9_BeginScene(device);
5737 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
5739 hr = IDirect3DDevice9_SetPixelShader(device, shader_11);
5740 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
5741 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, 3 * sizeof(float));
5742 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
5744 hr = IDirect3DDevice9_SetPixelShader(device, shader_12);
5745 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
5746 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, 3 * sizeof(float));
5747 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
5749 hr = IDirect3DDevice9_SetPixelShader(device, shader_14);
5750 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
5751 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad3, 3 * sizeof(float));
5752 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
5754 if (shader_20)
5756 hr = IDirect3DDevice9_SetPixelShader(device, shader_20);
5757 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
5758 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad4, 3 * sizeof(float));
5759 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
5762 hr = IDirect3DDevice9_EndScene(device);
5763 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
5765 color = getPixelColor(device, 160, 360);
5766 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x80, 0x80, 0x00), 1),
5767 "quad 1 has color %08x, expected 0x00808000\n", color);
5768 color = getPixelColor(device, 480, 360);
5769 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x80, 0x80, 0x00), 1),
5770 "quad 2 has color %08x, expected 0x00808000\n", color);
5771 color = getPixelColor(device, 480, 120);
5772 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x80, 0x80, 0x00), 1),
5773 "quad 3 has color %08x, expected 0x00808000\n", color);
5774 if(shader_20) {
5775 color = getPixelColor(device, 160, 120);
5776 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0xbf, 0xbf, 0x80), 1),
5777 "quad 4 has color %08x, expected 0x00bfbf80\n", color);
5779 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
5780 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
5782 if(shader_20) IDirect3DPixelShader9_Release(shader_20);
5783 IDirect3DPixelShader9_Release(shader_14);
5784 IDirect3DPixelShader9_Release(shader_12);
5785 IDirect3DPixelShader9_Release(shader_11);
5786 refcount = IDirect3DDevice9_Release(device);
5787 ok(!refcount, "Device has %u references left.\n", refcount);
5788 done:
5789 IDirect3D9_Release(d3d);
5790 DestroyWindow(window);
5793 static void dp2add_ps_test(void)
5795 IDirect3DPixelShader9 *shader_dp2add_sat;
5796 IDirect3DPixelShader9 *shader_dp2add;
5797 IDirect3DDevice9 *device;
5798 IDirect3D9 *d3d;
5799 ULONG refcount;
5800 D3DCAPS9 caps;
5801 DWORD color;
5802 HWND window;
5803 HRESULT hr;
5805 /* DP2ADD is defined as: (src0.r * src1.r) + (src0.g * src1.g) + src2.
5806 * One D3D restriction of all shader instructions except SINCOS is that no more than 2
5807 * source tokens can be constants. So, for this exercise, we move contents of c0 to
5808 * r0 first.
5809 * The result here for the r,g,b components should be roughly 0.5:
5810 * (0.5 * 0.5) + (0.5 * 0.5) + 0.0 = 0.5 */
5811 static const DWORD shader_code_dp2add[] = {
5812 0xffff0200, /* ps_2_0 */
5813 0x05000051, 0xa00f0000, 0x3f000000, 0x3f000000, 0x3f800000, 0x00000000, /* def c0, 0.5, 0.5, 1.0, 0 */
5815 0x02000001, 0x800f0000, 0xa0e40000, /* mov r0, c0 */
5816 0x0400005a, 0x80070000, 0x80000000, 0x80000000, 0x80ff0000, /* dp2add r0.rgb, r0, r0, r0.a */
5818 0x02000001, 0x80080000, 0xa0aa0000, /* mov r0.a, c0.b */
5819 0x02000001, 0x800f0800, 0x80e40000, /* mov oC0, r0 */
5820 0x0000ffff /* end */
5823 /* Test the _sat modifier, too. Result here should be:
5824 * DP2: (-0.5 * -0.5) + (-0.5 * -0.5) + 2.0 = 2.5
5825 * _SAT: ==> 1.0
5826 * ADD: (1.0 + -0.5) = 0.5
5828 static const DWORD shader_code_dp2add_sat[] = {
5829 0xffff0200, /* ps_2_0 */
5830 0x05000051, 0xa00f0000, 0xbf000000, 0xbf000000, 0x3f800000, 0x40000000, /* def c0, -0.5, -0.5, 1.0, 2.0 */
5832 0x02000001, 0x800f0000, 0xa0e40000, /* mov r0, c0 */
5833 0x0400005a, 0x80170000, 0x80000000, 0x80000000, 0x80ff0000, /* dp2add_sat r0.rgb, r0, r0, r0.a */
5834 0x03000002, 0x80070000, 0x80e40000, 0xa0000000, /* add r0.rgb, r0, c0.r */
5836 0x02000001, 0x80080000, 0xa0aa0000, /* mov r0.a, c0.b */
5837 0x02000001, 0x800f0800, 0x80e40000, /* mov oC0, r0 */
5838 0x0000ffff /* end */
5840 static const float quad[] =
5842 -1.0f, -1.0f, 0.1f,
5843 -1.0f, 1.0f, 0.1f,
5844 1.0f, -1.0f, 0.1f,
5845 1.0f, 1.0f, 0.1f,
5848 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
5849 0, 0, 640, 480, NULL, NULL, NULL, NULL);
5850 d3d = Direct3DCreate9(D3D_SDK_VERSION);
5851 ok(!!d3d, "Failed to create a D3D object.\n");
5852 if (!(device = create_device(d3d, window, window, TRUE)))
5854 skip("Failed to create a D3D device, skipping tests.\n");
5855 goto done;
5858 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
5859 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
5860 if (caps.PixelShaderVersion < D3DPS_VERSION(2, 0))
5862 skip("No ps_2_0 support, skipping tests.\n");
5863 IDirect3DDevice9_Release(device);
5864 goto done;
5867 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff000000, 1.0f, 0);
5868 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
5870 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code_dp2add, &shader_dp2add);
5871 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
5873 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code_dp2add_sat, &shader_dp2add_sat);
5874 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
5876 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ);
5877 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF returned %08x\n", hr);
5879 hr = IDirect3DDevice9_SetPixelShader(device, shader_dp2add);
5880 ok(SUCCEEDED(hr), "Failed to create pixel shader, hr %#x.\n", hr);
5881 hr = IDirect3DDevice9_BeginScene(device);
5882 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
5883 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, 3 * sizeof(float));
5884 ok(SUCCEEDED(hr), "Failed to draw primitive, hr %#x.\n", hr);
5885 hr = IDirect3DDevice9_EndScene(device);
5886 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
5888 color = getPixelColor(device, 360, 240);
5889 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x7f, 0x7f, 0x7f), 1), "Got unexpected color 0x%08x.\n", color);
5891 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
5892 ok(SUCCEEDED(hr), "Failed to present frame, hr %#x.\n", hr);
5893 IDirect3DPixelShader9_Release(shader_dp2add);
5895 hr = IDirect3DDevice9_SetPixelShader(device, shader_dp2add_sat);
5896 ok(SUCCEEDED(hr), "Failed to create pixel shader, hr %#x.\n", hr);
5897 hr = IDirect3DDevice9_BeginScene(device);
5898 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
5899 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, 3 * sizeof(float));
5900 ok(SUCCEEDED(hr), "Failed to draw primitive, hr %#x.\n", hr);
5901 hr = IDirect3DDevice9_EndScene(device);
5902 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
5904 color = getPixelColor(device, 360, 240);
5905 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x7f, 0x7f, 0x7f), 1), "Got unexpected color 0x%08x.\n", color);
5907 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
5908 ok(SUCCEEDED(hr), "Failed to present frame, hr %#x.\n", hr);
5909 IDirect3DPixelShader9_Release(shader_dp2add_sat);
5911 refcount = IDirect3DDevice9_Release(device);
5912 ok(!refcount, "Device has %u references left.\n", refcount);
5913 done:
5914 IDirect3D9_Release(d3d);
5915 DestroyWindow(window);
5918 static void cnd_test(void)
5920 IDirect3DPixelShader9 *shader_11_coissue_2, *shader_12_coissue_2, *shader_13_coissue_2, *shader_14_coissue_2;
5921 IDirect3DPixelShader9 *shader_11_coissue, *shader_12_coissue, *shader_13_coissue, *shader_14_coissue;
5922 IDirect3DPixelShader9 *shader_11, *shader_12, *shader_13, *shader_14;
5923 IDirect3DDevice9 *device;
5924 IDirect3D9 *d3d;
5925 ULONG refcount;
5926 D3DCAPS9 caps;
5927 HWND window;
5928 DWORD color;
5929 HRESULT hr;
5931 /* ps 1.x shaders are rather picky with writemasks and source swizzles.
5932 * The dp3 is used to copy r0.r to all components of r1, then copy r1.a to
5933 * r0.a. Essentially it does a mov r0.a, r0.r, which isn't allowed as-is
5934 * in 1.x pixel shaders. */
5935 static const DWORD shader_code_11[] =
5937 0xffff0101, /* ps_1_1 */
5938 0x00000051, 0xa00f0000, 0x3f800000, 0x00000000, 0x00000000, 0x00000000, /* def c0, 1, 0, 0, 0 */
5939 0x00000040, 0xb00f0000, /* texcoord t0 */
5940 0x00000001, 0x800f0000, 0xb0e40000, /* mov r0, ???(t0) */
5941 0x00000008, 0x800f0001, 0x80e40000, 0xa0e40000, /* dp3 r1, r0, c0 */
5942 0x00000001, 0x80080000, 0x80ff0001, /* mov r0.a, r1.a */
5943 0x00000050, 0x800f0000, 0x80ff0000, 0xa0e40001, 0xa0e40002, /* cnd r0, r0.a, c1, c2 */
5944 0x0000ffff /* end */
5946 static const DWORD shader_code_12[] =
5948 0xffff0102, /* ps_1_2 */
5949 0x00000051, 0xa00f0000, 0x3f800000, 0x00000000, 0x00000000, 0x00000000, /* def c0, 1, 0, 0, 0 */
5950 0x00000040, 0xb00f0000, /* texcoord t0 */
5951 0x00000001, 0x800f0000, 0xb0e40000, /* mov r0, t0 */
5952 0x00000008, 0x800f0001, 0x80e40000, 0xa0e40000, /* dp3 r1, r0, c0 */
5953 0x00000001, 0x80080000, 0x80ff0001, /* mov r0.a, r1.a */
5954 0x00000050, 0x800f0000, 0x80ff0000, 0xa0e40001, 0xa0e40002, /* cnd r0, r0.a, c1, c2 */
5955 0x0000ffff /* end */
5957 static const DWORD shader_code_13[] =
5959 0xffff0103, /* ps_1_3 */
5960 0x00000051, 0xa00f0000, 0x3f800000, 0x00000000, 0x00000000, 0x00000000, /* def c0, 1, 0, 0, 0 */
5961 0x00000040, 0xb00f0000, /* texcoord t0 */
5962 0x00000001, 0x800f0000, 0xb0e40000, /* mov r0, t0 */
5963 0x00000008, 0x800f0001, 0x80e40000, 0xa0e40000, /* dp3, r1, r0, c0 */
5964 0x00000001, 0x80080000, 0x80ff0001, /* mov r0.a, r1.a */
5965 0x00000050, 0x800f0000, 0x80ff0000, 0xa0e40001, 0xa0e40002, /* cnd r0, r0.a, c1, c2 */
5966 0x0000ffff /* end */
5968 static const DWORD shader_code_14[] =
5970 0xffff0104, /* ps_1_3 */
5971 0x00000051, 0xa00f0000, 0x00000000, 0x00000000, 0x00000000, 0x3f800000, /* def c0, 0, 0, 0, 1 */
5972 0x00000040, 0x80070000, 0xb0e40000, /* texcrd r0, t0 */
5973 0x00000001, 0x80080000, 0xa0ff0000, /* mov r0.a, c0.a */
5974 0x00000050, 0x800f0000, 0x80e40000, 0xa0e40001, 0xa0e40002, /* cnd r0, r0, c1, c2 */
5975 0x0000ffff /* end */
5978 /* Special fun: The coissue flag on cnd: Apparently cnd always selects the 2nd source,
5979 * as if the src0 comparison against 0.5 always evaluates to true. The coissue flag isn't
5980 * set by the compiler, it was added manually after compilation. Note that the COISSUE
5981 * flag on a color(.xyz) operation is only allowed after an alpha operation. DirectX doesn't
5982 * have proper docs, but GL_ATI_fragment_shader explains the pairing of color and alpha ops
5983 * well enough.
5985 * The shader attempts to test the range [-1;1] against coissued cnd, which is a bit tricky.
5986 * The input from t0 is [0;1]. 0.5 is subtracted, then we have to multiply with 2. Since
5987 * constants are clamped to [-1;1], a 2.0 is constructed by adding c0.r(=1.0) to c0.r into r1.r,
5988 * then r1(2.0, 0.0, 0.0, 0.0) is passed to dp3(explained above).
5990 static const DWORD shader_code_11_coissue[] =
5992 0xffff0101, /* ps_1_1 */
5993 0x00000051, 0xa00f0000, 0x3f800000, 0x00000000, 0x00000000, 0x00000000, /* def c0, 1, 0, 0, 0 */
5994 0x00000051, 0xa00f0003, 0x3f000000, 0x3f000000, 0x3f000000, 0x00000000, /* def c3, 0.5, 0.5, 0.5, 0 */
5995 0x00000040, 0xb00f0000, /* texcoord t0 */
5996 0x00000001, 0x800f0000, 0xb0e40000, /* mov r0, t0 */
5997 0x00000003, 0x800f0000, 0x80e40000, 0xa0e40003, /* sub r0, r0, c3 */
5998 0x00000002, 0x800f0001, 0xa0e40000, 0xa0e40000, /* add r1, c0, c0 */
5999 0x00000008, 0x800f0001, 0x80e40000, 0x80e40001, /* dp3 r1, r0, r1 */
6000 0x00000001, 0x80080000, 0x80ff0001, /* mov r0.a, r1.a */
6001 0x40000050, 0x80070000, 0x80ff0000, 0xa0e40001, 0xa0e40002, /* +cnd r0.xyz, r0.a, c1, c2*/
6002 0x0000ffff /* end */
6004 static const DWORD shader_code_11_coissue_2[] =
6006 0xffff0101, /* ps_1_1 */
6007 0x00000051, 0xa00f0000, 0x3f800000, 0x00000000, 0x00000000, 0x00000000, /* def c0, 1, 0, 0, 0 */
6008 0x00000051, 0xa00f0003, 0x3f000000, 0x3f000000, 0x3f000000, 0x00000000, /* def c3, 0.5, 0.5, 0.5, 0 */
6009 0x00000040, 0xb00f0000, /* texcoord t0 */
6010 0x00000001, 0x800f0000, 0xb0e40000, /* mov r0, t0 */
6011 0x00000003, 0x800f0000, 0x80e40000, 0xa0e40003, /* sub r0, r0, c3 */
6012 0x00000002, 0x800f0001, 0xa0e40000, 0xa0e40000, /* add r1, c0, c0 */
6013 0x00000008, 0x800f0001, 0x80e40000, 0x80e40001, /* dp3 r1, r0, r1 */
6014 0x00000001, 0x800f0000, 0x80e40001, /* mov r0, r1 */
6015 0x00000001, 0x80070000, 0x80ff0001, /* mov r0.xyz, r1.a */
6016 0x40000050, 0x80080000, 0x80ff0000, 0xa0e40001, 0xa0e40002, /* +cnd r0.a, r0.a, c1, c2 */
6017 0x00000001, 0x80070000, 0x80ff0000, /* mov r0.xyz, r0.a */
6018 0x0000ffff /* end */
6020 static const DWORD shader_code_12_coissue[] =
6022 0xffff0102, /* ps_1_2 */
6023 0x00000051, 0xa00f0000, 0x3f800000, 0x00000000, 0x00000000, 0x00000000, /* def c0, 1, 0, 0, 0 */
6024 0x00000051, 0xa00f0003, 0x3f000000, 0x3f000000, 0x3f000000, 0x00000000, /* def c3, 0.5, 0.5, 0.5, 0 */
6025 0x00000040, 0xb00f0000, /* texcoord t0 */
6026 0x00000001, 0x800f0000, 0xb0e40000, /* mov r0, t0 */
6027 0x00000003, 0x800f0000, 0x80e40000, 0xa0e40003, /* sub r0, r0, c3 */
6028 0x00000002, 0x800f0001, 0xa0e40000, 0xa0e40000, /* add r1, c0, c0 */
6029 0x00000008, 0x800f0001, 0x80e40000, 0x80e40001, /* dp3 r1, r0, r1 */
6030 0x00000001, 0x80080000, 0x80ff0001, /* mov r0.a, r1.a */
6031 0x40000050, 0x80070000, 0x80ff0000, 0xa0e40001, 0xa0e40002, /* +cnd r0.xyz, r0.a, c1, c2*/
6032 0x0000ffff /* end */
6034 static const DWORD shader_code_12_coissue_2[] =
6036 0xffff0102, /* ps_1_2 */
6037 0x00000051, 0xa00f0000, 0x3f800000, 0x00000000, 0x00000000, 0x00000000, /* def c0, 1, 0, 0, 0 */
6038 0x00000051, 0xa00f0003, 0x3f000000, 0x3f000000, 0x3f000000, 0x00000000, /* def c3, 0.5, 0.5, 0.5, 0 */
6039 0x00000040, 0xb00f0000, /* texcoord t0 */
6040 0x00000001, 0x800f0000, 0xb0e40000, /* mov r0, t0 */
6041 0x00000003, 0x800f0000, 0x80e40000, 0xa0e40003, /* sub r0, r0, c3 */
6042 0x00000002, 0x800f0001, 0xa0e40000, 0xa0e40000, /* add r1, c0, c0 */
6043 0x00000008, 0x800f0001, 0x80e40000, 0x80e40001, /* dp3 r1, r0, r1 */
6044 0x00000001, 0x800f0000, 0x80e40001, /* mov r0, r1 */
6045 0x00000001, 0x80070000, 0x80ff0001, /* mov r0.xyz, r1.a */
6046 0x40000050, 0x80080000, 0x80ff0000, 0xa0e40001, 0xa0e40002, /* +cnd r0.a, r0.a, c1, c2 */
6047 0x00000001, 0x80070000, 0x80ff0000, /* mov r0.xyz, r0.a */
6048 0x0000ffff /* end */
6050 static const DWORD shader_code_13_coissue[] =
6052 0xffff0103, /* ps_1_3 */
6053 0x00000051, 0xa00f0000, 0x3f800000, 0x00000000, 0x00000000, 0x00000000, /* def c0, 1, 0, 0, 0 */
6054 0x00000051, 0xa00f0003, 0x3f000000, 0x3f000000, 0x3f000000, 0x00000000, /* def c3, 0.5, 0.5, 0.5, 0 */
6055 0x00000040, 0xb00f0000, /* texcoord t0 */
6056 0x00000001, 0x800f0000, 0xb0e40000, /* mov r0, t0 */
6057 0x00000003, 0x800f0000, 0x80e40000, 0xa0e40003, /* sub r0, r0, c3 */
6058 0x00000002, 0x800f0001, 0xa0e40000, 0xa0e40000, /* add r1, c0, c0 */
6059 0x00000008, 0x800f0001, 0x80e40000, 0x80e40001, /* dp3 r1, r0, r1 */
6060 0x00000001, 0x80080000, 0x80ff0001, /* mov r0.a, r1.a */
6061 0x40000050, 0x80070000, 0x80ff0000, 0xa0e40001, 0xa0e40002, /* +cnd r0.xyz, r0.a, c1, c2*/
6062 0x0000ffff /* end */
6064 static const DWORD shader_code_13_coissue_2[] =
6066 0xffff0103, /* ps_1_3 */
6067 0x00000051, 0xa00f0000, 0x3f800000, 0x00000000, 0x00000000, 0x00000000, /* def c0, 1, 0, 0, 0 */
6068 0x00000051, 0xa00f0003, 0x3f000000, 0x3f000000, 0x3f000000, 0x00000000, /* def c3, 0.5, 0.5, 0.5, 0 */
6069 0x00000040, 0xb00f0000, /* texcoord t0 */
6070 0x00000001, 0x800f0000, 0xb0e40000, /* mov r0, t0 */
6071 0x00000003, 0x800f0000, 0x80e40000, 0xa0e40003, /* sub r0, r0, c3 */
6072 0x00000002, 0x800f0001, 0xa0e40000, 0xa0e40000, /* add r1, c0, c0 */
6073 0x00000008, 0x800f0001, 0x80e40000, 0x80e40001, /* dp3 r1, r0, r1 */
6074 0x00000001, 0x800f0000, 0x80e40001, /* mov r0, r1 */
6075 0x00000001, 0x80070000, 0x80ff0001, /* mov r0.xyz, r1.a */
6076 0x40000050, 0x80080000, 0x80ff0000, 0xa0e40001, 0xa0e40002, /* +cnd r0.a, r0.a, c1, c2 */
6077 0x00000001, 0x80070000, 0x80ff0000, /* mov r0.xyz, r0.a */
6078 0x0000ffff /* end */
6080 /* ps_1_4 does not have a different cnd behavior, just pass the [0;1]
6081 * texcrd result to cnd, it will compare against 0.5. */
6082 static const DWORD shader_code_14_coissue[] =
6084 0xffff0104, /* ps_1_4 */
6085 0x00000051, 0xa00f0000, 0x00000000, 0x00000000, 0x00000000, 0x3f800000, /* def c0, 0, 0, 0, 1 */
6086 0x00000040, 0x80070000, 0xb0e40000, /* texcrd r0.xyz, t0 */
6087 0x00000001, 0x80080000, 0xa0ff0000, /* mov r0.a, c0.a */
6088 0x40000050, 0x80070000, 0x80e40000, 0xa0e40001, 0xa0e40002, /* +cnd r0.xyz, r0, c1, c2 */
6089 0x0000ffff /* end */
6091 static const DWORD shader_code_14_coissue_2[] =
6093 0xffff0104, /* ps_1_4 */
6094 0x00000051, 0xa00f0000, 0x00000000, 0x00000000, 0x00000000, 0x3f800000, /* def c0, 0, 0, 0, 1 */
6095 0x00000040, 0x80070000, 0xb0e40000, /* texcrd r0.xyz, t0 */
6096 0x00000001, 0x80080000, 0x80000000, /* mov r0.a, r0.x */
6097 0x00000001, 0x80070001, 0xa0ff0000, /* mov r1.xyz, c0.a */
6098 0x40000050, 0x80080001, 0x80ff0000, 0xa0e40001, 0xa0e40002, /* +cnd r1.a, r0.a, c1, c2 */
6099 0x00000001, 0x80070000, 0x80ff0001, /* mov r0.xyz, r1.a */
6100 0x00000001, 0x80080000, 0xa0ff0000, /* mov r0.a, c0.a */
6101 0x0000ffff /* end */
6103 static const float quad1[] =
6105 -1.0f, -1.0f, 0.1f, 0.0f, 0.0f, 1.0f,
6106 -1.0f, 0.0f, 0.1f, 0.0f, 1.0f, 0.0f,
6107 0.0f, -1.0f, 0.1f, 1.0f, 0.0f, 1.0f,
6108 0.0f, 0.0f, 0.1f, 1.0f, 1.0f, 0.0f,
6110 static const float quad2[] =
6112 0.0f, -1.0f, 0.1f, 0.0f, 0.0f, 1.0f,
6113 0.0f, 0.0f, 0.1f, 0.0f, 1.0f, 0.0f,
6114 1.0f, -1.0f, 0.1f, 1.0f, 0.0f, 1.0f,
6115 1.0f, 0.0f, 0.1f, 1.0f, 1.0f, 0.0f,
6117 static const float quad3[] =
6119 0.0f, 0.0f, 0.1f, 0.0f, 0.0f, 1.0f,
6120 0.0f, 1.0f, 0.1f, 0.0f, 1.0f, 0.0f,
6121 1.0f, 0.0f, 0.1f, 1.0f, 0.0f, 1.0f,
6122 1.0f, 1.0f, 0.1f, 1.0f, 1.0f, 0.0f,
6124 static const float quad4[] =
6126 -1.0f, 0.0f, 0.1f, 0.0f, 0.0f, 1.0f,
6127 -1.0f, 1.0f, 0.1f, 0.0f, 1.0f, 0.0f,
6128 0.0f, 0.0f, 0.1f, 1.0f, 0.0f, 1.0f,
6129 0.0f, 1.0f, 0.1f, 1.0f, 1.0f, 0.0f,
6131 static const float test_data_c1[4] = {0.0f, 0.0f, 0.0f, 0.0f};
6132 static const float test_data_c2[4] = {1.0f, 1.0f, 1.0f, 1.0f};
6133 static const float test_data_c1_coi[4] = {0.0f, 1.0f, 0.0f, 0.0f};
6134 static const float test_data_c2_coi[4] = {1.0f, 0.0f, 1.0f, 1.0f};
6136 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
6137 0, 0, 640, 480, NULL, NULL, NULL, NULL);
6138 d3d = Direct3DCreate9(D3D_SDK_VERSION);
6139 ok(!!d3d, "Failed to create a D3D object.\n");
6140 if (!(device = create_device(d3d, window, window, TRUE)))
6142 skip("Failed to create a D3D device, skipping tests.\n");
6143 goto done;
6146 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
6147 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
6148 if (caps.PixelShaderVersion < D3DPS_VERSION(1, 4))
6150 skip("No ps_1_4 support, skipping tests.\n");
6151 IDirect3DDevice9_Release(device);
6152 goto done;
6155 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff00ffff, 1.0f, 0);
6156 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
6158 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code_11, &shader_11);
6159 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
6160 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code_12, &shader_12);
6161 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
6162 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code_13, &shader_13);
6163 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
6164 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code_14, &shader_14);
6165 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
6166 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code_11_coissue, &shader_11_coissue);
6167 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
6168 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code_12_coissue, &shader_12_coissue);
6169 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
6170 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code_13_coissue, &shader_13_coissue);
6171 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
6172 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code_14_coissue, &shader_14_coissue);
6173 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
6174 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code_11_coissue_2, &shader_11_coissue_2);
6175 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
6176 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code_12_coissue_2, &shader_12_coissue_2);
6177 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
6178 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code_13_coissue_2, &shader_13_coissue_2);
6179 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
6180 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code_14_coissue_2, &shader_14_coissue_2);
6181 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
6183 hr = IDirect3DDevice9_SetPixelShaderConstantF(device, 1, test_data_c1, 1);
6184 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShaderConstantF returned %08x\n", hr);
6185 hr = IDirect3DDevice9_SetPixelShaderConstantF(device, 2, test_data_c2, 1);
6186 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShaderConstantF returned %08x\n", hr);
6187 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1);
6188 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF returned %08x\n", hr);
6190 hr = IDirect3DDevice9_BeginScene(device);
6191 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
6193 hr = IDirect3DDevice9_SetPixelShader(device, shader_11);
6194 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
6195 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, 6 * sizeof(float));
6196 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
6198 hr = IDirect3DDevice9_SetPixelShader(device, shader_12);
6199 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
6200 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, 6 * sizeof(float));
6201 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
6203 hr = IDirect3DDevice9_SetPixelShader(device, shader_13);
6204 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
6205 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad3, 6 * sizeof(float));
6206 ok(hr == D3D_OK, "DrawPrimitiveUP failed (%08x)\n", hr);
6208 hr = IDirect3DDevice9_SetPixelShader(device, shader_14);
6209 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
6210 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad4, 6 * sizeof(float));
6211 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
6213 hr = IDirect3DDevice9_EndScene(device);
6214 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
6216 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
6217 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexShader returned %08x\n", hr);
6219 /* This is the 1.4 test. Each component(r, g, b) is tested separately against 0.5 */
6220 color = getPixelColor(device, 158, 118);
6221 ok(color == 0x00ff00ff, "pixel 158, 118 has color %08x, expected 0x00ff00ff\n", color);
6222 color = getPixelColor(device, 162, 118);
6223 ok(color == 0x000000ff, "pixel 162, 118 has color %08x, expected 0x000000ff\n", color);
6224 color = getPixelColor(device, 158, 122);
6225 ok(color == 0x00ffffff, "pixel 162, 122 has color %08x, expected 0x00ffffff\n", color);
6226 color = getPixelColor(device, 162, 122);
6227 ok(color == 0x0000ffff, "pixel 162, 122 has color %08x, expected 0x0000ffff\n", color);
6229 /* 1.1 shader. All 3 components get set, based on the .w comparison */
6230 color = getPixelColor(device, 158, 358);
6231 ok(color == 0x00ffffff, "pixel 158, 358 has color %08x, expected 0x00ffffff\n", color);
6232 color = getPixelColor(device, 162, 358);
6233 ok(color_match(color, 0x00000000, 1), "pixel 162, 358 has color 0x%08x, expected 0x00000000.\n", color);
6234 color = getPixelColor(device, 158, 362);
6235 ok(color == 0x00ffffff, "pixel 158, 362 has color %08x, expected 0x00ffffff\n", color);
6236 color = getPixelColor(device, 162, 362);
6237 ok(color_match(color, 0x00000000, 1), "pixel 162, 362 has color 0x%08x, expected 0x00000000.\n", color);
6239 /* 1.2 shader */
6240 color = getPixelColor(device, 478, 358);
6241 ok(color == 0x00ffffff, "pixel 478, 358 has color %08x, expected 0x00ffffff\n", color);
6242 color = getPixelColor(device, 482, 358);
6243 ok(color_match(color, 0x00000000, 1), "pixel 482, 358 has color 0x%08x, expected 0x00000000.\n", color);
6244 color = getPixelColor(device, 478, 362);
6245 ok(color == 0x00ffffff, "pixel 478, 362 has color %08x, expected 0x00ffffff\n", color);
6246 color = getPixelColor(device, 482, 362);
6247 ok(color_match(color, 0x00000000, 1), "pixel 482, 362 has color 0x%08x, expected 0x00000000.\n", color);
6249 /* 1.3 shader */
6250 color = getPixelColor(device, 478, 118);
6251 ok(color == 0x00ffffff, "pixel 478, 118 has color %08x, expected 0x00ffffff\n", color);
6252 color = getPixelColor(device, 482, 118);
6253 ok(color_match(color, 0x00000000, 1), "pixel 482, 118 has color 0x%08x, expected 0x00000000.\n", color);
6254 color = getPixelColor(device, 478, 122);
6255 ok(color == 0x00ffffff, "pixel 478, 122 has color %08x, expected 0x00ffffff\n", color);
6256 color = getPixelColor(device, 482, 122);
6257 ok(color_match(color, 0x00000000, 1), "pixel 482, 122 has color 0x%08x, expected 0x00000000.\n", color);
6259 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
6260 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
6262 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff00ffff, 0.0, 0);
6263 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
6264 hr = IDirect3DDevice9_SetPixelShaderConstantF(device, 1, test_data_c1_coi, 1);
6265 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShaderConstantF returned %08x\n", hr);
6266 hr = IDirect3DDevice9_SetPixelShaderConstantF(device, 2, test_data_c2_coi, 1);
6267 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShaderConstantF returned %08x\n", hr);
6269 hr = IDirect3DDevice9_BeginScene(device);
6270 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
6272 hr = IDirect3DDevice9_SetPixelShader(device, shader_11_coissue);
6273 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
6274 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, 6 * sizeof(float));
6275 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
6277 hr = IDirect3DDevice9_SetPixelShader(device, shader_12_coissue);
6278 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
6279 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, 6 * sizeof(float));
6280 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
6282 hr = IDirect3DDevice9_SetPixelShader(device, shader_13_coissue);
6283 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
6284 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad3, 6 * sizeof(float));
6285 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
6287 hr = IDirect3DDevice9_SetPixelShader(device, shader_14_coissue);
6288 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
6289 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad4, 6 * sizeof(float));
6290 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
6292 hr = IDirect3DDevice9_EndScene(device);
6293 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
6295 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
6296 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShader returned %08x\n", hr);
6298 /* This is the 1.4 test. The coissue doesn't change the behavior here, but keep in mind
6299 * that we swapped the values in c1 and c2 to make the other tests return some color
6301 color = getPixelColor(device, 158, 118);
6302 ok(color == 0x00ffffff, "pixel 158, 118 has color %08x, expected 0x00ffffff\n", color);
6303 color = getPixelColor(device, 162, 118);
6304 ok(color == 0x0000ffff, "pixel 162, 118 has color %08x, expected 0x0000ffff\n", color);
6305 color = getPixelColor(device, 158, 122);
6306 ok(color == 0x00ff00ff, "pixel 162, 122 has color %08x, expected 0x00ff00ff\n", color);
6307 color = getPixelColor(device, 162, 122);
6308 ok(color == 0x000000ff, "pixel 162, 122 has color %08x, expected 0x000000ff\n", color);
6310 /* 1.1 shader. coissue flag changed the semantic of cnd, c1 is always selected
6311 * (The Win7 nvidia driver always selects c2)
6313 color = getPixelColor(device, 158, 358);
6314 ok(color_match(color, 0x0000ff00, 1) || broken(color_match(color, 0x00ff00ff, 1)),
6315 "pixel 158, 358 has color %08x, expected 0x0000ff00\n", color);
6316 color = getPixelColor(device, 162, 358);
6317 ok(color_match(color, 0x0000ff00, 1) || broken(color_match(color, 0x00ff00ff, 1)),
6318 "pixel 162, 358 has color %08x, expected 0x0000ff00\n", color);
6319 color = getPixelColor(device, 158, 362);
6320 ok(color_match(color, 0x0000ff00, 1) || broken(color_match(color, 0x00ff00ff, 1)),
6321 "pixel 158, 362 has color %08x, expected 0x0000ff00\n", color);
6322 color = getPixelColor(device, 162, 362);
6323 ok(color_match(color, 0x0000ff00, 1) || broken(color_match(color, 0x00ff00ff, 1)),
6324 "pixel 162, 362 has color %08x, expected 0x0000ff00\n", color);
6326 /* 1.2 shader */
6327 color = getPixelColor(device, 478, 358);
6328 ok(color_match(color, 0x0000ff00, 1) || broken(color_match(color, 0x00ff00ff, 1)),
6329 "pixel 478, 358 has color %08x, expected 0x0000ff00\n", color);
6330 color = getPixelColor(device, 482, 358);
6331 ok(color_match(color, 0x0000ff00, 1) || broken(color_match(color, 0x00ff00ff, 1)),
6332 "pixel 482, 358 has color %08x, expected 0x0000ff00\n", color);
6333 color = getPixelColor(device, 478, 362);
6334 ok(color_match(color, 0x0000ff00, 1) || broken(color_match(color, 0x00ff00ff, 1)),
6335 "pixel 478, 362 has color %08x, expected 0x0000ff00\n", color);
6336 color = getPixelColor(device, 482, 362);
6337 ok(color_match(color, 0x0000ff00, 1) || broken(color_match(color, 0x00ff00ff, 1)),
6338 "pixel 482, 362 has color %08x, expected 0x0000ff00\n", color);
6340 /* 1.3 shader */
6341 color = getPixelColor(device, 478, 118);
6342 ok(color_match(color, 0x0000ff00, 1) || broken(color_match(color, 0x00ff00ff, 1)),
6343 "pixel 478, 118 has color %08x, expected 0x0000ff00\n", color);
6344 color = getPixelColor(device, 482, 118);
6345 ok(color_match(color, 0x0000ff00, 1) || broken(color_match(color, 0x00ff00ff, 1)),
6346 "pixel 482, 118 has color %08x, expected 0x0000ff00\n", color);
6347 color = getPixelColor(device, 478, 122);
6348 ok(color_match(color, 0x0000ff00, 1) || broken(color_match(color, 0x00ff00ff, 1)),
6349 "pixel 478, 122 has color %08x, expected 0x0000ff00\n", color);
6350 color = getPixelColor(device, 482, 122);
6351 ok(color_match(color, 0x0000ff00, 1) || broken(color_match(color, 0x00ff00ff, 1)),
6352 "pixel 482, 122 has color %08x, expected 0x0000ff00\n", color);
6354 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
6355 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
6357 /* Retest with the coissue flag on the alpha instruction instead. This
6358 * works "as expected". The Windows 8 testbot (WARP) seems to handle this
6359 * the same as coissue on .rgb. */
6360 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff00ffff, 0.0, 0);
6361 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
6363 hr = IDirect3DDevice9_BeginScene(device);
6364 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
6366 hr = IDirect3DDevice9_SetPixelShader(device, shader_11_coissue_2);
6367 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
6368 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, 6 * sizeof(float));
6369 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
6371 hr = IDirect3DDevice9_SetPixelShader(device, shader_12_coissue_2);
6372 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
6373 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, 6 * sizeof(float));
6374 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
6376 hr = IDirect3DDevice9_SetPixelShader(device, shader_13_coissue_2);
6377 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
6378 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad3, 6 * sizeof(float));
6379 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
6381 hr = IDirect3DDevice9_SetPixelShader(device, shader_14_coissue_2);
6382 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
6383 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad4, 6 * sizeof(float));
6384 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
6386 hr = IDirect3DDevice9_EndScene(device);
6387 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
6389 /* 1.4 shader */
6390 color = getPixelColor(device, 158, 118);
6391 ok(color == 0x00ffffff, "pixel 158, 118 has color %08x, expected 0x00ffffff\n", color);
6392 color = getPixelColor(device, 162, 118);
6393 ok(color == 0x00000000, "pixel 162, 118 has color %08x, expected 0x00000000\n", color);
6394 color = getPixelColor(device, 158, 122);
6395 ok(color == 0x00ffffff, "pixel 162, 122 has color %08x, expected 0x00ffffff\n", color);
6396 color = getPixelColor(device, 162, 122);
6397 ok(color == 0x00000000, "pixel 162, 122 has color %08x, expected 0x00000000\n", color);
6399 /* 1.1 shader */
6400 color = getPixelColor(device, 238, 358);
6401 ok(color_match(color, 0x00ffffff, 1) || broken(color_match(color, 0x00000000, 1)),
6402 "pixel 238, 358 has color %08x, expected 0x00ffffff\n", color);
6403 color = getPixelColor(device, 242, 358);
6404 ok(color_match(color, 0x00000000, 1),
6405 "pixel 242, 358 has color %08x, expected 0x00000000\n", color);
6406 color = getPixelColor(device, 238, 362);
6407 ok(color_match(color, 0x00ffffff, 1) || broken(color_match(color, 0x00000000, 1)),
6408 "pixel 238, 362 has color %08x, expected 0x00ffffff\n", color);
6409 color = getPixelColor(device, 242, 362);
6410 ok(color_match(color, 0x00000000, 1),
6411 "pixel 242, 362 has color %08x, expected 0x00000000\n", color);
6413 /* 1.2 shader */
6414 color = getPixelColor(device, 558, 358);
6415 ok(color_match(color, 0x00ffffff, 1) || broken(color_match(color, 0x00000000, 1)),
6416 "pixel 558, 358 has color %08x, expected 0x00ffffff\n", color);
6417 color = getPixelColor(device, 562, 358);
6418 ok(color_match(color, 0x00000000, 1),
6419 "pixel 562, 358 has color %08x, expected 0x00000000\n", color);
6420 color = getPixelColor(device, 558, 362);
6421 ok(color_match(color, 0x00ffffff, 1) || broken(color_match(color, 0x00000000, 1)),
6422 "pixel 558, 362 has color %08x, expected 0x00ffffff\n", color);
6423 color = getPixelColor(device, 562, 362);
6424 ok(color_match(color, 0x00000000, 1),
6425 "pixel 562, 362 has color %08x, expected 0x00000000\n", color);
6427 /* 1.3 shader */
6428 color = getPixelColor(device, 558, 118);
6429 ok(color_match(color, 0x00ffffff, 1) || broken(color_match(color, 0x00000000, 1)),
6430 "pixel 558, 118 has color %08x, expected 0x00ffffff\n", color);
6431 color = getPixelColor(device, 562, 118);
6432 ok(color_match(color, 0x00000000, 1),
6433 "pixel 562, 118 has color %08x, expected 0x00000000\n", color);
6434 color = getPixelColor(device, 558, 122);
6435 ok(color_match(color, 0x00ffffff, 1) || broken(color_match(color, 0x00000000, 1)),
6436 "pixel 558, 122 has color %08x, expected 0x00ffffff\n", color);
6437 color = getPixelColor(device, 562, 122);
6438 ok(color_match(color, 0x00000000, 1),
6439 "pixel 562, 122 has color %08x, expected 0x00000000\n", color);
6441 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
6442 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
6444 IDirect3DPixelShader9_Release(shader_14_coissue_2);
6445 IDirect3DPixelShader9_Release(shader_13_coissue_2);
6446 IDirect3DPixelShader9_Release(shader_12_coissue_2);
6447 IDirect3DPixelShader9_Release(shader_11_coissue_2);
6448 IDirect3DPixelShader9_Release(shader_14_coissue);
6449 IDirect3DPixelShader9_Release(shader_13_coissue);
6450 IDirect3DPixelShader9_Release(shader_12_coissue);
6451 IDirect3DPixelShader9_Release(shader_11_coissue);
6452 IDirect3DPixelShader9_Release(shader_14);
6453 IDirect3DPixelShader9_Release(shader_13);
6454 IDirect3DPixelShader9_Release(shader_12);
6455 IDirect3DPixelShader9_Release(shader_11);
6456 refcount = IDirect3DDevice9_Release(device);
6457 ok(!refcount, "Device has %u references left.\n", refcount);
6458 done:
6459 IDirect3D9_Release(d3d);
6460 DestroyWindow(window);
6463 static void nested_loop_test(void)
6465 IDirect3DVertexShader9 *vshader;
6466 IDirect3DPixelShader9 *shader;
6467 IDirect3DDevice9 *device;
6468 IDirect3D9 *d3d;
6469 ULONG refcount;
6470 D3DCAPS9 caps;
6471 DWORD color;
6472 HWND window;
6473 HRESULT hr;
6475 static const DWORD shader_code[] =
6477 0xffff0300, /* ps_3_0 */
6478 0x05000051, 0xa00f0000, 0x00000000, 0x00000000, 0x00000000, 0x3f800000, /* def c0, 0, 0, 0, 1 */
6479 0x05000051, 0xa00f0001, 0x3d000000, 0x00000000, 0x00000000, 0x00000000, /* def c1, 1/32, 0, 0, 0*/
6480 0x05000030, 0xf00f0000, 0x00000004, 0x00000000, 0x00000002, 0x00000000, /* defi i0, 4, 0, 2, 0 */
6481 0x02000001, 0x800f0000, 0xa0e40000, /* mov r0, c0 */
6482 0x0200001b, 0xf0e40800, 0xf0e40000, /* loop aL, i0 */
6483 0x0200001b, 0xf0e40800, 0xf0e40000, /* loop aL, i0 */
6484 0x03000002, 0x800f0000, 0x80e40000, 0xa0e40001, /* add r0, r0, c1 */
6485 0x0000001d, /* endloop */
6486 0x0000001d, /* endloop */
6487 0x02000001, 0x800f0800, 0x80e40000, /* mov oC0, r0 */
6488 0x0000ffff /* end */
6490 static const DWORD vshader_code[] =
6492 0xfffe0300, /* vs_3_0 */
6493 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
6494 0x0200001f, 0x80000000, 0xe00f0000, /* dcl_position o0 */
6495 0x02000001, 0xe00f0000, 0x90e40000, /* mov o0, v0 */
6496 0x0000ffff /* end */
6498 static const float quad[] =
6500 -1.0f, -1.0f, 0.1f,
6501 -1.0f, 1.0f, 0.1f,
6502 1.0f, -1.0f, 0.1f,
6503 1.0f, 1.0f, 0.1f,
6506 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
6507 0, 0, 640, 480, NULL, NULL, NULL, NULL);
6508 d3d = Direct3DCreate9(D3D_SDK_VERSION);
6509 ok(!!d3d, "Failed to create a D3D object.\n");
6510 if (!(device = create_device(d3d, window, window, TRUE)))
6512 skip("Failed to create a D3D device, skipping tests.\n");
6513 goto done;
6516 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
6517 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
6518 if (caps.PixelShaderVersion < D3DPS_VERSION(3, 0) || caps.VertexShaderVersion < D3DVS_VERSION(3, 0))
6520 skip("No shader model 3 support, skipping tests.\n");
6521 IDirect3DDevice9_Release(device);
6522 goto done;
6525 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code, &shader);
6526 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader failed with %08x\n", hr);
6527 hr = IDirect3DDevice9_SetPixelShader(device, shader);
6528 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShader failed with %08x\n", hr);
6529 hr = IDirect3DDevice9_CreateVertexShader(device, vshader_code, &vshader);
6530 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader failed with %08x\n", hr);
6531 hr = IDirect3DDevice9_SetVertexShader(device, vshader);
6532 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexShader failed with %08x\n", hr);
6533 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ);
6534 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed with %08x\n", hr);
6535 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x0000ff00, 1.0f, 0);
6536 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
6538 hr = IDirect3DDevice9_BeginScene(device);
6539 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
6540 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, 3 * sizeof(float));
6541 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
6542 hr = IDirect3DDevice9_EndScene(device);
6543 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
6545 color = getPixelColor(device, 360, 240);
6546 ok(color_match(color, 0x00800000, 1),
6547 "Nested loop test returned color 0x%08x, expected 0x00800000.\n", color);
6549 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
6550 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
6552 IDirect3DPixelShader9_Release(shader);
6553 IDirect3DVertexShader9_Release(vshader);
6554 refcount = IDirect3DDevice9_Release(device);
6555 ok(!refcount, "Device has %u references left.\n", refcount);
6556 done:
6557 IDirect3D9_Release(d3d);
6558 DestroyWindow(window);
6561 static void pretransformed_varying_test(void)
6563 /* dcl_position: fails to compile */
6564 static const DWORD blendweight_code[] =
6566 0xffff0300, /* ps_3_0 */
6567 0x0200001f, 0x80000001, 0x900f0000, /* dcl_blendweight, v0 */
6568 0x02000001, 0x800f0800, 0x90e40000, /* mov oC0, v0 */
6569 0x0000ffff /* end */
6571 static const DWORD blendindices_code[] =
6573 0xffff0300, /* ps_3_0 */
6574 0x0200001f, 0x80000002, 0x900f0000, /* dcl_blendindices, v0 */
6575 0x02000001, 0x800f0800, 0x90e40000, /* mov oC0, v0 */
6576 0x0000ffff /* end */
6578 static const DWORD normal_code[] =
6580 0xffff0300, /* ps_3_0 */
6581 0x0200001f, 0x80000003, 0x900f0000, /* dcl_normal, v0 */
6582 0x02000001, 0x800f0800, 0x90e40000, /* mov oC0, v0 */
6583 0x0000ffff /* end */
6585 /* psize: fails? */
6586 static const DWORD texcoord0_code[] =
6588 0xffff0300, /* ps_3_0 */
6589 0x0200001f, 0x80000005, 0x900f0000, /* dcl_texcoord0, v0 */
6590 0x02000001, 0x800f0800, 0x90e40000, /* mov oC0, v0 */
6591 0x0000ffff /* end */
6593 static const DWORD tangent_code[] =
6595 0xffff0300, /* ps_3_0 */
6596 0x0200001f, 0x80000006, 0x900f0000, /* dcl_tangent, v0 */
6597 0x02000001, 0x800f0800, 0x90e40000, /* mov oC0, v0 */
6598 0x0000ffff /* end */
6600 static const DWORD binormal_code[] =
6602 0xffff0300, /* ps_3_0 */
6603 0x0200001f, 0x80000007, 0x900f0000, /* dcl_binormal, v0 */
6604 0x02000001, 0x800f0800, 0x90e40000, /* mov oC0, v0 */
6605 0x0000ffff /* end */
6607 /* tessfactor: fails */
6608 /* positiont: fails */
6609 static const DWORD color_code[] =
6611 0xffff0300, /* ps_3_0 */
6612 0x0200001f, 0x8000000a, 0x900f0000, /* dcl_color0, v0 */
6613 0x02000001, 0x800f0800, 0x90e40000, /* mov oC0, v0 */
6614 0x0000ffff /* end */
6616 static const DWORD fog_code[] =
6618 0xffff0300, /* ps_3_0 */
6619 0x0200001f, 0x8000000b, 0x900f0000, /* dcl_fog, v0 */
6620 0x02000001, 0x800f0800, 0x90e40000, /* mov oC0, v0 */
6621 0x0000ffff /* end */
6623 static const DWORD depth_code[] =
6625 0xffff0300, /* ps_3_0 */
6626 0x0200001f, 0x8000000c, 0x900f0000, /* dcl_depth, v0 */
6627 0x02000001, 0x800f0800, 0x90e40000, /* mov oC0, v0 */
6628 0x0000ffff /* end */
6630 static const DWORD specular_code[] =
6632 0xffff0300, /* ps_3_0 */
6633 0x0200001f, 0x8001000a, 0x900f0000, /* dcl_color1, v0 */
6634 0x02000001, 0x800f0800, 0x90e40000, /* mov oC0, v0 */
6635 0x0000ffff /* end */
6637 /* sample: fails */
6639 static const struct
6641 const char *name;
6642 const DWORD *shader_code;
6643 DWORD color;
6644 BOOL todo;
6646 tests[] =
6648 {"blendweight", blendweight_code, 0x00191919, TRUE },
6649 {"blendindices", blendindices_code, 0x00333333, TRUE },
6650 {"normal", normal_code, 0x004c4c4c, TRUE },
6651 {"texcoord0", texcoord0_code, 0x00808c8c, FALSE},
6652 {"tangent", tangent_code, 0x00999999, TRUE },
6653 {"binormal", binormal_code, 0x00b2b2b2, TRUE },
6654 {"color", color_code, 0x00e6e6e6, FALSE},
6655 {"fog", fog_code, 0x00666666, TRUE },
6656 {"depth", depth_code, 0x00cccccc, TRUE },
6657 {"specular", specular_code, 0x004488ff, FALSE},
6659 /* Declare a monster vertex type :-) */
6660 static const D3DVERTEXELEMENT9 decl_elements[] = {
6661 {0, 0, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITIONT, 0},
6662 {0, 16, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_BLENDWEIGHT, 0},
6663 {0, 32, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_BLENDINDICES, 0},
6664 {0, 48, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_NORMAL, 0},
6665 {0, 64, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_FOG, 0},
6666 {0, 80, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
6667 {0, 96, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TANGENT, 0},
6668 {0, 112, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_BINORMAL, 0},
6669 {0, 128, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_DEPTH, 0},
6670 {0, 144, D3DDECLTYPE_D3DCOLOR, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR, 0},
6671 {0, 148, D3DDECLTYPE_D3DCOLOR, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR, 1},
6672 D3DDECL_END()
6675 static const struct
6677 float pos_x, pos_y, pos_z, rhw;
6678 float weight_1, weight_2, weight_3, weight_4;
6679 float index_1, index_2, index_3, index_4;
6680 float normal_1, normal_2, normal_3, normal_4;
6681 float fog_1, fog_2, fog_3, fog_4;
6682 float texcoord_1, texcoord_2, texcoord_3, texcoord_4;
6683 float tangent_1, tangent_2, tangent_3, tangent_4;
6684 float binormal_1, binormal_2, binormal_3, binormal_4;
6685 float depth_1, depth_2, depth_3, depth_4;
6686 D3DCOLOR diffuse;
6687 D3DCOLOR specular;
6689 data[] =
6692 0.0f, 0.0f, 0.1f, 1.0f,
6693 0.1f, 0.1f, 0.1f, 0.1f,
6694 0.2f, 0.2f, 0.2f, 0.2f,
6695 0.3f, 0.3f, 0.3f, 0.3f,
6696 0.4f, 0.4f, 0.4f, 0.4f,
6697 0.5f, 0.55f, 0.55f, 0.55f,
6698 0.6f, 0.6f, 0.6f, 0.7f,
6699 0.7f, 0.7f, 0.7f, 0.6f,
6700 0.8f, 0.8f, 0.8f, 0.8f,
6701 0xe6e6e6e6, /* 0.9 * 256 */
6702 0x224488ff, /* Nothing special */
6705 640.0f, 0.0f, 0.1f, 1.0f,
6706 0.1f, 0.1f, 0.1f, 0.1f,
6707 0.2f, 0.2f, 0.2f, 0.2f,
6708 0.3f, 0.3f, 0.3f, 0.3f,
6709 0.4f, 0.4f, 0.4f, 0.4f,
6710 0.5f, 0.55f, 0.55f, 0.55f,
6711 0.6f, 0.6f, 0.6f, 0.7f,
6712 0.7f, 0.7f, 0.7f, 0.6f,
6713 0.8f, 0.8f, 0.8f, 0.8f,
6714 0xe6e6e6e6, /* 0.9 * 256 */
6715 0x224488ff, /* Nothing special */
6718 0.0f, 480.0f, 0.1f, 1.0f,
6719 0.1f, 0.1f, 0.1f, 0.1f,
6720 0.2f, 0.2f, 0.2f, 0.2f,
6721 0.3f, 0.3f, 0.3f, 0.3f,
6722 0.4f, 0.4f, 0.4f, 0.4f,
6723 0.5f, 0.55f, 0.55f, 0.55f,
6724 0.6f, 0.6f, 0.6f, 0.7f,
6725 0.7f, 0.7f, 0.7f, 0.6f,
6726 0.8f, 0.8f, 0.8f, 0.8f,
6727 0xe6e6e6e6, /* 0.9 * 256 */
6728 0x224488ff, /* Nothing special */
6731 640.0f, 480.0f, 0.1f, 1.0f,
6732 0.1f, 0.1f, 0.1f, 0.1f,
6733 0.2f, 0.2f, 0.2f, 0.2f,
6734 0.3f, 0.3f, 0.3f, 0.3f,
6735 0.4f, 0.4f, 0.4f, 0.4f,
6736 0.5f, 0.55f, 0.55f, 0.55f,
6737 0.6f, 0.6f, 0.6f, 0.7f,
6738 0.7f, 0.7f, 0.7f, 0.6f,
6739 0.8f, 0.8f, 0.8f, 0.8f,
6740 0xe6e6e6e6, /* 0.9 * 256 */
6741 0x224488ff, /* Nothing special */
6744 IDirect3DVertexDeclaration9 *decl;
6745 IDirect3DDevice9 *device;
6746 IDirect3D9 *d3d;
6747 unsigned int i;
6748 ULONG refcount;
6749 D3DCAPS9 caps;
6750 DWORD color;
6751 HWND window;
6752 HRESULT hr;
6754 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
6755 0, 0, 640, 480, NULL, NULL, NULL, NULL);
6756 d3d = Direct3DCreate9(D3D_SDK_VERSION);
6757 ok(!!d3d, "Failed to create a D3D object.\n");
6758 if (!(device = create_device(d3d, window, window, TRUE)))
6760 skip("Failed to create a D3D device, skipping tests.\n");
6761 goto done;
6764 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
6765 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
6766 if (caps.PixelShaderVersion < D3DPS_VERSION(3, 0) || caps.VertexShaderVersion < D3DVS_VERSION(3, 0))
6768 skip("No shader model 3 support, skipping tests.\n");
6769 IDirect3DDevice9_Release(device);
6770 goto done;
6773 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements, &decl);
6774 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexDeclaration returned %08x\n", hr);
6775 hr = IDirect3DDevice9_SetVertexDeclaration(device, decl);
6776 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexDeclaration returned %08x\n", hr);
6778 hr = IDirect3DDevice9_SetVertexDeclaration(device, decl);
6779 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexDeclaration returned %08x\n", hr);
6780 for (i = 0; i < sizeof(tests) / sizeof(*tests); ++i)
6782 IDirect3DPixelShader9 *shader;
6784 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffffffff, 1.0f, 0);
6785 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
6787 hr = IDirect3DDevice9_CreatePixelShader(device, tests[i].shader_code, &shader);
6788 ok(SUCCEEDED(hr), "Failed to create pixel shader for test %s, hr %#x.\n", tests[i].name, hr);
6790 hr = IDirect3DDevice9_SetPixelShader(device, shader);
6791 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShader returned %08x\n", hr);
6793 hr = IDirect3DDevice9_BeginScene(device);
6794 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
6795 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, data, sizeof(*data));
6796 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
6797 hr = IDirect3DDevice9_EndScene(device);
6798 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
6800 /* This isn't a weekend's job to fix, ignore the problem for now.
6801 * Needs a replacement pipeline. */
6802 color = getPixelColor(device, 360, 240);
6803 if (tests[i].todo)
6804 todo_wine ok(color_match(color, tests[i].color, 1)
6805 || broken(color_match(color, 0x00000000, 1)
6806 && tests[i].shader_code == blendindices_code),
6807 "Test %s returned color 0x%08x, expected 0x%08x (todo).\n",
6808 tests[i].name, color, tests[i].color);
6809 else
6810 ok(color_match(color, tests[i].color, 1),
6811 "Test %s returned color 0x%08x, expected 0x%08x.\n",
6812 tests[i].name, color, tests[i].color);
6814 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
6815 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
6817 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
6818 ok(SUCCEEDED(hr), "Failed to set pixel shader for test %s, hr %#x.\n", tests[i].name, hr);
6819 IDirect3DPixelShader9_Release(shader);
6822 IDirect3DVertexDeclaration9_Release(decl);
6823 refcount = IDirect3DDevice9_Release(device);
6824 ok(!refcount, "Device has %u references left.\n", refcount);
6825 done:
6826 IDirect3D9_Release(d3d);
6827 DestroyWindow(window);
6830 static void test_compare_instructions(void)
6832 IDirect3DVertexShader9 *shader_slt_scalar;
6833 IDirect3DVertexShader9 *shader_sge_scalar;
6834 IDirect3DVertexShader9 *shader_slt_vec;
6835 IDirect3DVertexShader9 *shader_sge_vec;
6836 IDirect3DDevice9 *device;
6837 IDirect3D9 *d3d;
6838 D3DCOLOR color;
6839 ULONG refcount;
6840 D3DCAPS9 caps;
6841 HWND window;
6842 HRESULT hr;
6844 static const DWORD shader_sge_vec_code[] =
6846 0xfffe0101, /* vs_1_1 */
6847 0x0000001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
6848 0x00000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
6849 0x00000001, 0x800f0000, 0xa0e40000, /* mov r0, c0 */
6850 0x0000000d, 0xd00f0000, 0x80e40000, 0xa0e40001, /* sge oD0, r0, c1 */
6851 0x0000ffff /* end */
6853 static const DWORD shader_slt_vec_code[] =
6855 0xfffe0101, /* vs_1_1 */
6856 0x0000001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
6857 0x00000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
6858 0x00000001, 0x800f0000, 0xa0e40000, /* mov r0, c0 */
6859 0x0000000c, 0xd00f0000, 0x80e40000, 0xa0e40001, /* slt oD0, r0, c1 */
6860 0x0000ffff /* end */
6862 static const DWORD shader_sge_scalar_code[] =
6864 0xfffe0101, /* vs_1_1 */
6865 0x0000001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
6866 0x00000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
6867 0x00000001, 0x800f0000, 0xa0e40000, /* mov r0, c0 */
6868 0x0000000d, 0xd0010000, 0x80000000, 0xa0550001, /* slt oD0.r, r0.r, c1.b */
6869 0x0000000d, 0xd0020000, 0x80550000, 0xa0aa0001, /* slt oD0.g, r0.g, c1.r */
6870 0x0000000d, 0xd0040000, 0x80aa0000, 0xa0000001, /* slt oD0.b, r0.b, c1.g */
6871 0x0000ffff /* end */
6873 static const DWORD shader_slt_scalar_code[] =
6875 0xfffe0101, /* vs_1_1 */
6876 0x0000001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
6877 0x00000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
6878 0x00000001, 0x800f0000, 0xa0e40000, /* mov r0, c0 */
6879 0x0000000c, 0xd0010000, 0x80000000, 0xa0aa0001, /* slt oD0.r, r0.r, c1.b */
6880 0x0000000c, 0xd0020000, 0x80550000, 0xa0000001, /* slt oD0.g, r0.g, c1.r */
6881 0x0000000c, 0xd0040000, 0x80aa0000, 0xa0550001, /* slt oD0.b, r0.b, c1.g */
6882 0x0000ffff /* end */
6884 static const float quad1[] =
6886 -1.0f, -1.0f, 0.1f,
6887 -1.0f, 0.0f, 0.1f,
6888 0.0f, -1.0f, 0.1f,
6889 0.0f, 0.0f, 0.1f,
6891 static const float quad2[] =
6893 0.0f, -1.0f, 0.1f,
6894 0.0f, 0.0f, 0.1f,
6895 1.0f, -1.0f, 0.1f,
6896 1.0f, 0.0f, 0.1f,
6898 static const float quad3[] =
6900 -1.0f, 0.0f, 0.1f,
6901 -1.0f, 1.0f, 0.1f,
6902 0.0f, 0.0f, 0.1f,
6903 0.0f, 1.0f, 0.1f,
6905 static const float quad4[] =
6907 0.0f, 0.0f, 0.1f,
6908 0.0f, 1.0f, 0.1f,
6909 1.0f, 0.0f, 0.1f,
6910 1.0f, 1.0f, 0.1f,
6912 static const float const0[4] = {0.8f, 0.2f, 0.2f, 0.2f};
6913 static const float const1[4] = {0.2f, 0.8f, 0.2f, 0.2f};
6915 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
6916 0, 0, 640, 480, NULL, NULL, NULL, NULL);
6917 d3d = Direct3DCreate9(D3D_SDK_VERSION);
6918 ok(!!d3d, "Failed to create a D3D object.\n");
6919 if (!(device = create_device(d3d, window, window, TRUE)))
6921 skip("Failed to create a D3D device, skipping tests.\n");
6922 goto done;
6925 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
6926 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
6927 if (caps.VertexShaderVersion < D3DVS_VERSION(1, 1))
6929 skip("No vs_1_1 support, skipping tests.\n");
6930 IDirect3DDevice9_Release(device);
6931 goto done;
6934 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffffffff, 1.0f, 0);
6935 ok(SUCCEEDED(hr), "IDirect3DDevice9_Clear returned %#x.\n", hr);
6937 hr = IDirect3DDevice9_CreateVertexShader(device, shader_sge_vec_code, &shader_sge_vec);
6938 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader returned %08x\n", hr);
6939 hr = IDirect3DDevice9_CreateVertexShader(device, shader_slt_vec_code, &shader_slt_vec);
6940 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader returned %08x\n", hr);
6941 hr = IDirect3DDevice9_CreateVertexShader(device, shader_sge_scalar_code, &shader_sge_scalar);
6942 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader returned %08x\n", hr);
6943 hr = IDirect3DDevice9_CreateVertexShader(device, shader_slt_scalar_code, &shader_slt_scalar);
6944 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader returned %08x\n", hr);
6945 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 0, const0, 1);
6946 ok(SUCCEEDED(hr), "SetVertexShaderConstantF failed (%08x)\n", hr);
6947 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 1, const1, 1);
6948 ok(SUCCEEDED(hr), "SetVertexShaderConstantF failed (%08x)\n", hr);
6949 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ);
6950 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetFVF failed (%08x)\n", hr);
6952 hr = IDirect3DDevice9_BeginScene(device);
6953 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
6955 hr = IDirect3DDevice9_SetVertexShader(device, shader_sge_vec);
6956 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
6957 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, sizeof(float) * 3);
6958 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
6960 hr = IDirect3DDevice9_SetVertexShader(device, shader_slt_vec);
6961 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
6962 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, sizeof(float) * 3);
6963 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
6965 hr = IDirect3DDevice9_SetVertexShader(device, shader_sge_scalar);
6966 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
6967 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad3, sizeof(float) * 3);
6968 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
6970 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 0, const0, 1);
6971 ok(SUCCEEDED(hr), "Failed to set vertex shader constant, hr %#x.\n", hr);
6973 hr = IDirect3DDevice9_SetVertexShader(device, shader_slt_scalar);
6974 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
6975 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad4, sizeof(float) * 3);
6976 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
6978 hr = IDirect3DDevice9_EndScene(device);
6979 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
6981 color = getPixelColor(device, 160, 360);
6982 ok(color == 0x00ff00ff, "Compare test: Quad 1(sge vec) returned color 0x%08x, expected 0x00ff00ff\n", color);
6983 color = getPixelColor(device, 480, 360);
6984 ok(color == 0x0000ff00, "Compare test: Quad 2(slt vec) returned color 0x%08x, expected 0x0000ff00\n", color);
6985 color = getPixelColor(device, 160, 120);
6986 ok(color == 0x00ffffff, "Compare test: Quad 3(sge scalar) returned color 0x%08x, expected 0x00ffffff\n", color);
6987 color = getPixelColor(device, 480, 160);
6988 ok(color == 0x000000ff, "Compare test: Quad 4(slt scalar) returned color 0x%08x, expected 0x000000ff\n", color);
6990 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
6991 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
6993 IDirect3DVertexShader9_Release(shader_sge_vec);
6994 IDirect3DVertexShader9_Release(shader_slt_vec);
6995 IDirect3DVertexShader9_Release(shader_sge_scalar);
6996 IDirect3DVertexShader9_Release(shader_slt_scalar);
6997 refcount = IDirect3DDevice9_Release(device);
6998 ok(!refcount, "Device has %u references left.\n", refcount);
6999 done:
7000 IDirect3D9_Release(d3d);
7001 DestroyWindow(window);
7004 static void test_vshader_input(void)
7006 IDirect3DVertexDeclaration9 *decl_twotexcrd, *decl_onetexcrd, *decl_twotex_wrongidx, *decl_twotexcrd_rightorder;
7007 IDirect3DVertexDeclaration9 *decl_texcoord_color, *decl_color_color, *decl_color_ubyte, *decl_color_float;
7008 IDirect3DVertexShader9 *swapped_shader, *texcoord_color_shader, *color_color_shader;
7009 D3DADAPTER_IDENTIFIER9 identifier;
7010 IDirect3DPixelShader9 *ps;
7011 IDirect3DDevice9 *device;
7012 IDirect3D9 *d3d;
7013 ULONG refcount;
7014 unsigned int i;
7015 D3DCAPS9 caps;
7016 DWORD color;
7017 HWND window;
7018 HRESULT hr;
7019 BOOL warp;
7021 static const DWORD swapped_shader_code_3[] =
7023 0xfffe0300, /* vs_3_0 */
7024 0x0200001f, 0x80000000, 0xe00f0000, /* dcl_position o0 */
7025 0x0200001f, 0x8000000a, 0xe00f0001, /* dcl_color o1 */
7026 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
7027 0x0200001f, 0x80000005, 0x900f0001, /* dcl_texcoord0 v1 */
7028 0x0200001f, 0x80010005, 0x900f0002, /* dcl_texcoord1 v2 */
7029 0x02000001, 0xe00f0000, 0x90e40000, /* mov o0, v0 */
7030 0x02000001, 0x800f0001, 0x90e40001, /* mov r1, v1 */
7031 0x03000002, 0xe00f0001, 0x80e40001, 0x91e40002, /* sub o1, r1, v2 */
7032 0x0000ffff /* end */
7034 static const DWORD swapped_shader_code_1[] =
7036 0xfffe0101, /* vs_1_1 */
7037 0x0000001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
7038 0x0000001f, 0x80000005, 0x900f0001, /* dcl_texcoord0 v1 */
7039 0x0000001f, 0x80010005, 0x900f0002, /* dcl_texcoord1 v2 */
7040 0x00000001, 0xc00f0000, 0x90e40000, /* mov o0, v0 */
7041 0x00000001, 0x800f0001, 0x90e40001, /* mov r1, v1 */
7042 0x00000002, 0xd00f0000, 0x80e40001, 0x91e40002, /* sub o1, r1, v2 */
7043 0x0000ffff /* end */
7045 static const DWORD swapped_shader_code_2[] =
7047 0xfffe0200, /* vs_2_0 */
7048 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
7049 0x0200001f, 0x80000005, 0x900f0001, /* dcl_texcoord0 v1 */
7050 0x0200001f, 0x80010005, 0x900f0002, /* dcl_texcoord1 v2 */
7051 0x02000001, 0xc00f0000, 0x90e40000, /* mov o0, v0 */
7052 0x02000001, 0x800f0001, 0x90e40001, /* mov r1, v1 */
7053 0x03000002, 0xd00f0000, 0x80e40001, 0x91e40002, /* sub o1, r1, v2 */
7054 0x0000ffff /* end */
7056 static const DWORD texcoord_color_shader_code_3[] =
7058 0xfffe0300, /* vs_3_0 */
7059 0x0200001f, 0x80000000, 0xe00f0000, /* dcl_position o0 */
7060 0x0200001f, 0x8000000a, 0xe00f0001, /* dcl_color o1 */
7061 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
7062 0x0200001f, 0x80000005, 0x900f0001, /* dcl_texcoord v1 */
7063 0x02000001, 0xe00f0000, 0x90e40000, /* mov o0, v0 */
7064 0x02000001, 0xe00f0001, 0x90e40001, /* mov o1, v1 */
7065 0x0000ffff /* end */
7067 static const DWORD texcoord_color_shader_code_2[] =
7069 0xfffe0200, /* vs_2_0 */
7070 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
7071 0x0200001f, 0x80000005, 0x900f0001, /* dcl_texcoord v1 */
7072 0x02000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
7073 0x02000001, 0xd00f0000, 0x90e40001, /* mov oD0, v1 */
7074 0x0000ffff /* end */
7076 static const DWORD texcoord_color_shader_code_1[] =
7078 0xfffe0101, /* vs_1_1 */
7079 0x0000001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
7080 0x0000001f, 0x80000005, 0x900f0001, /* dcl_texcoord v1 */
7081 0x00000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
7082 0x00000001, 0xd00f0000, 0x90e40001, /* mov oD0, v1 */
7083 0x0000ffff /* end */
7085 static const DWORD color_color_shader_code_3[] =
7087 0xfffe0300, /* vs_3_0 */
7088 0x0200001f, 0x80000000, 0xe00f0000, /* dcl_position o0 */
7089 0x0200001f, 0x8000000a, 0xe00f0001, /* dcl_color o1 */
7090 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
7091 0x0200001f, 0x8000000a, 0x900f0001, /* dcl_color v1 */
7092 0x02000001, 0xe00f0000, 0x90e40000, /* mov o0, v0 */
7093 0x03000005, 0xe00f0001, 0xa0e40000, 0x90e40001, /* mul o1, c0, v1 */
7094 0x0000ffff /* end */
7096 static const DWORD color_color_shader_code_2[] =
7098 0xfffe0200, /* vs_2_0 */
7099 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
7100 0x0200001f, 0x8000000a, 0x900f0001, /* dcl_color v1 */
7101 0x02000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
7102 0x03000005, 0xd00f0000, 0xa0e40000, 0x90e40001, /* mul oD0, c0, v1 */
7103 0x0000ffff /* end */
7105 static const DWORD color_color_shader_code_1[] =
7107 0xfffe0101, /* vs_1_1 */
7108 0x0000001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
7109 0x0000001f, 0x8000000a, 0x900f0001, /* dcl_color v1 */
7110 0x00000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
7111 0x00000005, 0xd00f0000, 0xa0e40000, 0x90e40001, /* mul oD0, c0, v1 */
7112 0x0000ffff /* end */
7114 static const DWORD ps3_code[] =
7116 0xffff0300, /* ps_3_0 */
7117 0x0200001f, 0x8000000a, 0x900f0000, /* dcl_color0 v0 */
7118 0x02000001, 0x800f0800, 0x90e40000, /* mov oC0, v0 */
7119 0x0000ffff /* end */
7121 static const float quad1[] =
7123 -1.0f, -1.0f, 0.1f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, -1.0f, 0.5f, 0.0f,
7124 -1.0f, 0.0f, 0.1f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, -1.0f, 0.5f, 0.0f,
7125 0.0f, -1.0f, 0.1f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, -1.0f, 0.5f, 0.0f,
7126 0.0f, 0.0f, 0.1f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, -1.0f, 0.5f, 0.0f,
7128 static const float quad2[] =
7130 0.0f, -1.0f, 0.1f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f,
7131 0.0f, 0.0f, 0.1f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f,
7132 1.0f, -1.0f, 0.1f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f,
7133 1.0f, 0.0f, 0.1f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f,
7135 static const float quad3[] =
7137 -1.0f, 0.0f, 0.1f, -1.0f, 0.0f, 0.0f, 0.0f, 1.0f, -1.0f, 0.0f, 0.0f,
7138 -1.0f, 1.0f, 0.1f, -1.0f, 0.0f, 0.0f, 0.0f, 0.0f, -1.0f, 1.0f, 0.0f,
7139 0.0f, 0.0f, 0.1f, -1.0f, 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f,
7140 0.0f, 1.0f, 0.1f, -1.0f, 0.0f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, 0.0f,
7142 static const float quad4[] =
7144 0.0f, 0.0f, 0.1f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, -1.0f, 0.5f, 0.0f,
7145 0.0f, 1.0f, 0.1f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, -1.0f, 0.5f, 0.0f,
7146 1.0f, 0.0f, 0.1f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, -1.0f, 0.5f, 0.0f,
7147 1.0f, 1.0f, 0.1f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, -1.0f, 0.5f, 0.0f,
7149 static const float quad1_modified[] =
7151 -1.0f, -1.0f, 0.1f, 1.0f, 0.0f, 1.0f, 0.0f, -1.0f, 0.0f, 0.0f, 0.0f,
7152 -1.0f, 0.0f, 0.1f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f, -1.0f, 0.0f,
7153 0.0f, -1.0f, 0.1f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f,
7154 0.0f, 0.0f, 0.1f, 1.0f, 0.0f, 1.0f, 0.0f, -1.0f, -1.0f, -1.0f, 0.0f,
7156 static const float quad2_modified[] =
7158 0.0f, -1.0f, 0.1f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f,
7159 0.0f, 0.0f, 0.1f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f,
7160 1.0f, -1.0f, 0.1f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f,
7161 1.0f, 0.0f, 0.1f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f,
7163 static const struct
7165 struct vec3 position;
7166 DWORD diffuse;
7168 quad1_color[] =
7170 {{-1.0f, -1.0f, 0.1f}, 0x00ff8040},
7171 {{-1.0f, 0.0f, 0.1f}, 0x00ff8040},
7172 {{ 0.0f, -1.0f, 0.1f}, 0x00ff8040},
7173 {{ 0.0f, 0.0f, 0.1f}, 0x00ff8040},
7175 quad2_color[] =
7177 {{ 0.0f, -1.0f, 0.1f}, 0x00ff8040},
7178 {{ 0.0f, 0.0f, 0.1f}, 0x00ff8040},
7179 {{ 1.0f, -1.0f, 0.1f}, 0x00ff8040},
7180 {{ 1.0f, 0.0f, 0.1f}, 0x00ff8040},
7182 quad3_color[] =
7184 {{-1.0f, 0.0f, 0.1f}, 0x00ff8040},
7185 {{-1.0f, 1.0f, 0.1f}, 0x00ff8040},
7186 {{ 0.0f, 0.0f, 0.1f}, 0x00ff8040},
7187 {{ 0.0f, 1.0f, 0.1f}, 0x00ff8040},
7189 static const float quad4_color[] =
7191 0.0f, 0.0f, 0.1f, 1.0f, 1.0f, 0.0f, 0.0f,
7192 0.0f, 1.0f, 0.1f, 1.0f, 1.0f, 0.0f, 0.0f,
7193 1.0f, 0.0f, 0.1f, 1.0f, 1.0f, 0.0f, 1.0f,
7194 1.0f, 1.0f, 0.1f, 1.0f, 1.0f, 0.0f, 1.0f,
7196 static const D3DVERTEXELEMENT9 decl_elements_twotexcrd[] =
7198 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
7199 {0, 12, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
7200 {0, 28, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 1},
7201 D3DDECL_END()
7203 static const D3DVERTEXELEMENT9 decl_elements_twotexcrd_rightorder[] =
7205 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
7206 {0, 12, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 1},
7207 {0, 28, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
7208 D3DDECL_END()
7210 static const D3DVERTEXELEMENT9 decl_elements_onetexcrd[] =
7212 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
7213 {0, 12, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
7214 D3DDECL_END()
7216 static const D3DVERTEXELEMENT9 decl_elements_twotexcrd_wrongidx[] =
7218 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
7219 {0, 12, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 1},
7220 {0, 28, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 2},
7221 D3DDECL_END()
7223 static const D3DVERTEXELEMENT9 decl_elements_texcoord_color[] =
7225 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
7226 {0, 12, D3DDECLTYPE_D3DCOLOR, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
7227 D3DDECL_END()
7229 static const D3DVERTEXELEMENT9 decl_elements_color_color[] =
7231 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
7232 {0, 12, D3DDECLTYPE_D3DCOLOR, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR, 0},
7233 D3DDECL_END()
7235 static const D3DVERTEXELEMENT9 decl_elements_color_ubyte[] =
7237 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
7238 {0, 12, D3DDECLTYPE_UBYTE4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR, 0},
7239 D3DDECL_END()
7241 static const D3DVERTEXELEMENT9 decl_elements_color_float[] =
7243 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
7244 {0, 12, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR, 0},
7245 D3DDECL_END()
7247 static const float normalize[4] = {1.0f / 256.0f, 1.0f / 256.0f, 1.0f / 256.0f, 1.0f / 256.0f};
7248 static const float no_normalize[4] = {1.0f, 1.0f, 1.0f, 1.0f};
7250 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
7251 0, 0, 640, 480, NULL, NULL, NULL, NULL);
7252 d3d = Direct3DCreate9(D3D_SDK_VERSION);
7253 ok(!!d3d, "Failed to create a D3D object.\n");
7254 if (!(device = create_device(d3d, window, window, TRUE)))
7256 skip("Failed to create a D3D device, skipping tests.\n");
7257 goto done;
7260 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
7261 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
7262 if (caps.VertexShaderVersion < D3DVS_VERSION(3, 0))
7264 skip("No vs_3_0 support, skipping tests.\n");
7265 IDirect3DDevice9_Release(device);
7266 goto done;
7269 hr = IDirect3D9_GetAdapterIdentifier(d3d, D3DADAPTER_DEFAULT, 0, &identifier);
7270 ok(SUCCEEDED(hr), "Failed to get adapter identifier, hr %#x.\n", hr);
7271 warp = !strcmp(identifier.Description, "Microsoft Basic Render Driver");
7273 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements_twotexcrd, &decl_twotexcrd);
7274 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexDeclaration returned %08x\n", hr);
7275 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements_onetexcrd, &decl_onetexcrd);
7276 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexDeclaration returned %08x\n", hr);
7277 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements_twotexcrd_wrongidx, &decl_twotex_wrongidx);
7278 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexDeclaration returned %08x\n", hr);
7279 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements_twotexcrd_rightorder, &decl_twotexcrd_rightorder);
7280 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexDeclaration returned %08x\n", hr);
7282 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements_texcoord_color, &decl_texcoord_color);
7283 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexDeclaration returned %08x\n", hr);
7284 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements_color_color, &decl_color_color);
7285 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexDeclaration returned %08x\n", hr);
7286 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements_color_ubyte, &decl_color_ubyte);
7287 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexDeclaration returned %08x\n", hr);
7288 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements_color_float, &decl_color_float);
7289 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexDeclaration returned %08x\n", hr);
7291 hr = IDirect3DDevice9_CreatePixelShader(device, ps3_code, &ps);
7292 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader returned %08x\n", hr);
7294 for (i = 1; i <= 3; ++i)
7296 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffff0000, 1.0f, 0);
7297 ok(SUCCEEDED(hr), "IDirect3DDevice9_Clear returned %#x.\n", hr);
7298 if(i == 3) {
7299 hr = IDirect3DDevice9_CreateVertexShader(device, swapped_shader_code_3, &swapped_shader);
7300 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader returned %08x\n", hr);
7301 hr = IDirect3DDevice9_SetPixelShader(device, ps);
7302 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShader returned %08x\n", hr);
7303 } else if(i == 2){
7304 hr = IDirect3DDevice9_CreateVertexShader(device, swapped_shader_code_2, &swapped_shader);
7305 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader returned %08x\n", hr);
7306 } else if(i == 1) {
7307 hr = IDirect3DDevice9_CreateVertexShader(device, swapped_shader_code_1, &swapped_shader);
7308 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader returned %08x\n", hr);
7311 hr = IDirect3DDevice9_BeginScene(device);
7312 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
7314 hr = IDirect3DDevice9_SetVertexShader(device, swapped_shader);
7315 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
7317 hr = IDirect3DDevice9_SetVertexDeclaration(device, decl_twotexcrd);
7318 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
7319 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, sizeof(float) * 11);
7320 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
7322 hr = IDirect3DDevice9_SetVertexDeclaration(device, decl_onetexcrd);
7323 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
7324 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, sizeof(float) * 11);
7325 if (i == 3 || i == 2)
7326 ok(SUCCEEDED(hr), "Failed to draw, i %u, hr %#x.\n", i, hr);
7327 else if (i == 1)
7328 /* Succeeds or fails, depending on SW or HW vertex processing. */
7329 ok(hr == D3DERR_INVALIDCALL || hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
7331 hr = IDirect3DDevice9_SetVertexDeclaration(device, decl_twotexcrd_rightorder);
7332 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
7333 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad4, sizeof(float) * 11);
7334 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
7336 hr = IDirect3DDevice9_SetVertexDeclaration(device, decl_twotex_wrongidx);
7337 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
7338 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad3, sizeof(float) * 11);
7339 if (i == 3 || i == 2)
7340 ok(SUCCEEDED(hr), "Failed to draw, i %u, hr %#x.\n", i, hr);
7341 else if (i == 1)
7342 ok(hr == D3DERR_INVALIDCALL || hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
7344 hr = IDirect3DDevice9_EndScene(device);
7345 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
7347 if(i == 3 || i == 2) {
7348 color = getPixelColor(device, 160, 360);
7349 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0xff, 0xff, 0x80), 1),
7350 "Input test: Quad 1(2crd) returned color 0x%08x, expected 0x00ffff80\n", color);
7352 /* The last value of the read but undefined stream is used, it is 0x00. The defined input is vec4(1, 0, 0, 0) */
7353 color = getPixelColor(device, 480, 360);
7354 /* On the Windows 8 testbot (WARP) the draw succeeds, but uses
7355 * mostly random data as input. */
7356 ok(color == 0x00ffff00 || color == 0x00ff0000 || broken(warp),
7357 "Got unexpected color 0x%08x for quad 2 (1crd).\n", color);
7358 color = getPixelColor(device, 160, 120);
7359 /* Same as above, accept both the last used value and 0.0 for the undefined streams */
7360 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0xff, 0x00, 0x80), 1) || color == D3DCOLOR_ARGB(0x00, 0xff, 0x00, 0x00),
7361 "Input test: Quad 3(2crd-wrongidx) returned color 0x%08x, expected 0x00ff0080\n", color);
7363 color = getPixelColor(device, 480, 160);
7364 ok(color == 0x00000000, "Input test: Quad 4(2crd-rightorder) returned color 0x%08x, expected 0x00000000\n", color);
7365 } else if(i == 1) {
7366 color = getPixelColor(device, 160, 360);
7367 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0xff, 0xff, 0x80), 1),
7368 "Input test: Quad 1(2crd) returned color 0x%08x, expected 0x00ffff80\n", color);
7369 color = getPixelColor(device, 480, 360);
7370 /* Accept the clear color as well in this case, since SW VP
7371 * returns an error. On the Windows 8 testbot (WARP) the draw
7372 * succeeds, but uses mostly random data as input. */
7373 ok(color == 0x00ffff00 || color == 0x00ff0000 || broken(warp),
7374 "Got unexpected color 0x%08x for quad 2 (1crd).\n", color);
7375 color = getPixelColor(device, 160, 120);
7376 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0xff, 0x00, 0x80), 1) || color == D3DCOLOR_ARGB(0x00, 0xff, 0x00, 0x00),
7377 "Input test: Quad 3(2crd-wrongidx) returned color 0x%08x, expected 0x00ff0080\n", color);
7378 color = getPixelColor(device, 480, 160);
7379 ok(color == 0x00000000, "Input test: Quad 4(2crd-rightorder) returned color 0x%08x, expected 0x00000000\n", color);
7382 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
7383 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
7385 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff808080, 0.0, 0);
7386 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
7388 /* Now find out if the whole streams are re-read, or just the last
7389 * active value for the vertices is used. */
7390 hr = IDirect3DDevice9_BeginScene(device);
7391 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
7393 hr = IDirect3DDevice9_SetVertexShader(device, swapped_shader);
7394 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
7396 hr = IDirect3DDevice9_SetVertexDeclaration(device, decl_twotexcrd);
7397 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
7398 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_POINTLIST, 3, quad1_modified, sizeof(float) * 11);
7399 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
7401 hr = IDirect3DDevice9_SetVertexDeclaration(device, decl_onetexcrd);
7402 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
7403 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2_modified, sizeof(float) * 11);
7404 if (i == 3 || i == 2)
7405 ok(SUCCEEDED(hr), "Failed to draw, i %u, hr %#x.\n", i, hr);
7406 else if (i == 1)
7407 /* Succeeds or fails, depending on SW or HW vertex processing. */
7408 ok(hr == D3DERR_INVALIDCALL || hr == D3D_OK, "Got unexpected hr %#x.\n", hr);
7410 hr = IDirect3DDevice9_EndScene(device);
7411 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
7413 color = getPixelColor(device, 480, 350);
7414 /* vs_1_1 may fail, accept the clear color. Some drivers also set the undefined streams to 0, accept that
7415 * as well.
7417 * NOTE: This test fails on the reference rasterizer. In the refrast, the 4 vertices have different colors,
7418 * i.e., the whole old stream is read, and not just the last used attribute. Some games require that this
7419 * does *not* happen, otherwise they can crash because of a read from a bad pointer, so do not accept the
7420 * refrast's result.
7422 * A test app for this behavior is Half Life 2 Episode 2 in dxlevel 95, and related games(Portal, TF2).
7424 ok(color == 0x000000ff || color == 0x00808080 || color == 0x00000000
7425 || broken(color_match(color, D3DCOLOR_ARGB(0x00, 0x0b, 0x75, 0x80), 1)),
7426 "Got unexpected color 0x%08x for quad 2 (different colors).\n", color);
7428 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
7429 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
7431 IDirect3DDevice9_SetVertexShader(device, NULL);
7432 IDirect3DDevice9_SetPixelShader(device, NULL);
7433 IDirect3DDevice9_SetVertexDeclaration(device, NULL);
7435 IDirect3DVertexShader9_Release(swapped_shader);
7438 for (i = 1; i <= 3; ++i)
7440 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff0000ff, 1.0f, 0);
7441 ok(SUCCEEDED(hr), "IDirect3DDevice9_Clear returned %#x.\n", hr);
7442 if(i == 3) {
7443 hr = IDirect3DDevice9_CreateVertexShader(device, texcoord_color_shader_code_3, &texcoord_color_shader);
7444 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader returned %08x\n", hr);
7445 hr = IDirect3DDevice9_CreateVertexShader(device, color_color_shader_code_3, &color_color_shader);
7446 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader returned %08x\n", hr);
7447 hr = IDirect3DDevice9_SetPixelShader(device, ps);
7448 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShader returned %08x\n", hr);
7449 } else if(i == 2){
7450 hr = IDirect3DDevice9_CreateVertexShader(device, texcoord_color_shader_code_2, &texcoord_color_shader);
7451 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader returned %08x\n", hr);
7452 hr = IDirect3DDevice9_CreateVertexShader(device, color_color_shader_code_2, &color_color_shader);
7453 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader returned %08x\n", hr);
7454 } else if(i == 1) {
7455 hr = IDirect3DDevice9_CreateVertexShader(device, texcoord_color_shader_code_1, &texcoord_color_shader);
7456 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader returned %08x\n", hr);
7457 hr = IDirect3DDevice9_CreateVertexShader(device, color_color_shader_code_1, &color_color_shader);
7458 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader returned %08x\n", hr);
7461 hr = IDirect3DDevice9_BeginScene(device);
7462 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
7464 hr = IDirect3DDevice9_SetVertexShader(device, texcoord_color_shader);
7465 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
7466 hr = IDirect3DDevice9_SetVertexDeclaration(device, decl_texcoord_color);
7467 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
7468 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1_color, sizeof(quad1_color[0]));
7469 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
7471 hr = IDirect3DDevice9_SetVertexShader(device, color_color_shader);
7472 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
7474 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 0, normalize, 1);
7475 ok(SUCCEEDED(hr), "Failed to set vertex shader constant, hr %#x.\n", hr);
7476 hr = IDirect3DDevice9_SetVertexDeclaration(device, decl_color_ubyte);
7477 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
7478 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2_color, sizeof(quad2_color[0]));
7479 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
7481 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 0, no_normalize, 1);
7482 ok(SUCCEEDED(hr), "Failed to set vertex shader constant, hr %#x.\n", hr);
7483 hr = IDirect3DDevice9_SetVertexDeclaration(device, decl_color_color);
7484 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
7485 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad3_color, sizeof(quad3_color[0]));
7486 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
7488 hr = IDirect3DDevice9_SetVertexDeclaration(device, decl_color_float);
7489 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
7490 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad4_color, sizeof(float) * 7);
7491 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
7493 hr = IDirect3DDevice9_EndScene(device);
7494 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
7496 IDirect3DDevice9_SetVertexShader(device, NULL);
7497 IDirect3DDevice9_SetVertexDeclaration(device, NULL);
7498 IDirect3DDevice9_SetPixelShader(device, NULL);
7500 color = getPixelColor(device, 160, 360);
7501 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0xff, 0x80, 0x40), 1),
7502 "Input test: Quad 1(color-texcoord) returned color 0x%08x, expected 0x00ff8040\n", color);
7503 color = getPixelColor(device, 480, 360);
7504 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x40, 0x80, 0xff), 1),
7505 "Input test: Quad 2(color-ubyte) returned color 0x%08x, expected 0x004080ff\n", color);
7506 color = getPixelColor(device, 160, 120);
7507 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0xff, 0x80, 0x40), 1),
7508 "Input test: Quad 3(color-color) returned color 0x%08x, expected 0x00ff8040\n", color);
7509 color = getPixelColor(device, 480, 160);
7510 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0xff, 0xff, 0x00), 1),
7511 "Input test: Quad 4(color-float) returned color 0x%08x, expected 0x00ffff00\n", color);
7513 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
7514 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
7516 IDirect3DVertexShader9_Release(texcoord_color_shader);
7517 IDirect3DVertexShader9_Release(color_color_shader);
7520 IDirect3DVertexDeclaration9_Release(decl_twotexcrd);
7521 IDirect3DVertexDeclaration9_Release(decl_onetexcrd);
7522 IDirect3DVertexDeclaration9_Release(decl_twotex_wrongidx);
7523 IDirect3DVertexDeclaration9_Release(decl_twotexcrd_rightorder);
7525 IDirect3DVertexDeclaration9_Release(decl_texcoord_color);
7526 IDirect3DVertexDeclaration9_Release(decl_color_color);
7527 IDirect3DVertexDeclaration9_Release(decl_color_ubyte);
7528 IDirect3DVertexDeclaration9_Release(decl_color_float);
7530 IDirect3DPixelShader9_Release(ps);
7531 refcount = IDirect3DDevice9_Release(device);
7532 ok(!refcount, "Device has %u references left.\n", refcount);
7533 done:
7534 IDirect3D9_Release(d3d);
7535 DestroyWindow(window);
7538 static void srgbtexture_test(void)
7540 /* Fill a texture with 0x7f (~ .5), and then turn on the D3DSAMP_SRGBTEXTURE
7541 * texture stage state to render a quad using that texture. The resulting
7542 * color components should be 0x36 (~ 0.21), per this formula:
7543 * linear_color = ((srgb_color + 0.055) / 1.055) ^ 2.4
7544 * This is true where srgb_color > 0.04045. */
7545 struct IDirect3DTexture9 *texture;
7546 struct IDirect3DSurface9 *surface;
7547 IDirect3DDevice9 *device;
7548 IDirect3D9 *d3d;
7549 D3DCOLOR color;
7550 ULONG refcount;
7551 HWND window;
7552 HRESULT hr;
7554 static const float quad[] =
7556 -1.0f, -1.0f, 0.0f, 0.0f, 1.0f,
7557 -1.0f, 1.0f, 0.0f, 0.0f, 0.0f,
7558 1.0f, -1.0f, 0.0f, 1.0f, 1.0f,
7559 1.0f, 1.0f, 0.0f, 1.0f, 0.0f,
7562 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
7563 0, 0, 640, 480, NULL, NULL, NULL, NULL);
7564 d3d = Direct3DCreate9(D3D_SDK_VERSION);
7565 ok(!!d3d, "Failed to create a D3D object.\n");
7566 if (!(device = create_device(d3d, window, window, TRUE)))
7568 skip("Failed to create a D3D device, skipping tests.\n");
7569 goto done;
7572 if (IDirect3D9_CheckDeviceFormat(d3d, 0, D3DDEVTYPE_HAL,
7573 D3DFMT_X8R8G8B8, D3DUSAGE_QUERY_SRGBREAD, D3DRTYPE_TEXTURE, D3DFMT_A8R8G8B8) != D3D_OK)
7575 skip("D3DFMT_A8R8G8B8 textures with SRGBREAD not supported.\n");
7576 IDirect3DDevice9_Release(device);
7577 goto done;
7580 hr = IDirect3DDevice9_CreateTexture(device, 16, 16, 1, 0, D3DFMT_A8R8G8B8, D3DPOOL_MANAGED, &texture, NULL);
7581 ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);
7582 hr = IDirect3DTexture9_GetSurfaceLevel(texture, 0, &surface);
7583 ok(hr == D3D_OK, "IDirect3DTexture9_GetSurfaceLevel failed with %08x\n", hr);
7585 fill_surface(surface, 0xff7f7f7f, 0);
7586 IDirect3DSurface9_Release(surface);
7588 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
7589 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
7590 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *) texture);
7591 ok(hr == D3D_OK, "IDirect3DDevice9_SetTexture failed with %08x\n", hr);
7593 hr = IDirect3DDevice9_BeginScene(device);
7594 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
7596 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_SRGBTEXTURE, TRUE);
7597 ok(SUCCEEDED(hr), "Failed to set sampler state, hr %#x.\n", hr);
7598 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1);
7599 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
7600 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, 5 * sizeof(float));
7601 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
7603 hr = IDirect3DDevice9_EndScene(device);
7604 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
7606 color = getPixelColor(device, 320, 240);
7607 ok(color_match(color, 0x00363636, 1), "sRGB quad has color 0x%08x, expected 0x00363636.\n", color);
7609 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
7610 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
7612 IDirect3DTexture9_Release(texture);
7613 refcount = IDirect3DDevice9_Release(device);
7614 ok(!refcount, "Device has %u references left.\n", refcount);
7615 done:
7616 IDirect3D9_Release(d3d);
7617 DestroyWindow(window);
7620 static void shademode_test(void)
7622 /* Render a quad and try all of the different fixed function shading models. */
7623 DWORD color0_gouraud = 0, color1_gouraud = 0;
7624 DWORD primtype = D3DPT_TRIANGLESTRIP;
7625 IDirect3DVertexBuffer9 *vb_strip;
7626 IDirect3DVertexBuffer9 *vb_list;
7627 DWORD shademode = D3DSHADE_FLAT;
7628 IDirect3DDevice9 *device;
7629 DWORD color0, color1;
7630 void *data = NULL;
7631 IDirect3D9 *d3d;
7632 ULONG refcount;
7633 HWND window;
7634 HRESULT hr;
7635 UINT i, j;
7637 static const struct
7639 struct vec3 position;
7640 DWORD diffuse;
7642 quad_strip[] =
7644 {{-1.0f, -1.0f, 0.0f}, 0xffff0000},
7645 {{-1.0f, 1.0f, 0.0f}, 0xff00ff00},
7646 {{ 1.0f, -1.0f, 0.0f}, 0xff0000ff},
7647 {{ 1.0f, 1.0f, 0.0f}, 0xffffffff},
7649 quad_list[] =
7651 {{-1.0f, -1.0f, 0.0f}, 0xffff0000},
7652 {{-1.0f, 1.0f, 0.0f}, 0xff00ff00},
7653 {{ 1.0f, -1.0f, 0.0f}, 0xff0000ff},
7655 {{ 1.0f, -1.0f, 0.0f}, 0xff0000ff},
7656 {{-1.0f, 1.0f, 0.0f}, 0xff00ff00},
7657 {{ 1.0f, 1.0f, 0.0f}, 0xffffffff},
7660 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
7661 0, 0, 640, 480, NULL, NULL, NULL, NULL);
7662 d3d = Direct3DCreate9(D3D_SDK_VERSION);
7663 ok(!!d3d, "Failed to create a D3D object.\n");
7664 if (!(device = create_device(d3d, window, window, TRUE)))
7666 skip("Failed to create a D3D device, skipping tests.\n");
7667 goto done;
7670 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
7671 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
7673 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
7674 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed with %08x\n", hr);
7676 hr = IDirect3DDevice9_CreateVertexBuffer(device, sizeof(quad_strip), 0, 0, D3DPOOL_MANAGED, &vb_strip, NULL);
7677 ok(hr == D3D_OK, "CreateVertexBuffer failed with %08x\n", hr);
7678 hr = IDirect3DVertexBuffer9_Lock(vb_strip, 0, sizeof(quad_strip), &data, 0);
7679 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Lock failed with %08x\n", hr);
7680 memcpy(data, quad_strip, sizeof(quad_strip));
7681 hr = IDirect3DVertexBuffer9_Unlock(vb_strip);
7682 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Unlock failed with %08x\n", hr);
7684 hr = IDirect3DDevice9_CreateVertexBuffer(device, sizeof(quad_list), 0, 0, D3DPOOL_MANAGED, &vb_list, NULL);
7685 ok(hr == D3D_OK, "CreateVertexBuffer failed with %08x\n", hr);
7686 hr = IDirect3DVertexBuffer9_Lock(vb_list, 0, sizeof(quad_list), &data, 0);
7687 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Lock failed with %08x\n", hr);
7688 memcpy(data, quad_list, sizeof(quad_list));
7689 hr = IDirect3DVertexBuffer9_Unlock(vb_list);
7690 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Unlock failed with %08x\n", hr);
7692 /* Try it first with a TRIANGLESTRIP. Do it with different geometry because
7693 * the color fixups we have to do for FLAT shading will be dependent on that. */
7694 hr = IDirect3DDevice9_SetStreamSource(device, 0, vb_strip, 0, sizeof(quad_strip[0]));
7695 ok(hr == D3D_OK, "IDirect3DDevice9_SetStreamSource failed with %08x\n", hr);
7697 /* First loop uses a TRIANGLESTRIP geometry, 2nd uses a TRIANGLELIST */
7698 for (j=0; j<2; j++) {
7700 /* Inner loop just changes the D3DRS_SHADEMODE */
7701 for (i=0; i<3; i++) {
7702 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffffffff, 0.0, 0);
7703 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
7705 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_SHADEMODE, shademode);
7706 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
7708 hr = IDirect3DDevice9_BeginScene(device);
7709 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
7710 hr = IDirect3DDevice9_DrawPrimitive(device, primtype, 0, 2);
7711 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
7712 hr = IDirect3DDevice9_EndScene(device);
7713 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
7715 /* Sample two spots from the output */
7716 color0 = getPixelColor(device, 100, 100); /* Inside first triangle */
7717 color1 = getPixelColor(device, 500, 350); /* Inside second triangle */
7718 switch(shademode) {
7719 case D3DSHADE_FLAT:
7720 /* Should take the color of the first vertex of each triangle */
7721 if (0)
7723 /* This test depends on EXT_provoking_vertex being
7724 * available. This extension is currently (20090810)
7725 * not common enough to let the test fail if it isn't
7726 * present. */
7727 ok(color0 == 0x00ff0000, "FLAT shading has color0 %08x, expected 0x00ff0000\n", color0);
7728 ok(color1 == 0x0000ff00, "FLAT shading has color1 %08x, expected 0x0000ff00\n", color1);
7730 shademode = D3DSHADE_GOURAUD;
7731 break;
7732 case D3DSHADE_GOURAUD:
7733 /* Should be an interpolated blend */
7735 ok(color_match(color0, D3DCOLOR_ARGB(0x00, 0x0d, 0xca, 0x28), 2),
7736 "GOURAUD shading has color0 %08x, expected 0x00dca28\n", color0);
7737 ok(color_match(color1, D3DCOLOR_ARGB(0x00, 0x0d, 0x45, 0xc7), 2),
7738 "GOURAUD shading has color1 %08x, expected 0x000d45c7\n", color1);
7740 color0_gouraud = color0;
7741 color1_gouraud = color1;
7743 shademode = D3DSHADE_PHONG;
7744 break;
7745 case D3DSHADE_PHONG:
7746 /* Should be the same as GOURAUD, since no hardware implements this */
7747 ok(color_match(color0, D3DCOLOR_ARGB(0x00, 0x0d, 0xca, 0x28), 2),
7748 "PHONG shading has color0 %08x, expected 0x000dca28\n", color0);
7749 ok(color_match(color1, D3DCOLOR_ARGB(0x00, 0x0d, 0x45, 0xc7), 2),
7750 "PHONG shading has color1 %08x, expected 0x000d45c7\n", color1);
7752 ok(color0 == color0_gouraud, "difference between GOURAUD and PHONG shading detected: %08x %08x\n",
7753 color0_gouraud, color0);
7754 ok(color1 == color1_gouraud, "difference between GOURAUD and PHONG shading detected: %08x %08x\n",
7755 color1_gouraud, color1);
7756 break;
7760 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
7761 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
7763 /* Now, do it all over again with a TRIANGLELIST */
7764 hr = IDirect3DDevice9_SetStreamSource(device, 0, vb_list, 0, sizeof(quad_list[0]));
7765 ok(hr == D3D_OK, "IDirect3DDevice9_SetStreamSource failed with %08x\n", hr);
7766 primtype = D3DPT_TRIANGLELIST;
7767 shademode = D3DSHADE_FLAT;
7770 IDirect3DVertexBuffer9_Release(vb_strip);
7771 IDirect3DVertexBuffer9_Release(vb_list);
7772 refcount = IDirect3DDevice9_Release(device);
7773 ok(!refcount, "Device has %u references left.\n", refcount);
7774 done:
7775 IDirect3D9_Release(d3d);
7776 DestroyWindow(window);
7779 static void alpha_test(void)
7781 IDirect3DSurface9 *backbuffer, *offscreen;
7782 IDirect3DTexture9 *offscreenTexture;
7783 IDirect3DDevice9 *device;
7784 IDirect3D9 *d3d;
7785 D3DCOLOR color;
7786 ULONG refcount;
7787 HWND window;
7788 HRESULT hr;
7790 static const struct
7792 struct vec3 position;
7793 DWORD diffuse;
7795 quad1[] =
7797 {{-1.0f, -1.0f, 0.1f}, 0x4000ff00},
7798 {{-1.0f, 0.0f, 0.1f}, 0x4000ff00},
7799 {{ 1.0f, -1.0f, 0.1f}, 0x4000ff00},
7800 {{ 1.0f, 0.0f, 0.1f}, 0x4000ff00},
7802 quad2[] =
7804 {{-1.0f, 0.0f, 0.1f}, 0xc00000ff},
7805 {{-1.0f, 1.0f, 0.1f}, 0xc00000ff},
7806 {{ 1.0f, 0.0f, 0.1f}, 0xc00000ff},
7807 {{ 1.0f, 1.0f, 0.1f}, 0xc00000ff},
7809 static const float composite_quad[][5] =
7811 { 0.0f, -1.0f, 0.1f, 0.0f, 1.0f},
7812 { 0.0f, 1.0f, 0.1f, 0.0f, 0.0f},
7813 { 1.0f, -1.0f, 0.1f, 1.0f, 1.0f},
7814 { 1.0f, 1.0f, 0.1f, 1.0f, 0.0f},
7817 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
7818 0, 0, 640, 480, NULL, NULL, NULL, NULL);
7819 d3d = Direct3DCreate9(D3D_SDK_VERSION);
7820 ok(!!d3d, "Failed to create a D3D object.\n");
7821 if (!(device = create_device(d3d, window, window, TRUE)))
7823 skip("Failed to create a D3D device, skipping tests.\n");
7824 goto done;
7827 /* Clear the render target with alpha = 0.5 */
7828 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x80ff0000, 1.0f, 0);
7829 ok(hr == D3D_OK, "Clear failed, hr = %08x\n", hr);
7831 hr = IDirect3DDevice9_CreateTexture(device, 128, 128, 1, D3DUSAGE_RENDERTARGET,
7832 D3DFMT_X8R8G8B8, D3DPOOL_DEFAULT, &offscreenTexture, NULL);
7833 ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);
7835 hr = IDirect3DDevice9_GetBackBuffer(device, 0, 0, D3DBACKBUFFER_TYPE_MONO, &backbuffer);
7836 ok(hr == D3D_OK, "Can't get back buffer, hr = %08x\n", hr);
7838 hr = IDirect3DTexture9_GetSurfaceLevel(offscreenTexture, 0, &offscreen);
7839 ok(hr == D3D_OK, "Can't get offscreen surface, hr = %08x\n", hr);
7841 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
7842 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed, hr = %#08x\n", hr);
7844 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
7845 ok(hr == D3D_OK, "SetTextureStageState failed, hr = %08x\n", hr);
7846 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
7847 ok(hr == D3D_OK, "SetTextureStageState failed, hr = %08x\n", hr);
7848 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MINFILTER, D3DTEXF_POINT);
7849 ok(SUCCEEDED(hr), "SetSamplerState D3DSAMP_MINFILTER failed (0x%08x)\n", hr);
7850 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAGFILTER, D3DTEXF_POINT);
7851 ok(SUCCEEDED(hr), "SetSamplerState D3DSAMP_MAGFILTER failed (0x%08x)\n", hr);
7852 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
7853 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
7855 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ALPHABLENDENABLE, TRUE);
7856 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState failed, hr = %08x\n", hr);
7857 hr = IDirect3DDevice9_BeginScene(device);
7858 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
7860 /* Draw two quads, one with src alpha blending, one with dest alpha
7861 * blending. */
7862 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_SRCBLEND, D3DBLEND_SRCALPHA);
7863 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
7864 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA);
7865 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
7866 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, sizeof(quad1[0]));
7867 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
7869 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_SRCBLEND, D3DBLEND_DESTALPHA);
7870 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
7871 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_DESTBLEND, D3DBLEND_INVDESTALPHA);
7872 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
7873 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, sizeof(quad2[0]));
7874 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
7876 /* Switch to the offscreen buffer, and redo the testing. The offscreen
7877 * render target doesn't have an alpha channel. DESTALPHA and INVDESTALPHA
7878 * "don't work" on render targets without alpha channel, they give
7879 * essentially ZERO and ONE blend factors. */
7880 hr = IDirect3DDevice9_SetRenderTarget(device, 0, offscreen);
7881 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
7882 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x80ff0000, 1.0f, 0);
7883 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
7885 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_SRCBLEND, D3DBLEND_SRCALPHA);
7886 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
7887 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA);
7888 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
7889 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, sizeof(quad1[0]));
7890 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
7892 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_SRCBLEND, D3DBLEND_DESTALPHA);
7893 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
7894 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_DESTBLEND, D3DBLEND_INVDESTALPHA);
7895 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
7896 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, sizeof(quad2[0]));
7897 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
7899 hr = IDirect3DDevice9_SetRenderTarget(device, 0, backbuffer);
7900 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
7902 /* Render the offscreen texture onto the frame buffer to be able to
7903 * compare it regularly. Disable alpha blending for the final
7904 * composition. */
7905 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ALPHABLENDENABLE, FALSE);
7906 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
7907 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1);
7908 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
7910 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *) offscreenTexture);
7911 ok(SUCCEEDED(hr), "Failed to set texture, hr %#x.\n", hr);
7912 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, composite_quad, sizeof(float) * 5);
7913 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
7915 hr = IDirect3DDevice9_EndScene(device);
7916 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
7918 color = getPixelColor(device, 160, 360);
7919 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0xbf, 0x40, 0x00), 1),
7920 "SRCALPHA on frame buffer returned color %08x, expected 0x00bf4000\n", color);
7922 color = getPixelColor(device, 160, 120);
7923 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x7f, 0x00, 0x80), 2),
7924 "DSTALPHA on frame buffer returned color %08x, expected 0x007f0080\n", color);
7926 color = getPixelColor(device, 480, 360);
7927 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0xbf, 0x40, 0x00), 1),
7928 "SRCALPHA on texture returned color %08x, expected 0x00bf4000\n", color);
7930 color = getPixelColor(device, 480, 120);
7931 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x00, 0x00, 0xff), 1),
7932 "DSTALPHA on texture returned color %08x, expected 0x000000ff\n", color);
7934 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
7936 IDirect3DSurface9_Release(backbuffer);
7937 IDirect3DTexture9_Release(offscreenTexture);
7938 IDirect3DSurface9_Release(offscreen);
7939 refcount = IDirect3DDevice9_Release(device);
7940 ok(!refcount, "Device has %u references left.\n", refcount);
7941 done:
7942 IDirect3D9_Release(d3d);
7943 DestroyWindow(window);
7946 struct vertex_shortcolor {
7947 float x, y, z;
7948 unsigned short r, g, b, a;
7950 struct vertex_floatcolor {
7951 float x, y, z;
7952 float r, g, b, a;
7955 static void fixed_function_decl_test(void)
7957 IDirect3DVertexDeclaration9 *dcl_float = NULL, *dcl_short = NULL, *dcl_ubyte = NULL, *dcl_color = NULL;
7958 IDirect3DVertexDeclaration9 *dcl_color_2 = NULL, *dcl_ubyte_2 = NULL, *dcl_positiont;
7959 IDirect3DVertexBuffer9 *vb, *vb2;
7960 IDirect3DDevice9 *device;
7961 BOOL s_ok, ub_ok, f_ok;
7962 DWORD color, size, i;
7963 IDirect3D9 *d3d;
7964 ULONG refcount;
7965 D3DCAPS9 caps;
7966 HWND window;
7967 void *data;
7968 HRESULT hr;
7970 static const D3DVERTEXELEMENT9 decl_elements_d3dcolor[] = {
7971 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
7972 {0, 12, D3DDECLTYPE_D3DCOLOR, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR, 0},
7973 D3DDECL_END()
7975 static const D3DVERTEXELEMENT9 decl_elements_d3dcolor_2streams[] = {
7976 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
7977 {1, 0, D3DDECLTYPE_D3DCOLOR, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR, 0},
7978 D3DDECL_END()
7980 static const D3DVERTEXELEMENT9 decl_elements_ubyte4n[] = {
7981 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
7982 {0, 12, D3DDECLTYPE_UBYTE4N, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR, 0},
7983 D3DDECL_END()
7985 static const D3DVERTEXELEMENT9 decl_elements_ubyte4n_2streams[] = {
7986 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
7987 {1, 0, D3DDECLTYPE_UBYTE4N, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR, 0},
7988 D3DDECL_END()
7990 static const D3DVERTEXELEMENT9 decl_elements_short4[] = {
7991 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
7992 {0, 12, D3DDECLTYPE_USHORT4N, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR, 0},
7993 D3DDECL_END()
7995 static const D3DVERTEXELEMENT9 decl_elements_float[] = {
7996 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
7997 {0, 12, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR, 0},
7998 D3DDECL_END()
8000 static const D3DVERTEXELEMENT9 decl_elements_positiont[] = {
8001 {0, 0, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITIONT, 0},
8002 {0, 16, D3DDECLTYPE_D3DCOLOR, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR, 0},
8003 D3DDECL_END()
8005 static const struct
8007 struct vec3 position;
8008 DWORD diffuse;
8010 quad1[] = /* D3DCOLOR */
8012 {{-1.0f, -1.0f, 0.1f}, 0x00ffff00},
8013 {{-1.0f, 0.0f, 0.1f}, 0x00ffff00},
8014 {{ 0.0f, -1.0f, 0.1f}, 0x00ffff00},
8015 {{ 0.0f, 0.0f, 0.1f}, 0x00ffff00},
8017 quad2[] = /* UBYTE4N */
8019 {{-1.0f, 0.0f, 0.1f}, 0x00ffff00},
8020 {{-1.0f, 1.0f, 0.1f}, 0x00ffff00},
8021 {{ 0.0f, 0.0f, 0.1f}, 0x00ffff00},
8022 {{ 0.0f, 1.0f, 0.1f}, 0x00ffff00},
8024 static const struct vertex_shortcolor quad3[] = /* short */
8026 { 0.0f, -1.0f, 0.1f, 0x0000, 0x0000, 0xffff, 0xffff},
8027 { 0.0f, 0.0f, 0.1f, 0x0000, 0x0000, 0xffff, 0xffff},
8028 { 1.0f, -1.0f, 0.1f, 0x0000, 0x0000, 0xffff, 0xffff},
8029 { 1.0f, 0.0f, 0.1f, 0x0000, 0x0000, 0xffff, 0xffff},
8031 static const struct vertex_floatcolor quad4[] =
8033 { 0.0f, 0.0f, 0.1f, 1.0, 0.0, 0.0, 0.0},
8034 { 0.0f, 1.0f, 0.1f, 1.0, 0.0, 0.0, 0.0},
8035 { 1.0f, 0.0f, 0.1f, 1.0, 0.0, 0.0, 0.0},
8036 { 1.0f, 1.0f, 0.1f, 1.0, 0.0, 0.0, 0.0},
8038 static const DWORD colors[] =
8040 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00ffffff,
8041 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00ffffff,
8042 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00ffffff,
8043 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00ffffff,
8044 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00ffffff,
8045 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00ffffff,
8046 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00ffffff,
8047 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00ffffff,
8048 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00ffffff,
8049 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00ffffff,
8050 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00ffffff,
8051 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00ffffff,
8052 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00ffffff,
8053 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00ffffff,
8054 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00ffffff,
8055 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00ffffff,
8057 static const float quads[] =
8059 -1.0f, -1.0f, 0.1f,
8060 -1.0f, 0.0f, 0.1f,
8061 0.0f, -1.0f, 0.1f,
8062 0.0f, 0.0f, 0.1f,
8064 0.0f, -1.0f, 0.1f,
8065 0.0f, 0.0f, 0.1f,
8066 1.0f, -1.0f, 0.1f,
8067 1.0f, 0.0f, 0.1f,
8069 0.0f, 0.0f, 0.1f,
8070 0.0f, 1.0f, 0.1f,
8071 1.0f, 0.0f, 0.1f,
8072 1.0f, 1.0f, 0.1f,
8074 -1.0f, 0.0f, 0.1f,
8075 -1.0f, 1.0f, 0.1f,
8076 0.0f, 0.0f, 0.1f,
8077 0.0f, 1.0f, 0.1f,
8079 static const struct
8081 struct vec4 position;
8082 DWORD diffuse;
8084 quad_transformed[] =
8086 {{ 90.0f, 110.0f, 0.1f, 2.0f}, 0x00ffff00},
8087 {{570.0f, 110.0f, 0.1f, 2.0f}, 0x00ffff00},
8088 {{ 90.0f, 300.0f, 0.1f, 2.0f}, 0x00ffff00},
8089 {{570.0f, 300.0f, 0.1f, 2.0f}, 0x00ffff00},
8092 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
8093 0, 0, 640, 480, NULL, NULL, NULL, NULL);
8094 d3d = Direct3DCreate9(D3D_SDK_VERSION);
8095 ok(!!d3d, "Failed to create a D3D object.\n");
8096 if (!(device = create_device(d3d, window, window, TRUE)))
8098 skip("Failed to create a D3D device, skipping tests.\n");
8099 goto done;
8102 memset(&caps, 0, sizeof(caps));
8103 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
8104 ok(hr == D3D_OK, "GetDeviceCaps failed, hr = %08x\n", hr);
8106 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffffffff, 1.0f, 0);
8107 ok(hr == D3D_OK, "Clear failed, hr = %08x\n", hr);
8109 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements_d3dcolor, &dcl_color);
8110 ok(SUCCEEDED(hr), "CreateVertexDeclaration failed (%08x)\n", hr);
8111 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements_short4, &dcl_short);
8112 ok(SUCCEEDED(hr) || hr == E_FAIL, "CreateVertexDeclaration failed (%08x)\n", hr);
8113 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements_float, &dcl_float);
8114 ok(SUCCEEDED(hr), "CreateVertexDeclaration failed (%08x)\n", hr);
8115 if(caps.DeclTypes & D3DDTCAPS_UBYTE4N) {
8116 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements_ubyte4n_2streams, &dcl_ubyte_2);
8117 ok(SUCCEEDED(hr), "CreateVertexDeclaration failed (%08x)\n", hr);
8118 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements_ubyte4n, &dcl_ubyte);
8119 ok(SUCCEEDED(hr), "CreateVertexDeclaration failed (%08x)\n", hr);
8120 } else {
8121 trace("D3DDTCAPS_UBYTE4N not supported\n");
8122 dcl_ubyte_2 = NULL;
8123 dcl_ubyte = NULL;
8125 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements_d3dcolor_2streams, &dcl_color_2);
8126 ok(SUCCEEDED(hr), "CreateVertexDeclaration failed (%08x)\n", hr);
8127 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements_positiont, &dcl_positiont);
8128 ok(SUCCEEDED(hr), "CreateVertexDeclaration failed (%08x)\n", hr);
8130 size = max(sizeof(quad1), max(sizeof(quad2), max(sizeof(quad3), max(sizeof(quad4), sizeof(quads)))));
8131 hr = IDirect3DDevice9_CreateVertexBuffer(device, size,
8132 0, 0, D3DPOOL_MANAGED, &vb, NULL);
8133 ok(hr == D3D_OK, "CreateVertexBuffer failed with %08x\n", hr);
8135 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
8136 ok(SUCCEEDED(hr), "Failed to disable lighting, hr %#x.\n", hr);
8138 hr = IDirect3DDevice9_BeginScene(device);
8139 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
8141 f_ok = FALSE; s_ok = FALSE; ub_ok = FALSE;
8142 if (dcl_color)
8144 hr = IDirect3DDevice9_SetVertexDeclaration(device, dcl_color);
8145 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
8146 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, sizeof(quad1[0]));
8147 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
8150 /* Tests with non-standard fixed function types fail on the refrast. The
8151 * ATI driver partially accepts them, the NVIDIA driver accepts them all.
8152 * All those differences even though we're using software vertex
8153 * processing. Doh! */
8154 if (dcl_ubyte)
8156 hr = IDirect3DDevice9_SetVertexDeclaration(device, dcl_ubyte);
8157 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
8158 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, sizeof(quad2[0]));
8159 ok(hr == D3D_OK || hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
8160 ub_ok = SUCCEEDED(hr);
8163 if (dcl_short)
8165 hr = IDirect3DDevice9_SetVertexDeclaration(device, dcl_short);
8166 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
8167 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad3, sizeof(quad3[0]));
8168 ok(hr == D3D_OK || hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
8169 s_ok = SUCCEEDED(hr);
8172 if (dcl_float)
8174 hr = IDirect3DDevice9_SetVertexDeclaration(device, dcl_float);
8175 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
8176 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad4, sizeof(quad4[0]));
8177 ok(hr == D3D_OK || hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
8178 f_ok = SUCCEEDED(hr);
8181 hr = IDirect3DDevice9_EndScene(device);
8182 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
8184 if(dcl_short) {
8185 color = getPixelColor(device, 480, 360);
8186 ok(color == 0x000000ff || !s_ok,
8187 "D3DDECLTYPE_USHORT4N returned color %08x, expected 0x000000ff\n", color);
8189 if(dcl_ubyte) {
8190 color = getPixelColor(device, 160, 120);
8191 ok(color == 0x0000ffff || !ub_ok,
8192 "D3DDECLTYPE_UBYTE4N returned color %08x, expected 0x0000ffff\n", color);
8194 if(dcl_color) {
8195 color = getPixelColor(device, 160, 360);
8196 ok(color == 0x00ffff00,
8197 "D3DDECLTYPE_D3DCOLOR returned color %08x, expected 0x00ffff00\n", color);
8199 if(dcl_float) {
8200 color = getPixelColor(device, 480, 120);
8201 ok(color == 0x00ff0000 || !f_ok,
8202 "D3DDECLTYPE_FLOAT4 returned color %08x, expected 0x00ff0000\n", color);
8204 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
8206 /* The following test with vertex buffers doesn't serve to find out new
8207 * information from windows. It is a plain regression test because wined3d
8208 * uses different codepaths for attribute conversion with vertex buffers.
8209 * It makes sure that the vertex buffer one works, while the above tests
8210 * whether the immediate mode code works. */
8211 f_ok = FALSE; s_ok = FALSE; ub_ok = FALSE;
8212 hr = IDirect3DDevice9_BeginScene(device);
8213 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
8215 if (dcl_color)
8217 hr = IDirect3DVertexBuffer9_Lock(vb, 0, sizeof(quad1), &data, 0);
8218 ok(SUCCEEDED(hr), "Failed to lock vertex buffer, hr %#x.\n", hr);
8219 memcpy(data, quad1, sizeof(quad1));
8220 hr = IDirect3DVertexBuffer9_Unlock(vb);
8221 ok(SUCCEEDED(hr), "Failed to unlock vertex buffer, hr %#x.\n", hr);
8222 hr = IDirect3DDevice9_SetVertexDeclaration(device, dcl_color);
8223 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
8224 hr = IDirect3DDevice9_SetStreamSource(device, 0, vb, 0, sizeof(quad1[0]));
8225 ok(SUCCEEDED(hr), "Failed to set stream source, hr %#x.\n", hr);
8226 hr = IDirect3DDevice9_DrawPrimitive(device, D3DPT_TRIANGLESTRIP, 0, 2);
8227 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
8230 if (dcl_ubyte)
8232 hr = IDirect3DVertexBuffer9_Lock(vb, 0, sizeof(quad2), &data, 0);
8233 ok(SUCCEEDED(hr), "Failed to lock vertex buffer, hr %#x.\n", hr);
8234 memcpy(data, quad2, sizeof(quad2));
8235 hr = IDirect3DVertexBuffer9_Unlock(vb);
8236 ok(SUCCEEDED(hr), "Failed to unlock vertex buffer, hr %#x.\n", hr);
8237 hr = IDirect3DDevice9_SetVertexDeclaration(device, dcl_ubyte);
8238 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
8239 hr = IDirect3DDevice9_SetStreamSource(device, 0, vb, 0, sizeof(quad2[0]));
8240 ok(SUCCEEDED(hr), "Failed to set stream source, hr %#x.\n", hr);
8241 hr = IDirect3DDevice9_DrawPrimitive(device, D3DPT_TRIANGLESTRIP, 0, 2);
8242 ok(hr == D3D_OK || hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
8243 ub_ok = SUCCEEDED(hr);
8246 if (dcl_short)
8248 hr = IDirect3DVertexBuffer9_Lock(vb, 0, sizeof(quad3), &data, 0);
8249 ok(SUCCEEDED(hr), "Failed to lock vertex buffer, hr %#x.\n", hr);
8250 memcpy(data, quad3, sizeof(quad3));
8251 hr = IDirect3DVertexBuffer9_Unlock(vb);
8252 ok(SUCCEEDED(hr), "Failed to unlock vertex buffer, hr %#x.\n", hr);
8253 hr = IDirect3DDevice9_SetVertexDeclaration(device, dcl_short);
8254 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
8255 hr = IDirect3DDevice9_SetStreamSource(device, 0, vb, 0, sizeof(quad3[0]));
8256 ok(SUCCEEDED(hr), "Failed to set stream source, hr %#x.\n", hr);
8257 hr = IDirect3DDevice9_DrawPrimitive(device, D3DPT_TRIANGLESTRIP, 0, 2);
8258 ok(hr == D3D_OK || hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
8259 s_ok = SUCCEEDED(hr);
8262 if (dcl_float)
8264 hr = IDirect3DVertexBuffer9_Lock(vb, 0, sizeof(quad4), &data, 0);
8265 ok(SUCCEEDED(hr), "Failed to lock vertex buffer, hr %#x.\n", hr);
8266 memcpy(data, quad4, sizeof(quad4));
8267 hr = IDirect3DVertexBuffer9_Unlock(vb);
8268 ok(SUCCEEDED(hr), "Failed to unlock vertex buffer, hr %#x.\n", hr);
8269 hr = IDirect3DDevice9_SetVertexDeclaration(device, dcl_float);
8270 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
8271 hr = IDirect3DDevice9_SetStreamSource(device, 0, vb, 0, sizeof(quad4[0]));
8272 ok(SUCCEEDED(hr), "Failed to set stream source, hr %#x.\n", hr);
8273 hr = IDirect3DDevice9_DrawPrimitive(device, D3DPT_TRIANGLESTRIP, 0, 2);
8274 ok(hr == D3D_OK || hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
8275 f_ok = SUCCEEDED(hr);
8278 hr = IDirect3DDevice9_EndScene(device);
8279 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
8281 hr = IDirect3DDevice9_SetStreamSource(device, 0, NULL, 0, 0);
8282 ok(hr == D3D_OK, "IDirect3DDevice9_SetStreamSource failed with %08x\n", hr);
8283 hr = IDirect3DDevice9_SetVertexDeclaration(device, NULL);
8284 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexDeclaration failed (%08x)\n", hr);
8286 if(dcl_short) {
8287 color = getPixelColor(device, 480, 360);
8288 ok(color == 0x000000ff || !s_ok,
8289 "D3DDECLTYPE_USHORT4N returned color %08x, expected 0x000000ff\n", color);
8291 if(dcl_ubyte) {
8292 color = getPixelColor(device, 160, 120);
8293 ok(color == 0x0000ffff || !ub_ok,
8294 "D3DDECLTYPE_UBYTE4N returned color %08x, expected 0x0000ffff\n", color);
8296 if(dcl_color) {
8297 color = getPixelColor(device, 160, 360);
8298 ok(color == 0x00ffff00,
8299 "D3DDECLTYPE_D3DCOLOR returned color %08x, expected 0x00ffff00\n", color);
8301 if(dcl_float) {
8302 color = getPixelColor(device, 480, 120);
8303 ok(color == 0x00ff0000 || !f_ok,
8304 "D3DDECLTYPE_FLOAT4 returned color %08x, expected 0x00ff0000\n", color);
8306 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
8308 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff0000ff, 0.0, 0);
8309 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
8311 hr = IDirect3DVertexBuffer9_Lock(vb, 0, sizeof(quad_transformed), &data, 0);
8312 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Lock failed with %08x\n", hr);
8313 memcpy(data, quad_transformed, sizeof(quad_transformed));
8314 hr = IDirect3DVertexBuffer9_Unlock(vb);
8315 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Unlock failed (%08x)\n", hr);
8317 hr = IDirect3DDevice9_SetVertexDeclaration(device, dcl_positiont);
8318 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexDeclaration failed with %08x\n", hr);
8320 hr = IDirect3DDevice9_BeginScene(device);
8321 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
8322 hr = IDirect3DDevice9_SetStreamSource(device, 0, vb, 0, sizeof(quad_transformed[0]));
8323 ok(SUCCEEDED(hr), "Failed to set stream source, hr %#x.\n", hr);
8324 hr = IDirect3DDevice9_DrawPrimitive(device, D3DPT_TRIANGLESTRIP, 0, 2);
8325 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
8326 hr = IDirect3DDevice9_EndScene(device);
8327 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
8329 color = getPixelColor(device, 88, 108);
8330 ok(color == 0x000000ff,
8331 "pixel 88/108 has color %08x, expected 0x000000ff\n", color);
8332 color = getPixelColor(device, 92, 108);
8333 ok(color == 0x000000ff,
8334 "pixel 92/108 has color %08x, expected 0x000000ff\n", color);
8335 color = getPixelColor(device, 88, 112);
8336 ok(color == 0x000000ff,
8337 "pixel 88/112 has color %08x, expected 0x000000ff\n", color);
8338 color = getPixelColor(device, 92, 112);
8339 ok(color == 0x00ffff00,
8340 "pixel 92/112 has color %08x, expected 0x00ffff00\n", color);
8342 color = getPixelColor(device, 568, 108);
8343 ok(color == 0x000000ff,
8344 "pixel 568/108 has color %08x, expected 0x000000ff\n", color);
8345 color = getPixelColor(device, 572, 108);
8346 ok(color == 0x000000ff,
8347 "pixel 572/108 has color %08x, expected 0x000000ff\n", color);
8348 color = getPixelColor(device, 568, 112);
8349 ok(color == 0x00ffff00,
8350 "pixel 568/112 has color %08x, expected 0x00ffff00\n", color);
8351 color = getPixelColor(device, 572, 112);
8352 ok(color == 0x000000ff,
8353 "pixel 572/112 has color %08x, expected 0x000000ff\n", color);
8355 color = getPixelColor(device, 88, 298);
8356 ok(color == 0x000000ff,
8357 "pixel 88/298 has color %08x, expected 0x000000ff\n", color);
8358 color = getPixelColor(device, 92, 298);
8359 ok(color == 0x00ffff00,
8360 "pixel 92/298 has color %08x, expected 0x00ffff00\n", color);
8361 color = getPixelColor(device, 88, 302);
8362 ok(color == 0x000000ff,
8363 "pixel 88/302 has color %08x, expected 0x000000ff\n", color);
8364 color = getPixelColor(device, 92, 302);
8365 ok(color == 0x000000ff,
8366 "pixel 92/302 has color %08x, expected 0x000000ff\n", color);
8368 color = getPixelColor(device, 568, 298);
8369 ok(color == 0x00ffff00,
8370 "pixel 568/298 has color %08x, expected 0x00ffff00\n", color);
8371 color = getPixelColor(device, 572, 298);
8372 ok(color == 0x000000ff,
8373 "pixel 572/298 has color %08x, expected 0x000000ff\n", color);
8374 color = getPixelColor(device, 568, 302);
8375 ok(color == 0x000000ff,
8376 "pixel 568/302 has color %08x, expected 0x000000ff\n", color);
8377 color = getPixelColor(device, 572, 302);
8378 ok(color == 0x000000ff,
8379 "pixel 572/302 has color %08x, expected 0x000000ff\n", color);
8381 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
8383 /* This test is pointless without those two declarations: */
8384 if((!dcl_color_2) || (!dcl_ubyte_2)) {
8385 skip("color-ubyte switching test declarations aren't supported\n");
8386 goto out;
8389 hr = IDirect3DVertexBuffer9_Lock(vb, 0, sizeof(quads), &data, 0);
8390 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Lock failed with %08x\n", hr);
8391 memcpy(data, quads, sizeof(quads));
8392 hr = IDirect3DVertexBuffer9_Unlock(vb);
8393 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Unlock failed (%08x)\n", hr);
8394 hr = IDirect3DDevice9_CreateVertexBuffer(device, sizeof(colors),
8395 0, 0, D3DPOOL_MANAGED, &vb2, NULL);
8396 ok(hr == D3D_OK, "CreateVertexBuffer failed with %08x\n", hr);
8397 hr = IDirect3DVertexBuffer9_Lock(vb2, 0, sizeof(colors), &data, 0);
8398 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Lock failed with %08x\n", hr);
8399 memcpy(data, colors, sizeof(colors));
8400 hr = IDirect3DVertexBuffer9_Unlock(vb2);
8401 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Unlock failed (%08x)\n", hr);
8403 for(i = 0; i < 2; i++) {
8404 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffffffff, 0.0, 0);
8405 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
8407 hr = IDirect3DDevice9_SetStreamSource(device, 0, vb, 0, sizeof(float) * 3);
8408 ok(hr == D3D_OK, "IDirect3DDevice9_SetStreamSource failed with %08x\n", hr);
8409 if(i == 0) {
8410 hr = IDirect3DDevice9_SetStreamSource(device, 1, vb2, 0, sizeof(DWORD) * 4);
8411 } else {
8412 hr = IDirect3DDevice9_SetStreamSource(device, 1, vb2, 8, sizeof(DWORD) * 4);
8414 ok(hr == D3D_OK, "IDirect3DDevice9_SetStreamSource failed with %08x\n", hr);
8416 hr = IDirect3DDevice9_BeginScene(device);
8417 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
8419 hr = IDirect3DDevice9_SetVertexDeclaration(device, dcl_ubyte_2);
8420 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
8421 hr = IDirect3DDevice9_DrawPrimitive(device, D3DPT_TRIANGLESTRIP, 0, 2);
8422 ok(hr == D3D_OK || hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
8423 ub_ok = SUCCEEDED(hr);
8425 hr = IDirect3DDevice9_SetVertexDeclaration(device, dcl_color_2);
8426 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
8427 hr = IDirect3DDevice9_DrawPrimitive(device, D3DPT_TRIANGLESTRIP, 4, 2);
8428 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
8430 hr = IDirect3DDevice9_SetVertexDeclaration(device, dcl_ubyte_2);
8431 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
8432 hr = IDirect3DDevice9_DrawPrimitive(device, D3DPT_TRIANGLESTRIP, 8, 2);
8433 ok(hr == D3D_OK || hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
8434 ub_ok = (SUCCEEDED(hr) && ub_ok);
8436 hr = IDirect3DDevice9_EndScene(device);
8437 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
8439 if(i == 0) {
8440 color = getPixelColor(device, 480, 360);
8441 ok(color == 0x00ff0000,
8442 "D3DDECLTYPE_D3DCOLOR returned color %08x, expected 0x00ff0000\n", color);
8443 color = getPixelColor(device, 160, 120);
8444 ok(color == 0x00ffffff,
8445 "Unused quad returned color %08x, expected 0x00ffffff\n", color);
8446 color = getPixelColor(device, 160, 360);
8447 ok(color == 0x000000ff || !ub_ok,
8448 "D3DDECLTYPE_UBYTE4N returned color %08x, expected 0x000000ff\n", color);
8449 color = getPixelColor(device, 480, 120);
8450 ok(color == 0x000000ff || !ub_ok,
8451 "D3DDECLTYPE_UBYTE4N returned color %08x, expected 0x000000ff\n", color);
8452 } else {
8453 color = getPixelColor(device, 480, 360);
8454 ok(color == 0x000000ff,
8455 "D3DDECLTYPE_D3DCOLOR returned color %08x, expected 0x000000ff\n", color);
8456 color = getPixelColor(device, 160, 120);
8457 ok(color == 0x00ffffff,
8458 "Unused quad returned color %08x, expected 0x00ffffff\n", color);
8459 color = getPixelColor(device, 160, 360);
8460 ok(color == 0x00ff0000 || !ub_ok,
8461 "D3DDECLTYPE_UBYTE4N returned color %08x, expected 0x00ff0000\n", color);
8462 color = getPixelColor(device, 480, 120);
8463 ok(color == 0x00ff0000 || !ub_ok,
8464 "D3DDECLTYPE_UBYTE4N returned color %08x, expected 0x00ff0000\n", color);
8466 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
8469 IDirect3DVertexBuffer9_Release(vb2);
8470 out:
8471 IDirect3DVertexBuffer9_Release(vb);
8472 if(dcl_float) IDirect3DVertexDeclaration9_Release(dcl_float);
8473 if(dcl_short) IDirect3DVertexDeclaration9_Release(dcl_short);
8474 if(dcl_ubyte) IDirect3DVertexDeclaration9_Release(dcl_ubyte);
8475 if(dcl_color) IDirect3DVertexDeclaration9_Release(dcl_color);
8476 if(dcl_color_2) IDirect3DVertexDeclaration9_Release(dcl_color_2);
8477 if(dcl_ubyte_2) IDirect3DVertexDeclaration9_Release(dcl_ubyte_2);
8478 if(dcl_positiont) IDirect3DVertexDeclaration9_Release(dcl_positiont);
8479 refcount = IDirect3DDevice9_Release(device);
8480 ok(!refcount, "Device has %u references left.\n", refcount);
8481 done:
8482 IDirect3D9_Release(d3d);
8483 DestroyWindow(window);
8486 static void test_vshader_float16(void)
8488 IDirect3DVertexDeclaration9 *vdecl = NULL;
8489 IDirect3DVertexBuffer9 *buffer = NULL;
8490 IDirect3DVertexShader9 *shader;
8491 IDirect3DDevice9 *device;
8492 IDirect3D9 *d3d;
8493 ULONG refcount;
8494 D3DCAPS9 caps;
8495 DWORD color;
8496 HWND window;
8497 void *data;
8498 HRESULT hr;
8500 static const D3DVERTEXELEMENT9 decl_elements[] =
8502 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
8503 {0, 12, D3DDECLTYPE_FLOAT16_4,D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR, 0},
8504 D3DDECL_END()
8506 static const DWORD shader_code[] =
8508 0xfffe0101, /* vs_1_1 */
8509 0x0000001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
8510 0x0000001f, 0x8000000a, 0x900f0001, /* dcl_color v1 */
8511 0x00000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
8512 0x00000001, 0xd00f0000, 0x90e40001, /* mov oD0, v1 */
8513 0x0000ffff,
8515 static const struct vertex_float16color
8517 float x, y, z;
8518 DWORD c1, c2;
8520 quad[] =
8522 { -1.0, -1.0, 0.1, 0x3c000000, 0x00000000 }, /* green */
8523 { -1.0, 0.0, 0.1, 0x3c000000, 0x00000000 },
8524 { 0.0, -1.0, 0.1, 0x3c000000, 0x00000000 },
8525 { 0.0, 0.0, 0.1, 0x3c000000, 0x00000000 },
8527 { 0.0, -1.0, 0.1, 0x00003c00, 0x00000000 }, /* red */
8528 { 0.0, 0.0, 0.1, 0x00003c00, 0x00000000 },
8529 { 1.0, -1.0, 0.1, 0x00003c00, 0x00000000 },
8530 { 1.0, 0.0, 0.1, 0x00003c00, 0x00000000 },
8532 { 0.0, 0.0, 0.1, 0x00000000, 0x00003c00 }, /* blue */
8533 { 0.0, 1.0, 0.1, 0x00000000, 0x00003c00 },
8534 { 1.0, 0.0, 0.1, 0x00000000, 0x00003c00 },
8535 { 1.0, 1.0, 0.1, 0x00000000, 0x00003c00 },
8537 { -1.0, 0.0, 0.1, 0x00000000, 0x3c000000 }, /* alpha */
8538 { -1.0, 1.0, 0.1, 0x00000000, 0x3c000000 },
8539 { 0.0, 0.0, 0.1, 0x00000000, 0x3c000000 },
8540 { 0.0, 1.0, 0.1, 0x00000000, 0x3c000000 },
8543 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
8544 0, 0, 640, 480, NULL, NULL, NULL, NULL);
8545 d3d = Direct3DCreate9(D3D_SDK_VERSION);
8546 ok(!!d3d, "Failed to create a D3D object.\n");
8547 if (!(device = create_device(d3d, window, window, TRUE)))
8549 skip("Failed to create a D3D device, skipping tests.\n");
8550 goto done;
8553 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
8554 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
8555 if (caps.VertexShaderVersion < D3DVS_VERSION(3, 0))
8557 skip("No vs_3_0 support, skipping tests.\n");
8558 IDirect3DDevice9_Release(device);
8559 goto done;
8562 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff102030, 1.0f, 0);
8563 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed, hr=%08x\n", hr);
8565 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements, &vdecl);
8566 ok(SUCCEEDED(hr), "IDirect3DDevice9_CreateVertexDeclaration failed hr=%08x\n", hr);
8567 hr = IDirect3DDevice9_CreateVertexShader(device, shader_code, &shader);
8568 ok(SUCCEEDED(hr), "IDirect3DDevice9_CreateVertexShader failed hr=%08x\n", hr);
8569 hr = IDirect3DDevice9_SetVertexShader(device, shader);
8570 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetVertexShader failed hr=%08x\n", hr);
8572 hr = IDirect3DDevice9_BeginScene(device);
8573 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
8574 hr = IDirect3DDevice9_SetVertexDeclaration(device, vdecl);
8575 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
8576 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad + 0, sizeof(quad[0]));
8577 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
8578 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad + 4, sizeof(quad[0]));
8579 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
8580 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad + 8, sizeof(quad[0]));
8581 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
8582 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad + 12, sizeof(quad[0]));
8583 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
8584 hr = IDirect3DDevice9_EndScene(device);
8585 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
8587 color = getPixelColor(device, 480, 360);
8588 ok(color == 0x00ff0000,
8589 "Input 0x00003c00, 0x00000000 returned color %08x, expected 0x00ff0000\n", color);
8590 color = getPixelColor(device, 160, 120);
8591 ok(color == 0x00000000,
8592 "Input 0x00000000, 0x3c000000 returned color %08x, expected 0x00000000\n", color);
8593 color = getPixelColor(device, 160, 360);
8594 ok(color == 0x0000ff00,
8595 "Input 0x3c000000, 0x00000000 returned color %08x, expected 0x0000ff00\n", color);
8596 color = getPixelColor(device, 480, 120);
8597 ok(color == 0x000000ff,
8598 "Input 0x00000000, 0x00003c00 returned color %08x, expected 0x000000ff\n", color);
8599 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
8601 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff102030, 0.0, 0);
8602 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed, hr=%08x\n", hr);
8604 hr = IDirect3DDevice9_CreateVertexBuffer(device, sizeof(quad), 0, 0,
8605 D3DPOOL_MANAGED, &buffer, NULL);
8606 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexBuffer failed, hr=%08x\n", hr);
8607 hr = IDirect3DVertexBuffer9_Lock(buffer, 0, sizeof(quad), &data, 0);
8608 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Lock failed, hr=%08x\n", hr);
8609 memcpy(data, quad, sizeof(quad));
8610 hr = IDirect3DVertexBuffer9_Unlock(buffer);
8611 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Unlock failed, hr=%08x\n", hr);
8612 hr = IDirect3DDevice9_SetStreamSource(device, 0, buffer, 0, sizeof(quad[0]));
8613 ok(hr == D3D_OK, "IDirect3DDevice9_SetStreamSource failed, hr=%08x\n", hr);
8615 hr = IDirect3DDevice9_BeginScene(device);
8616 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
8617 hr = IDirect3DDevice9_DrawPrimitive(device, D3DPT_TRIANGLESTRIP, 0, 2);
8618 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
8619 hr = IDirect3DDevice9_DrawPrimitive(device, D3DPT_TRIANGLESTRIP, 4, 2);
8620 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
8621 hr = IDirect3DDevice9_DrawPrimitive(device, D3DPT_TRIANGLESTRIP, 8, 2);
8622 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
8623 hr = IDirect3DDevice9_DrawPrimitive(device, D3DPT_TRIANGLESTRIP, 12, 2);
8624 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
8625 hr = IDirect3DDevice9_EndScene(device);
8626 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
8628 color = getPixelColor(device, 480, 360);
8629 ok(color == 0x00ff0000,
8630 "Input 0x00003c00, 0x00000000 returned color %08x, expected 0x00ff0000\n", color);
8631 color = getPixelColor(device, 160, 120);
8632 ok(color == 0x00000000,
8633 "Input 0x00000000, 0x3c000000 returned color %08x, expected 0x00000000\n", color);
8634 color = getPixelColor(device, 160, 360);
8635 ok(color == 0x0000ff00,
8636 "Input 0x3c000000, 0x00000000 returned color %08x, expected 0x0000ff00\n", color);
8637 color = getPixelColor(device, 480, 120);
8638 ok(color == 0x000000ff,
8639 "Input 0x00000000, 0x00003c00 returned color %08x, expected 0x000000ff\n", color);
8640 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
8642 IDirect3DVertexDeclaration9_Release(vdecl);
8643 IDirect3DVertexShader9_Release(shader);
8644 IDirect3DVertexBuffer9_Release(buffer);
8645 refcount = IDirect3DDevice9_Release(device);
8646 ok(!refcount, "Device has %u references left.\n", refcount);
8647 done:
8648 IDirect3D9_Release(d3d);
8649 DestroyWindow(window);
8652 static void conditional_np2_repeat_test(void)
8654 IDirect3DTexture9 *texture;
8655 IDirect3DDevice9 *device;
8656 D3DLOCKED_RECT rect;
8657 unsigned int x, y;
8658 DWORD *dst, color;
8659 IDirect3D9 *d3d;
8660 ULONG refcount;
8661 D3DCAPS9 caps;
8662 HWND window;
8663 HRESULT hr;
8665 static const float quad[] =
8667 -1.0f, -1.0f, 0.1f, -0.2f, -0.2f,
8668 -1.0f, 1.0f, 0.1f, -0.2f, 1.2f,
8669 1.0f, -1.0f, 0.1f, 1.2f, -0.2f,
8670 1.0f, 1.0f, 0.1f, 1.2f, 1.2f,
8673 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
8674 0, 0, 640, 480, NULL, NULL, NULL, NULL);
8675 d3d = Direct3DCreate9(D3D_SDK_VERSION);
8676 ok(!!d3d, "Failed to create a D3D object.\n");
8677 if (!(device = create_device(d3d, window, window, TRUE)))
8679 skip("Failed to create a D3D device, skipping tests.\n");
8680 goto done;
8683 memset(&caps, 0, sizeof(caps));
8684 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
8685 ok(hr == D3D_OK, "IDirect3DDevice9_GetDeviceCaps failed hr=%08x\n", hr);
8686 if (caps.TextureCaps & D3DPTEXTURECAPS_NONPOW2CONDITIONAL)
8688 /* NP2 conditional requires the POW2 flag. Check that while we're at it */
8689 ok(caps.TextureCaps & D3DPTEXTURECAPS_POW2,
8690 "Card has conditional NP2 support without power of two restriction set\n");
8692 else if (caps.TextureCaps & D3DPTEXTURECAPS_POW2)
8694 skip("No conditional NP2 support, skipping conditional NP2 tests\n");
8695 IDirect3DDevice9_Release(device);
8696 goto done;
8698 else
8700 skip("Card has unconditional NP2 support, skipping conditional NP2 tests\n");
8701 IDirect3DDevice9_Release(device);
8702 goto done;
8705 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff000000, 1.0f, 0);
8706 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed, hr=%08x\n", hr);
8708 hr = IDirect3DDevice9_CreateTexture(device, 10, 10, 1, 0, D3DFMT_X8R8G8B8, D3DPOOL_MANAGED, &texture, NULL);
8709 ok(hr == D3D_OK, "IDirect3DDevice9_CreateTexture failed hr=%08x\n", hr);
8711 memset(&rect, 0, sizeof(rect));
8712 hr = IDirect3DTexture9_LockRect(texture, 0, &rect, NULL, 0);
8713 ok(hr == D3D_OK, "IDirect3DTexture9_LockRect failed hr=%08x\n", hr);
8714 for(y = 0; y < 10; y++) {
8715 for(x = 0; x < 10; x++) {
8716 dst = (DWORD *) ((BYTE *) rect.pBits + y * rect.Pitch + x * sizeof(DWORD));
8717 if(x == 0 || x == 9 || y == 0 || y == 9) {
8718 *dst = 0x00ff0000;
8719 } else {
8720 *dst = 0x000000ff;
8724 hr = IDirect3DTexture9_UnlockRect(texture, 0);
8725 ok(hr == D3D_OK, "IDirect3DTexture9_UnlockRect failed hr=%08x\n", hr);
8727 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *) texture);
8728 ok(hr == D3D_OK, "IDirect3DDevice9_SetTexture failed hr=%08x\n", hr);
8729 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
8730 ok(SUCCEEDED(hr), "Failed to disable lighting, hr %#x.\n", hr);
8731 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_ADDRESSU, D3DTADDRESS_WRAP);
8732 ok(hr == D3D_OK, "IDirect3DDevice9_SetSamplerState failed hr=%08x\n", hr);
8733 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_ADDRESSV, D3DTADDRESS_WRAP);
8734 ok(hr == D3D_OK, "IDirect3DDevice9_SetSamplerState failed hr=%08x\n", hr);
8735 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1);
8736 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexDeclaration failed, hr=%08x\n", hr);
8738 hr = IDirect3DDevice9_BeginScene(device);
8739 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
8740 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(float) * 5);
8741 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
8742 hr = IDirect3DDevice9_EndScene(device);
8743 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
8745 color = getPixelColor(device, 1, 1);
8746 ok(color == 0x00ff0000, "NP2: Pixel 1, 1 has color %08x, expected 0x00ff0000\n", color);
8747 color = getPixelColor(device, 639, 479);
8748 ok(color == 0x00ff0000, "NP2: Pixel 639, 479 has color %08x, expected 0x00ff0000\n", color);
8750 color = getPixelColor(device, 135, 101);
8751 ok(color == 0x00ff0000, "NP2: Pixel 135, 101 has color %08x, expected 0x00ff0000\n", color);
8752 color = getPixelColor(device, 140, 101);
8753 ok(color == 0x00ff0000, "NP2: Pixel 140, 101 has color %08x, expected 0x00ff0000\n", color);
8754 color = getPixelColor(device, 135, 105);
8755 ok(color == 0x00ff0000, "NP2: Pixel 135, 105 has color %08x, expected 0x00ff0000\n", color);
8756 color = getPixelColor(device, 140, 105);
8757 ok(color == 0x000000ff, "NP2: Pixel 140, 105 has color %08x, expected 0x000000ff\n", color);
8759 color = getPixelColor(device, 135, 376);
8760 ok(color == 0x00ff0000, "NP2: Pixel 135, 376 has color %08x, expected 0x00ff0000\n", color);
8761 color = getPixelColor(device, 140, 376);
8762 ok(color == 0x000000ff, "NP2: Pixel 140, 376 has color %08x, expected 0x000000ff\n", color);
8763 color = getPixelColor(device, 135, 379);
8764 ok(color == 0x00ff0000, "NP2: Pixel 135, 379 has color %08x, expected 0x00ff0000\n", color);
8765 color = getPixelColor(device, 140, 379);
8766 ok(color == 0x00ff0000, "NP2: Pixel 140, 379 has color %08x, expected 0x00ff0000\n", color);
8768 color = getPixelColor(device, 500, 101);
8769 ok(color == 0x00ff0000, "NP2: Pixel 500, 101 has color %08x, expected 0x00ff0000\n", color);
8770 color = getPixelColor(device, 504, 101);
8771 ok(color == 0x00ff0000, "NP2: Pixel 504, 101 has color %08x, expected 0x00ff0000\n", color);
8772 color = getPixelColor(device, 500, 105);
8773 ok(color == 0x000000ff, "NP2: Pixel 500, 105 has color %08x, expected 0x000000ff\n", color);
8774 color = getPixelColor(device, 504, 105);
8775 ok(color == 0x00ff0000, "NP2: Pixel 504, 105 has color %08x, expected 0x00ff0000\n", color);
8777 color = getPixelColor(device, 500, 376);
8778 ok(color == 0x000000ff, "NP2: Pixel 500, 376 has color %08x, expected 0x000000ff\n", color);
8779 color = getPixelColor(device, 504, 376);
8780 ok(color == 0x00ff0000, "NP2: Pixel 504, 376 has color %08x, expected 0x00ff0000\n", color);
8781 color = getPixelColor(device, 500, 380);
8782 ok(color == 0x00ff0000, "NP2: Pixel 500, 380 has color %08x, expected 0x00ff0000\n", color);
8783 color = getPixelColor(device, 504, 380);
8784 ok(color == 0x00ff0000, "NP2: Pixel 504, 380 has color %08x, expected 0x00ff0000\n", color);
8786 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
8788 IDirect3DTexture9_Release(texture);
8789 refcount = IDirect3DDevice9_Release(device);
8790 ok(!refcount, "Device has %u references left.\n", refcount);
8791 done:
8792 IDirect3D9_Release(d3d);
8793 DestroyWindow(window);
8796 static void vface_register_test(void)
8798 IDirect3DSurface9 *surface, *backbuffer;
8799 IDirect3DVertexShader9 *vshader;
8800 IDirect3DPixelShader9 *shader;
8801 IDirect3DTexture9 *texture;
8802 IDirect3DDevice9 *device;
8803 IDirect3D9 *d3d;
8804 ULONG refcount;
8805 D3DCAPS9 caps;
8806 DWORD color;
8807 HWND window;
8808 HRESULT hr;
8810 static const DWORD shader_code[] =
8812 0xffff0300, /* ps_3_0 */
8813 0x05000051, 0xa00f0000, 0x00000000, 0x3f800000, 0x00000000, 0x00000000, /* def c0, 0.0, 1.0, 0.0, 0.0 */
8814 0x05000051, 0xa00f0001, 0x3f800000, 0x00000000, 0x00000000, 0x00000000, /* def c1, 1.0, 0.0, 0.0, 0.0 */
8815 0x0200001f, 0x80000000, 0x900f1001, /* dcl vFace */
8816 0x02000001, 0x800f0001, 0xa0e40001, /* mov r1, c1 */
8817 0x04000058, 0x800f0000, 0x90e41001, 0xa0e40000, 0x80e40001, /* cmp r0, vFace, c0, r1 */
8818 0x02000001, 0x800f0800, 0x80e40000, /* mov oC0, r0 */
8819 0x0000ffff /* END */
8821 static const DWORD vshader_code[] =
8823 0xfffe0300, /* vs_3_0 */
8824 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
8825 0x0200001f, 0x80000000, 0xe00f0000, /* dcl_position o0 */
8826 0x02000001, 0xe00f0000, 0x90e40000, /* mov o0, v0 */
8827 0x0000ffff /* end */
8829 static const float quad[] =
8831 -1.0f, -1.0f, 0.1f,
8832 1.0f, -1.0f, 0.1f,
8833 -1.0f, 0.0f, 0.1f,
8835 1.0f, -1.0f, 0.1f,
8836 1.0f, 0.0f, 0.1f,
8837 -1.0f, 0.0f, 0.1f,
8839 -1.0f, 0.0f, 0.1f,
8840 -1.0f, 1.0f, 0.1f,
8841 1.0f, 0.0f, 0.1f,
8843 1.0f, 0.0f, 0.1f,
8844 -1.0f, 1.0f, 0.1f,
8845 1.0f, 1.0f, 0.1f,
8847 static const float blit[] =
8849 0.0f, -1.0f, 0.1f, 0.0f, 0.0f,
8850 1.0f, -1.0f, 0.1f, 1.0f, 0.0f,
8851 0.0f, 1.0f, 0.1f, 0.0f, 1.0f,
8852 1.0f, 1.0f, 0.1f, 1.0f, 1.0f,
8855 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
8856 0, 0, 640, 480, NULL, NULL, NULL, NULL);
8857 d3d = Direct3DCreate9(D3D_SDK_VERSION);
8858 ok(!!d3d, "Failed to create a D3D object.\n");
8859 if (!(device = create_device(d3d, window, window, TRUE)))
8861 skip("Failed to create a D3D device, skipping tests.\n");
8862 goto done;
8865 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
8866 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
8867 if (caps.PixelShaderVersion < D3DPS_VERSION(3, 0) || caps.VertexShaderVersion < D3DVS_VERSION(3, 0))
8869 skip("No shader model 3 support, skipping tests.\n");
8870 IDirect3DDevice9_Release(device);
8871 goto done;
8874 hr = IDirect3DDevice9_CreateVertexShader(device, vshader_code, &vshader);
8875 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader failed hr=%08x\n", hr);
8876 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code, &shader);
8877 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader failed hr=%08x\n", hr);
8878 hr = IDirect3DDevice9_CreateTexture(device, 128, 128, 1, D3DUSAGE_RENDERTARGET, D3DFMT_X8R8G8B8, D3DPOOL_DEFAULT, &texture, NULL);
8879 ok(hr == D3D_OK, "IDirect3DDevice9_CreateTexture failed hr=%08x\n", hr);
8880 hr = IDirect3DTexture9_GetSurfaceLevel(texture, 0, &surface);
8881 ok(hr == D3D_OK, "IDirect3DTexture9_GetSurfaceLevel failed hr=%08x\n", hr);
8882 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_CULLMODE, D3DCULL_NONE);
8883 ok(SUCCEEDED(hr), "Failed to set cull mode, hr %#x.\n", hr);
8884 hr = IDirect3DDevice9_SetPixelShader(device, shader);
8885 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShader failed hr=%08x\n", hr);
8886 hr = IDirect3DDevice9_SetVertexShader(device, vshader);
8887 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexShader failed hr=%08x\n", hr);
8888 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ);
8889 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed hr=%08x\n", hr);
8890 hr = IDirect3DDevice9_GetBackBuffer(device, 0, 0, D3DBACKBUFFER_TYPE_MONO, &backbuffer);
8891 ok(hr == D3D_OK, "IDirect3DDevice9_GetBackBuffer failed hr=%08x\n", hr);
8893 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff0000ff, 1.0f, 0);
8894 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed, hr=%08x\n", hr);
8896 hr = IDirect3DDevice9_BeginScene(device);
8897 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
8899 /* First, draw to the texture and the back buffer to test both offscreen and onscreen cases */
8900 hr = IDirect3DDevice9_SetRenderTarget(device, 0, surface);
8901 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
8902 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff0000ff, 0.0, 0);
8903 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
8904 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLELIST, 4, quad, sizeof(float) * 3);
8905 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
8906 hr = IDirect3DDevice9_SetRenderTarget(device, 0, backbuffer);
8907 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
8908 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLELIST, 4, quad, sizeof(float) * 3);
8909 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
8911 /* Blit the texture onto the back buffer to make it visible */
8912 hr = IDirect3DDevice9_SetVertexShader(device, NULL);
8913 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
8914 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
8915 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
8916 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *) texture);
8917 ok(SUCCEEDED(hr), "Failed to set texture, hr %#x.\n", hr);
8918 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
8919 ok(SUCCEEDED(hr), "Failed to set texture stage state, hr %#x.\n", hr);
8920 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
8921 ok(SUCCEEDED(hr), "Failed to set texture stage state, hr %#x.\n", hr);
8922 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1);
8923 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
8924 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, blit, sizeof(float) * 5);
8925 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
8927 hr = IDirect3DDevice9_EndScene(device);
8928 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
8930 color = getPixelColor(device, 160, 360);
8931 ok(color == 0x00ff0000, "vFace: Onscreen rendered front facing quad has color 0x%08x, expected 0x00ff0000\n", color);
8932 color = getPixelColor(device, 160, 120);
8933 ok(color == 0x0000ff00, "vFace: Onscreen rendered back facing quad has color 0x%08x, expected 0x0000ff00\n", color);
8934 color = getPixelColor(device, 480, 360);
8935 ok(color == 0x0000ff00, "vFace: Offscreen rendered back facing quad has color 0x%08x, expected 0x0000ff00\n", color);
8936 color = getPixelColor(device, 480, 120);
8937 ok(color == 0x00ff0000, "vFace: Offscreen rendered front facing quad has color 0x%08x, expected 0x00ff0000\n", color);
8938 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
8939 ok(SUCCEEDED(hr), "Present failed, hr %#x.\n", hr);
8941 IDirect3DPixelShader9_Release(shader);
8942 IDirect3DVertexShader9_Release(vshader);
8943 IDirect3DSurface9_Release(surface);
8944 IDirect3DSurface9_Release(backbuffer);
8945 IDirect3DTexture9_Release(texture);
8946 refcount = IDirect3DDevice9_Release(device);
8947 ok(!refcount, "Device has %u references left.\n", refcount);
8948 done:
8949 IDirect3D9_Release(d3d);
8950 DestroyWindow(window);
8953 static void fixed_function_bumpmap_test(void)
8955 IDirect3DVertexDeclaration9 *vertex_declaration;
8956 IDirect3DTexture9 *texture, *tex1, *tex2;
8957 D3DLOCKED_RECT locked_rect;
8958 IDirect3DDevice9 *device;
8959 BOOL L6V5U5_supported;
8960 float scale, offset;
8961 IDirect3D9 *d3d;
8962 unsigned int i;
8963 D3DCOLOR color;
8964 ULONG refcount;
8965 D3DCAPS9 caps;
8966 HWND window;
8967 HRESULT hr;
8969 static const float quad[][7] =
8971 {-1.0f, -1.0f, 0.1f, 0.0f, 0.0f, 0.0f, 0.0f},
8972 {-1.0f, 1.0f, 0.1f, 0.0f, 1.0f, 0.0f, 1.0f},
8973 { 1.0f, -1.0f, 0.1f, 1.0f, 0.0f, 1.0f, 0.0f},
8974 { 1.0f, 1.0f, 0.1f, 1.0f, 1.0f, 1.0f, 1.0f},
8976 static const D3DVERTEXELEMENT9 decl_elements[] =
8978 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
8979 {0, 12, D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
8980 {0, 20, D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 1},
8981 D3DDECL_END()
8983 /* use asymmetric matrix to test loading */
8984 static const float bumpenvmat[4] = {0.0f, 0.5f, -0.5f, 0.0f};
8986 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
8987 0, 0, 640, 480, NULL, NULL, NULL, NULL);
8988 d3d = Direct3DCreate9(D3D_SDK_VERSION);
8989 ok(!!d3d, "Failed to create a D3D object.\n");
8990 if (!(device = create_device(d3d, window, window, TRUE)))
8992 skip("Failed to create a D3D device, skipping tests.\n");
8993 goto done;
8996 memset(&caps, 0, sizeof(caps));
8997 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
8998 ok(hr == D3D_OK, "IDirect3DDevice9_GetDeviceCaps failed hr=%08x\n", hr);
8999 if (!(caps.TextureOpCaps & D3DTEXOPCAPS_BUMPENVMAP))
9001 skip("D3DTEXOPCAPS_BUMPENVMAP not set, skipping bumpmap tests\n");
9002 IDirect3DDevice9_Release(device);
9003 goto done;
9006 /* This check is disabled, some Windows drivers do not handle
9007 * D3DUSAGE_QUERY_LEGACYBUMPMAP properly. They report that it is not
9008 * supported, but after that bump mapping works properly. So just test if
9009 * the format is generally supported, and check the BUMPENVMAP flag. */
9010 L6V5U5_supported = SUCCEEDED(IDirect3D9_CheckDeviceFormat(d3d, 0, D3DDEVTYPE_HAL,
9011 D3DFMT_X8R8G8B8, 0, D3DRTYPE_TEXTURE, D3DFMT_L6V5U5));
9012 if (FAILED(IDirect3D9_CheckDeviceFormat(d3d, 0, D3DDEVTYPE_HAL,
9013 D3DFMT_X8R8G8B8, 0, D3DRTYPE_TEXTURE, D3DFMT_V8U8)))
9015 skip("D3DFMT_V8U8 not supported for legacy bump mapping\n");
9016 IDirect3DDevice9_Release(device);
9017 return;
9020 /* Generate the textures */
9021 generate_bumpmap_textures(device);
9023 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_BUMPENVMAT00, *(LPDWORD)&bumpenvmat[0]);
9024 ok(SUCCEEDED(hr), "SetTextureStageState failed (%08x)\n", hr);
9025 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_BUMPENVMAT01, *(LPDWORD)&bumpenvmat[1]);
9026 ok(SUCCEEDED(hr), "SetTextureStageState failed (%08x)\n", hr);
9027 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_BUMPENVMAT10, *(LPDWORD)&bumpenvmat[2]);
9028 ok(SUCCEEDED(hr), "SetTextureStageState failed (%08x)\n", hr);
9029 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_BUMPENVMAT11, *(LPDWORD)&bumpenvmat[3]);
9030 ok(SUCCEEDED(hr), "SetTextureStageState failed (%08x)\n", hr);
9032 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_BUMPENVMAP);
9033 ok(SUCCEEDED(hr), "SetTextureStageState failed (%08x)\n", hr);
9034 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_TEXTURE );
9035 ok(SUCCEEDED(hr), "SetTextureStageState failed (%08x)\n", hr);
9036 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG2, D3DTA_CURRENT );
9037 ok(SUCCEEDED(hr), "SetTextureStageState failed (%08x)\n", hr);
9039 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
9040 ok(SUCCEEDED(hr), "SetTextureStageState failed (%08x)\n", hr);
9041 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_COLORARG1, D3DTA_TEXTURE);
9042 ok(SUCCEEDED(hr), "SetTextureStageState failed (%08x)\n", hr);
9043 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_COLORARG2, D3DTA_CURRENT);
9044 ok(SUCCEEDED(hr), "SetTextureStageState failed (%08x)\n", hr);
9046 hr = IDirect3DDevice9_SetTextureStageState(device, 2, D3DTSS_COLOROP, D3DTOP_DISABLE);
9047 ok(SUCCEEDED(hr), "SetTextureStageState failed (%08x)\n", hr);
9049 hr = IDirect3DDevice9_SetVertexShader(device, NULL);
9050 ok(SUCCEEDED(hr), "SetVertexShader failed (%08x)\n", hr);
9052 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffff00ff, 1.0f, 0);
9053 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed (%08x)\n", hr);
9055 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements, &vertex_declaration);
9056 ok(SUCCEEDED(hr), "CreateVertexDeclaration failed (0x%08x)\n", hr);
9057 hr = IDirect3DDevice9_SetVertexDeclaration(device, vertex_declaration);
9058 ok(SUCCEEDED(hr), "SetVertexDeclaration failed (0x%08x)\n", hr);
9060 hr = IDirect3DDevice9_BeginScene(device);
9061 ok(SUCCEEDED(hr), "BeginScene failed (0x%08x)\n", hr);
9063 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quad[0], sizeof(quad[0]));
9064 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed (0x%08x)\n", hr);
9066 hr = IDirect3DDevice9_EndScene(device);
9067 ok(SUCCEEDED(hr), "EndScene failed (0x%08x)\n", hr);
9069 color = getPixelColor(device, 240, 60);
9070 ok(color_match(color, 0x005ea000, 4), "Got unexpected color 0x%08x.\n", color);
9071 color = getPixelColor(device, 400, 60);
9072 ok(color_match(color, 0x009ea000, 4), "Got unexpected color 0x%08x.\n", color);
9073 color = getPixelColor(device, 80, 180);
9074 ok(color_match(color, 0x005ea000, 4), "Got unexpected color 0x%08x.\n", color);
9075 color = getPixelColor(device, 560, 180);
9076 ok(color_match(color, 0x009ea000, 4), "Got unexpected color 0x%08x.\n", color);
9077 color = getPixelColor(device, 80, 300);
9078 ok(color_match(color, 0x005e6000, 4), "Got unexpected color 0x%08x.\n", color);
9079 color = getPixelColor(device, 560, 300);
9080 ok(color_match(color, 0x009e6000, 4), "Got unexpected color 0x%08x.\n", color);
9081 color = getPixelColor(device, 240, 420);
9082 ok(color_match(color, 0x005e6000, 4), "Got unexpected color 0x%08x.\n", color);
9083 color = getPixelColor(device, 400, 420);
9084 ok(color_match(color, 0x009e6000, 4), "Got unexpected color 0x%08x.\n", color);
9085 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
9086 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
9088 for(i = 0; i < 2; i++) {
9089 hr = IDirect3DDevice9_GetTexture(device, i, (IDirect3DBaseTexture9 **) &texture);
9090 ok(SUCCEEDED(hr), "IDirect3DDevice9_GetTexture failed (0x%08x)\n", hr);
9091 IDirect3DTexture9_Release(texture); /* For the GetTexture */
9092 hr = IDirect3DDevice9_SetTexture(device, i, NULL);
9093 ok(SUCCEEDED(hr), "SetTexture failed (0x%08x)\n", hr);
9094 IDirect3DTexture9_Release(texture); /* To destroy it */
9097 if (!L6V5U5_supported || !(caps.TextureOpCaps & D3DTEXOPCAPS_BUMPENVMAPLUMINANCE))
9099 skip("L6V5U5 / D3DTOP_BUMPENVMAPLUMINANCE not supported, skipping tests.\n");
9100 IDirect3DVertexDeclaration9_Release(vertex_declaration);
9101 IDirect3DDevice9_Release(device);
9102 goto done;
9105 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x00000000, 1.0f, 0);
9106 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
9107 /* This test only tests the luminance part. The bumpmapping part was already tested above and
9108 * would only make this test more complicated
9110 hr = IDirect3DDevice9_CreateTexture(device, 1, 1, 1, 0, D3DFMT_L6V5U5, D3DPOOL_MANAGED, &tex1, NULL);
9111 ok(hr == D3D_OK, "IDirect3DDevice9_CreateTexture failed, hr=%08x\n", hr);
9112 hr = IDirect3DDevice9_CreateTexture(device, 1, 1, 1, 0, D3DFMT_X8R8G8B8, D3DPOOL_MANAGED, &tex2, NULL);
9113 ok(hr == D3D_OK, "IDirect3DDevice9_CreateTexture failed, hr=%08x\n", hr);
9115 memset(&locked_rect, 0, sizeof(locked_rect));
9116 hr = IDirect3DTexture9_LockRect(tex1, 0, &locked_rect, NULL, 0);
9117 ok(SUCCEEDED(hr), "LockRect failed with 0x%08x\n", hr);
9118 *((DWORD *)locked_rect.pBits) = 0x4000; /* L = 0.25, V = 0.0, U = 0.0 */
9119 hr = IDirect3DTexture9_UnlockRect(tex1, 0);
9120 ok(SUCCEEDED(hr), "UnlockRect failed with 0x%08x\n", hr);
9122 memset(&locked_rect, 0, sizeof(locked_rect));
9123 hr = IDirect3DTexture9_LockRect(tex2, 0, &locked_rect, NULL, 0);
9124 ok(SUCCEEDED(hr), "LockRect failed with 0x%08x\n", hr);
9125 *((DWORD *)locked_rect.pBits) = 0x00ff80c0;
9126 hr = IDirect3DTexture9_UnlockRect(tex2, 0);
9127 ok(SUCCEEDED(hr), "UnlockRect failed with 0x%08x\n", hr);
9129 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *) tex1);
9130 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTexture failed (%08x)\n", hr);
9131 hr = IDirect3DDevice9_SetTexture(device, 1, (IDirect3DBaseTexture9 *) tex2);
9132 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTexture failed (%08x)\n", hr);
9134 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_BUMPENVMAPLUMINANCE);
9135 ok(SUCCEEDED(hr), "SetTextureStageState failed (%08x)\n", hr);
9136 scale = 2.0;
9137 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_BUMPENVLSCALE, *((DWORD *)&scale));
9138 ok(SUCCEEDED(hr), "SetTextureStageState failed (%08x)\n", hr);
9139 offset = 0.1;
9140 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_BUMPENVLOFFSET, *((DWORD *)&offset));
9141 ok(SUCCEEDED(hr), "SetTextureStageState failed (%08x)\n", hr);
9143 hr = IDirect3DDevice9_BeginScene(device);
9144 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
9145 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quad[0], sizeof(quad[0]));
9146 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9147 hr = IDirect3DDevice9_EndScene(device);
9148 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
9150 color = getPixelColor(device, 320, 240);
9151 /* red: 1.0 * (0.25 * 2.0 + 0.1) = 1.0 * 0.6 = 0.6 = 0x99
9152 * green: 0.5 * (0.25 * 2.0 + 0.1) = 0.5 * 0.6 = 0.3 = 0x4c
9153 * green: 0.75 * (0.25 * 2.0 + 0.1) = 0.75 * 0.6 = 0.45 = 0x72
9155 ok(color_match(color, 0x00994c72, 5), "bumpmap failed: Got color 0x%08x, expected 0x00994c72.\n", color);
9156 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
9157 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
9159 /* Check a result scale factor > 1.0 */
9160 scale = 10;
9161 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_BUMPENVLSCALE, *((DWORD *)&scale));
9162 ok(SUCCEEDED(hr), "SetTextureStageState failed (%08x)\n", hr);
9163 offset = 10;
9164 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_BUMPENVLOFFSET, *((DWORD *)&offset));
9165 ok(SUCCEEDED(hr), "SetTextureStageState failed (%08x)\n", hr);
9167 hr = IDirect3DDevice9_BeginScene(device);
9168 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
9169 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quad[0], sizeof(quad[0]));
9170 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9171 hr = IDirect3DDevice9_EndScene(device);
9172 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
9174 color = getPixelColor(device, 320, 240);
9175 ok(color_match(color, 0x00ff80c0, 1), "bumpmap failed: Got color 0x%08x, expected 0x00ff80c0.\n", color);
9176 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
9177 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
9179 /* Check clamping in the scale factor calculation */
9180 scale = 1000;
9181 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_BUMPENVLSCALE, *((DWORD *)&scale));
9182 ok(SUCCEEDED(hr), "SetTextureStageState failed (%08x)\n", hr);
9183 offset = -1;
9184 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_BUMPENVLOFFSET, *((DWORD *)&offset));
9185 ok(SUCCEEDED(hr), "SetTextureStageState failed (%08x)\n", hr);
9187 hr = IDirect3DDevice9_BeginScene(device);
9188 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
9189 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quad[0], sizeof(quad[0]));
9190 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9191 hr = IDirect3DDevice9_EndScene(device);
9192 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
9194 color = getPixelColor(device, 320, 240);
9195 ok(color_match(color, 0x00ff80c0, 1), "bumpmap failed: Got color 0x%08x, expected 0x00ff80c0.\n", color);
9196 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
9197 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
9199 IDirect3DTexture9_Release(tex1);
9200 IDirect3DTexture9_Release(tex2);
9201 IDirect3DVertexDeclaration9_Release(vertex_declaration);
9202 refcount = IDirect3DDevice9_Release(device);
9203 ok(!refcount, "Device has %u references left.\n", refcount);
9204 done:
9205 IDirect3D9_Release(d3d);
9206 DestroyWindow(window);
9209 static void stencil_cull_test(void)
9211 IDirect3DDevice9 *device;
9212 IDirect3D9 *d3d;
9213 ULONG refcount;
9214 D3DCAPS9 caps;
9215 HWND window;
9216 HRESULT hr;
9217 static const float quad1[] =
9219 -1.0, -1.0, 0.1,
9220 0.0, -1.0, 0.1,
9221 -1.0, 0.0, 0.1,
9222 0.0, 0.0, 0.1,
9224 static const float quad2[] =
9226 0.0, -1.0, 0.1,
9227 1.0, -1.0, 0.1,
9228 0.0, 0.0, 0.1,
9229 1.0, 0.0, 0.1,
9231 static const float quad3[] =
9233 0.0, 0.0, 0.1,
9234 1.0, 0.0, 0.1,
9235 0.0, 1.0, 0.1,
9236 1.0, 1.0, 0.1,
9238 static const float quad4[] =
9240 -1.0, 0.0, 0.1,
9241 0.0, 0.0, 0.1,
9242 -1.0, 1.0, 0.1,
9243 0.0, 1.0, 0.1,
9245 struct
9247 struct vec3 position;
9248 DWORD diffuse;
9250 painter[] =
9252 {{-1.0f, -1.0f, 0.0f}, 0x00000000},
9253 {{ 1.0f, -1.0f, 0.0f}, 0x00000000},
9254 {{-1.0f, 1.0f, 0.0f}, 0x00000000},
9255 {{ 1.0f, 1.0f, 0.0f}, 0x00000000},
9257 static const WORD indices_cw[] = {0, 1, 3};
9258 static const WORD indices_ccw[] = {0, 2, 3};
9259 unsigned int i;
9260 DWORD color;
9262 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
9263 0, 0, 640, 480, NULL, NULL, NULL, NULL);
9264 d3d = Direct3DCreate9(D3D_SDK_VERSION);
9265 ok(!!d3d, "Failed to create a D3D object.\n");
9266 if (!(device = create_device(d3d, window, window, TRUE)))
9268 skip("Cannot create a device with a D24S8 stencil buffer.\n");
9269 DestroyWindow(window);
9270 IDirect3D9_Release(d3d);
9271 return;
9273 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
9274 ok(SUCCEEDED(hr), "Failed to get caps, hr %#x.\n", hr);
9275 if (!(caps.StencilCaps & D3DSTENCILCAPS_TWOSIDED))
9277 skip("No two sided stencil support\n");
9278 goto cleanup;
9281 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_STENCIL, 0x00ff0000, 0.0, 0x8);
9282 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
9283 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ);
9284 ok(SUCCEEDED(hr), "Failed to set FVF,hr %#x.\n", hr);
9286 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, D3DZB_FALSE);
9287 ok(hr == D3D_OK, "Failed to disable Z test, %#x.\n", hr);
9288 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
9289 ok(hr == D3D_OK, "Failed to disable lighting, %#x.\n", hr);
9290 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_STENCILFAIL, D3DSTENCILOP_INCR);
9291 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
9292 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_STENCILZFAIL, D3DSTENCILOP_DECR);
9293 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
9294 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_STENCILPASS, D3DSTENCILOP_REPLACE);
9295 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
9296 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_STENCILREF, 0x3);
9297 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
9299 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_CCW_STENCILFAIL, D3DSTENCILOP_REPLACE);
9300 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
9301 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_CCW_STENCILZFAIL, D3DSTENCILOP_DECR);
9302 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
9303 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_CCW_STENCILPASS, D3DSTENCILOP_INCR);
9304 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
9306 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_STENCILENABLE, TRUE);
9307 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
9308 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_TWOSIDEDSTENCILMODE, FALSE);
9309 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
9311 /* First pass: Fill the stencil buffer with some values... */
9312 hr = IDirect3DDevice9_BeginScene(device);
9313 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
9315 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_CULLMODE, D3DCULL_CW);
9316 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
9317 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 4 /* NumVerts */,
9318 1 /* PrimCount */, indices_cw, D3DFMT_INDEX16, quad1, sizeof(float) * 3);
9319 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9320 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 4 /* NumVerts */,
9321 1 /* PrimCount */, indices_ccw, D3DFMT_INDEX16, quad1, sizeof(float) * 3);
9322 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9324 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_TWOSIDEDSTENCILMODE, TRUE);
9325 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
9326 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_CULLMODE, D3DCULL_NONE);
9327 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
9328 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 4 /* NumVerts */,
9329 1 /* PrimCount */, indices_cw, D3DFMT_INDEX16, quad2, sizeof(float) * 3);
9330 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9331 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 4 /* NumVerts */,
9332 1 /* PrimCount */, indices_ccw, D3DFMT_INDEX16, quad2, sizeof(float) * 3);
9333 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9335 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_CULLMODE, D3DCULL_CW);
9336 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
9337 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 4 /* NumVerts */,
9338 1 /* PrimCount */, indices_cw, D3DFMT_INDEX16, quad3, sizeof(float) * 3);
9339 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9340 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 4 /* NumVerts */,
9341 1 /* PrimCount */, indices_ccw, D3DFMT_INDEX16, quad3, sizeof(float) * 3);
9342 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9344 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_CULLMODE, D3DCULL_CCW);
9345 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
9346 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 4 /* NumVerts */,
9347 1 /* PrimCount */, indices_cw, D3DFMT_INDEX16, quad4, sizeof(float) * 3);
9348 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9349 hr = IDirect3DDevice9_DrawIndexedPrimitiveUP(device, D3DPT_TRIANGLELIST, 0 /* MinIndex */, 4 /* NumVerts */,
9350 1 /* PrimCount */, indices_ccw, D3DFMT_INDEX16, quad4, sizeof(float) * 3);
9351 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9353 hr = IDirect3DDevice9_EndScene(device);
9354 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
9356 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_STENCILZFAIL, D3DSTENCILOP_KEEP);
9357 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
9358 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_STENCILPASS, D3DSTENCILOP_KEEP);
9359 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
9360 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_STENCILFAIL, D3DSTENCILOP_KEEP);
9361 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
9362 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_TWOSIDEDSTENCILMODE, FALSE);
9363 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
9364 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_CULLMODE, D3DCULL_NONE);
9365 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
9366 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_STENCILFUNC, D3DCMP_EQUAL);
9367 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
9369 /* 2nd pass: Make the stencil values visible */
9370 hr = IDirect3DDevice9_BeginScene(device);
9371 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
9372 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
9373 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
9374 for (i = 0; i < 16; ++i)
9376 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_STENCILREF, i);
9377 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
9379 painter[0].diffuse = (i * 16); /* Creates shades of blue */
9380 painter[1].diffuse = (i * 16);
9381 painter[2].diffuse = (i * 16);
9382 painter[3].diffuse = (i * 16);
9383 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, painter, sizeof(painter[0]));
9384 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9386 hr = IDirect3DDevice9_EndScene(device);
9387 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
9389 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_STENCILENABLE, FALSE);
9390 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
9392 color = getPixelColor(device, 160, 420);
9393 ok(color == 0x00000030, "CCW triangle, twoside FALSE, cull cw, replace, has color 0x%08x, expected 0x00000030\n", color);
9394 color = getPixelColor(device, 160, 300);
9395 ok(color == 0x00000080, "CW triangle, twoside FALSE, cull cw, culled, has color 0x%08x, expected 0x00000080\n", color);
9397 color = getPixelColor(device, 480, 420);
9398 ok(color == 0x00000090, "CCW triangle, twoside TRUE, cull off, incr, has color 0x%08x, expected 0x00000090\n", color);
9399 color = getPixelColor(device, 480, 300);
9400 ok(color == 0x00000030, "CW triangle, twoside TRUE, cull off, replace, has color 0x%08x, expected 0x00000030\n", color);
9402 color = getPixelColor(device, 160, 180);
9403 ok(color == 0x00000080, "CCW triangle, twoside TRUE, cull ccw, culled, has color 0x%08x, expected 0x00000080\n", color);
9404 color = getPixelColor(device, 160, 60);
9405 ok(color == 0x00000030, "CW triangle, twoside TRUE, cull ccw, replace, has color 0x%08x, expected 0x00000030\n", color);
9407 color = getPixelColor(device, 480, 180);
9408 ok(color == 0x00000090, "CCW triangle, twoside TRUE, cull cw, incr, has color 0x%08x, expected 0x00000090\n", color);
9409 color = getPixelColor(device, 480, 60);
9410 ok(color == 0x00000080, "CW triangle, twoside TRUE, cull cw, culled, has color 0x%08x, expected 0x00000080\n", color);
9412 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
9413 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
9415 cleanup:
9416 refcount = IDirect3DDevice9_Release(device);
9417 ok(!refcount, "Device has %u references left.\n", refcount);
9418 IDirect3D9_Release(d3d);
9419 DestroyWindow(window);
9422 static void vpos_register_test(void)
9424 IDirect3DSurface9 *surface = NULL, *backbuffer;
9425 IDirect3DPixelShader9 *shader, *shader_frac;
9426 IDirect3DVertexShader9 *vshader;
9427 IDirect3DDevice9 *device;
9428 D3DLOCKED_RECT lr;
9429 IDirect3D9 *d3d;
9430 ULONG refcount;
9431 D3DCAPS9 caps;
9432 DWORD color;
9433 HWND window;
9434 HRESULT hr;
9435 DWORD *pos;
9437 static const DWORD shader_code[] =
9439 0xffff0300, /* ps_3_0 */
9440 0x0200001f, 0x80000000, 0x90031000, /* dcl vPos.xy */
9441 0x03000002, 0x80030000, 0x90541000, 0xa1fe0000, /* sub r0.xy, vPos.xy, c0.zw */
9442 0x02000001, 0x800f0001, 0xa0e40000, /* mov r1, c0 */
9443 0x02000001, 0x80080002, 0xa0550000, /* mov r2.a, c0.y */
9444 0x02000001, 0x80010002, 0xa0550000, /* mov r2.r, c0.y */
9445 0x04000058, 0x80020002, 0x80000000, 0x80000001, 0x80550001, /* cmp r2.g, r0.x, r1.x, r1.y */
9446 0x04000058, 0x80040002, 0x80550000, 0x80000001, 0x80550001, /* cmp r2.b, r0.y, r1.x, r1.y */
9447 0x02000001, 0x800f0800, 0x80e40002, /* mov oC0, r2 */
9448 0x0000ffff /* end */
9450 static const DWORD shader_frac_code[] =
9452 0xffff0300, /* ps_3_0 */
9453 0x05000051, 0xa00f0000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, /* def c0, 0.0, 0.0, 0.0, 0.0 */
9454 0x0200001f, 0x80000000, 0x90031000, /* dcl vPos.xy */
9455 0x02000001, 0x800f0000, 0xa0e40000, /* mov r0, c0 */
9456 0x02000013, 0x80030000, 0x90541000, /* frc r0.xy, vPos.xy */
9457 0x02000001, 0x800f0800, 0x80e40000, /* mov oC0, r0 */
9458 0x0000ffff /* end */
9460 static const DWORD vshader_code[] =
9462 0xfffe0300, /* vs_3_0 */
9463 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
9464 0x0200001f, 0x80000000, 0xe00f0000, /* dcl_position o0 */
9465 0x02000001, 0xe00f0000, 0x90e40000, /* mov o0, v0 */
9466 0x0000ffff /* end */
9468 static const float quad[] =
9470 -1.0f, -1.0f, 0.1f, 0.0f, 0.0f,
9471 -1.0f, 1.0f, 0.1f, 0.0f, 1.0f,
9472 1.0f, -1.0f, 0.1f, 1.0f, 0.0f,
9473 1.0f, 1.0f, 0.1f, 1.0f, 1.0f,
9475 float constant[4] = {1.0, 0.0, 320, 240};
9477 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
9478 0, 0, 640, 480, NULL, NULL, NULL, NULL);
9479 d3d = Direct3DCreate9(D3D_SDK_VERSION);
9480 ok(!!d3d, "Failed to create a D3D object.\n");
9481 if (!(device = create_device(d3d, window, window, TRUE)))
9483 skip("Failed to create a D3D device, skipping tests.\n");
9484 goto done;
9487 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
9488 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
9489 if (caps.PixelShaderVersion < D3DPS_VERSION(3, 0) || caps.VertexShaderVersion < D3DVS_VERSION(3, 0))
9491 skip("No shader model 3 support, skipping tests.\n");
9492 IDirect3DDevice9_Release(device);
9493 goto done;
9496 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff0000ff, 1.0f, 0);
9497 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed, hr=%08x\n", hr);
9498 hr = IDirect3DDevice9_CreateVertexShader(device, vshader_code, &vshader);
9499 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader failed hr=%08x\n", hr);
9500 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code, &shader);
9501 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader failed hr=%08x\n", hr);
9502 hr = IDirect3DDevice9_CreatePixelShader(device, shader_frac_code, &shader_frac);
9503 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader failed hr=%08x\n", hr);
9504 hr = IDirect3DDevice9_SetPixelShader(device, shader);
9505 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShader failed hr=%08x\n", hr);
9506 hr = IDirect3DDevice9_SetVertexShader(device, vshader);
9507 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexShader failed hr=%08x\n", hr);
9508 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ);
9509 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed hr=%08x\n", hr);
9510 hr = IDirect3DDevice9_GetBackBuffer(device, 0, 0, D3DBACKBUFFER_TYPE_MONO, &backbuffer);
9511 ok(hr == D3D_OK, "IDirect3DDevice9_GetBackBuffer failed hr=%08x\n", hr);
9513 hr = IDirect3DDevice9_BeginScene(device);
9514 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
9515 hr = IDirect3DDevice9_SetPixelShaderConstantF(device, 0, constant, 1);
9516 ok(SUCCEEDED(hr), "Failed to set pixel shader constant, hr %#x.\n", hr);
9517 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(float) * 5);
9518 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9519 hr = IDirect3DDevice9_EndScene(device);
9520 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
9522 /* This has to be pixel exact */
9523 color = getPixelColor(device, 319, 239);
9524 ok(color == 0x00000000, "vPos: Pixel 319,239 has color 0x%08x, expected 0x00000000\n", color);
9525 color = getPixelColor(device, 320, 239);
9526 ok(color == 0x0000ff00, "vPos: Pixel 320,239 has color 0x%08x, expected 0x0000ff00\n", color);
9527 color = getPixelColor(device, 319, 240);
9528 ok(color == 0x000000ff, "vPos: Pixel 319,240 has color 0x%08x, expected 0x000000ff\n", color);
9529 color = getPixelColor(device, 320, 240);
9530 ok(color == 0x0000ffff, "vPos: Pixel 320,240 has color 0x%08x, expected 0x0000ffff\n", color);
9531 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
9533 hr = IDirect3DDevice9_CreateRenderTarget(device, 32, 32, D3DFMT_X8R8G8B8, 0, 0, TRUE,
9534 &surface, NULL);
9535 ok(hr == D3D_OK, "IDirect3DDevice9_CreateRenderTarget failed hr=%08x\n", hr);
9536 hr = IDirect3DDevice9_BeginScene(device);
9537 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
9538 constant[2] = 16; constant[3] = 16;
9539 hr = IDirect3DDevice9_SetPixelShaderConstantF(device, 0, constant, 1);
9540 ok(SUCCEEDED(hr), "Failed to set pixel shader constant, hr %#x.\n", hr);
9541 hr = IDirect3DDevice9_SetRenderTarget(device, 0, surface);
9542 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
9543 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(float) * 5);
9544 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9545 hr = IDirect3DDevice9_EndScene(device);
9546 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
9548 hr = IDirect3DSurface9_LockRect(surface, &lr, NULL, D3DLOCK_READONLY);
9549 ok(hr == D3D_OK, "IDirect3DSurface9_LockRect failed, hr=%08x\n", hr);
9551 pos = (DWORD *) (((BYTE *) lr.pBits) + 14 * lr.Pitch + 14 * sizeof(DWORD));
9552 color = *pos & 0x00ffffff;
9553 ok(color == 0x00000000, "Pixel 14/14 has color 0x%08x, expected 0x00000000\n", color);
9554 pos = (DWORD *) (((BYTE *) lr.pBits) + 14 * lr.Pitch + 18 * sizeof(DWORD));
9555 color = *pos & 0x00ffffff;
9556 ok(color == 0x0000ff00, "Pixel 14/18 has color 0x%08x, expected 0x0000ff00\n", color);
9557 pos = (DWORD *) (((BYTE *) lr.pBits) + 18 * lr.Pitch + 14 * sizeof(DWORD));
9558 color = *pos & 0x00ffffff;
9559 ok(color == 0x000000ff, "Pixel 18/14 has color 0x%08x, expected 0x000000ff\n", color);
9560 pos = (DWORD *) (((BYTE *) lr.pBits) + 18 * lr.Pitch + 18 * sizeof(DWORD));
9561 color = *pos & 0x00ffffff;
9562 ok(color == 0x0000ffff, "Pixel 18/18 has color 0x%08x, expected 0x0000ffff\n", color);
9564 hr = IDirect3DSurface9_UnlockRect(surface);
9565 ok(hr == D3D_OK, "IDirect3DSurface9_UnlockRect failed, hr=%08x\n", hr);
9567 /* Test the fraction value of vPos. This is tested with the offscreen target and not the backbuffer to
9568 * have full control over the multisampling setting inside this test
9570 hr = IDirect3DDevice9_SetPixelShader(device, shader_frac);
9571 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShader failed hr=%08x\n", hr);
9572 hr = IDirect3DDevice9_BeginScene(device);
9573 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
9574 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff0000ff, 0.0, 0);
9575 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
9576 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(float) * 5);
9577 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9578 hr = IDirect3DDevice9_EndScene(device);
9579 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
9581 hr = IDirect3DDevice9_SetRenderTarget(device, 0, backbuffer);
9582 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderTarget failed, hr=%08x\n", hr);
9584 hr = IDirect3DSurface9_LockRect(surface, &lr, NULL, D3DLOCK_READONLY);
9585 ok(hr == D3D_OK, "IDirect3DSurface9_LockRect failed, hr=%08x\n", hr);
9587 pos = (DWORD *) (((BYTE *) lr.pBits) + 14 * lr.Pitch + 14 * sizeof(DWORD));
9588 color = *pos & 0x00ffffff;
9589 ok(color == 0x00000000, "vPos fraction test has color 0x%08x, expected 0x00000000\n", color);
9591 hr = IDirect3DSurface9_UnlockRect(surface);
9592 ok(hr == D3D_OK, "IDirect3DSurface9_UnlockRect failed, hr=%08x\n", hr);
9594 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
9595 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShader failed hr=%08x\n", hr);
9596 hr = IDirect3DDevice9_SetVertexShader(device, NULL);
9597 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexShader failed hr=%08x\n", hr);
9598 IDirect3DPixelShader9_Release(shader);
9599 IDirect3DPixelShader9_Release(shader_frac);
9600 IDirect3DVertexShader9_Release(vshader);
9601 if(surface) IDirect3DSurface9_Release(surface);
9602 IDirect3DSurface9_Release(backbuffer);
9603 refcount = IDirect3DDevice9_Release(device);
9604 ok(!refcount, "Device has %u references left.\n", refcount);
9605 done:
9606 IDirect3D9_Release(d3d);
9607 DestroyWindow(window);
9610 static BOOL point_match(IDirect3DDevice9 *device, UINT x, UINT y, UINT r)
9612 D3DCOLOR color;
9614 color = D3DCOLOR_ARGB(0x00, 0xff, 0xff, 0xff);
9615 if (!color_match(getPixelColor(device, x + r, y), color, 1)) return FALSE;
9616 if (!color_match(getPixelColor(device, x - r, y), color, 1)) return FALSE;
9617 if (!color_match(getPixelColor(device, x, y + r), color, 1)) return FALSE;
9618 if (!color_match(getPixelColor(device, x, y - r), color, 1)) return FALSE;
9620 ++r;
9621 color = D3DCOLOR_ARGB(0x00, 0x00, 0x00, 0xff);
9622 if (!color_match(getPixelColor(device, x + r, y), color, 1)) return FALSE;
9623 if (!color_match(getPixelColor(device, x - r, y), color, 1)) return FALSE;
9624 if (!color_match(getPixelColor(device, x, y + r), color, 1)) return FALSE;
9625 if (!color_match(getPixelColor(device, x, y - r), color, 1)) return FALSE;
9627 return TRUE;
9630 static void pointsize_test(void)
9632 float ptsize, ptsizemax_orig, ptsizemin_orig;
9633 IDirect3DSurface9 *rt, *backbuffer;
9634 IDirect3DTexture9 *tex1, *tex2;
9635 IDirect3DDevice9 *device;
9636 D3DLOCKED_RECT lr;
9637 IDirect3D9 *d3d;
9638 D3DCOLOR color;
9639 ULONG refcount;
9640 D3DCAPS9 caps;
9641 HWND window;
9642 HRESULT hr;
9644 static const RECT rect = {0, 0, 128, 128};
9645 static const DWORD tex1_data[4] = {0x00ff0000, 0x00ff0000, 0x00000000, 0x00000000};
9646 static const DWORD tex2_data[4] = {0x00000000, 0x0000ff00, 0x00000000, 0x0000ff00};
9647 static const float vertices[] =
9649 64.0f, 64.0f, 0.1f,
9650 128.0f, 64.0f, 0.1f,
9651 192.0f, 64.0f, 0.1f,
9652 256.0f, 64.0f, 0.1f,
9653 320.0f, 64.0f, 0.1f,
9654 384.0f, 64.0f, 0.1f,
9655 448.0f, 64.0f, 0.1f,
9656 512.0f, 64.0f, 0.1f,
9658 /* Transforms the coordinate system [-1.0;1.0]x[-1.0;1.0] to
9659 * [0.0;0.0]x[640.0;480.0]. Z is untouched. */
9660 D3DMATRIX matrix =
9662 2.0f / 640.0f, 0.0f, 0.0f, 0.0f,
9663 0.0f, -2.0 / 480.0f, 0.0f, 0.0f,
9664 0.0f, 0.0f, 1.0f, 0.0f,
9665 -1.0f, 1.0f, 0.0f, 1.0f,
9666 }}};
9668 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
9669 0, 0, 640, 480, NULL, NULL, NULL, NULL);
9670 d3d = Direct3DCreate9(D3D_SDK_VERSION);
9671 ok(!!d3d, "Failed to create a D3D object.\n");
9672 if (!(device = create_device(d3d, window, window, TRUE)))
9674 skip("Failed to create a D3D device, skipping tests.\n");
9675 goto done;
9678 memset(&caps, 0, sizeof(caps));
9679 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
9680 ok(hr == D3D_OK, "IDirect3DDevice9_GetDeviceCaps failed hr=%08x\n", hr);
9681 if(caps.MaxPointSize < 32.0) {
9682 skip("MaxPointSize < 32.0, skipping(MaxPointsize = %f)\n", caps.MaxPointSize);
9683 IDirect3DDevice9_Release(device);
9684 goto done;
9687 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff0000ff, 1.0f, 0);
9688 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed, hr=%08x\n", hr);
9689 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
9690 ok(SUCCEEDED(hr), "Failed to disable lighting, hr %#x.\n", hr);
9691 hr = IDirect3DDevice9_SetTransform(device, D3DTS_PROJECTION, &matrix);
9692 ok(hr == D3D_OK, "IDirect3DDevice9_SetTransform failed, hr=%08x\n", hr);
9693 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ);
9694 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed hr=%08x\n", hr);
9696 hr = IDirect3DDevice9_BeginScene(device);
9697 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
9699 ptsize = 15.0f;
9700 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_POINTSIZE, *(DWORD *)&ptsize);
9701 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
9702 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_POINTLIST, 1, &vertices[0], sizeof(float) * 3);
9703 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9705 ptsize = 31.0f;
9706 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_POINTSIZE, *(DWORD *)&ptsize);
9707 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
9708 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_POINTLIST, 1, &vertices[3], sizeof(float) * 3);
9709 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9711 ptsize = 30.75f;
9712 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_POINTSIZE, *(DWORD *)&ptsize);
9713 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
9714 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_POINTLIST, 1, &vertices[6], sizeof(float) * 3);
9715 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9717 if (caps.MaxPointSize >= 63.0f)
9719 ptsize = 63.0f;
9720 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_POINTSIZE, *(DWORD *)&ptsize);
9721 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
9722 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_POINTLIST, 1, &vertices[9], sizeof(float) * 3);
9723 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9725 ptsize = 62.75f;
9726 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_POINTSIZE, *(DWORD *)&ptsize);
9727 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
9728 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_POINTLIST, 1, &vertices[15], sizeof(float) * 3);
9729 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9732 ptsize = 1.0f;
9733 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_POINTSIZE, *(DWORD *)&ptsize);
9734 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
9735 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_POINTLIST, 1, &vertices[12], sizeof(float) * 3);
9736 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9738 hr = IDirect3DDevice9_GetRenderState(device, D3DRS_POINTSIZE_MAX, (DWORD *)&ptsizemax_orig);
9739 ok(SUCCEEDED(hr), "Failed to get render state, hr %#x.\n", hr);
9740 hr = IDirect3DDevice9_GetRenderState(device, D3DRS_POINTSIZE_MIN, (DWORD *)&ptsizemin_orig);
9741 ok(SUCCEEDED(hr), "Failed to get render state, hr %#x.\n", hr);
9743 /* What happens if point scaling is disabled, and POINTSIZE_MAX < POINTSIZE? */
9744 ptsize = 15.0f;
9745 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_POINTSIZE, *(DWORD *)&ptsize);
9746 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
9747 ptsize = 1.0f;
9748 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_POINTSIZE_MAX, *(DWORD *)&ptsize);
9749 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
9750 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_POINTLIST, 1, &vertices[18], sizeof(float) * 3);
9751 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9753 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_POINTSIZE_MAX, *(DWORD *)&ptsizemax_orig);
9754 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
9756 /* pointsize < pointsize_min < pointsize_max?
9757 * pointsize = 1.0, pointsize_min = 15.0, pointsize_max = default(usually 64.0) */
9758 ptsize = 1.0f;
9759 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_POINTSIZE, *(DWORD *)&ptsize);
9760 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
9761 ptsize = 15.0f;
9762 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_POINTSIZE_MIN, *(DWORD *)&ptsize);
9763 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
9764 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_POINTLIST, 1, &vertices[21], sizeof(float) * 3);
9765 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9767 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_POINTSIZE_MIN, *(DWORD *)&ptsizemin_orig);
9768 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
9770 hr = IDirect3DDevice9_EndScene(device);
9771 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
9773 ok(point_match(device, 64, 64, 7), "point_match(64, 64, 7) failed, expected point size 15.\n");
9774 ok(point_match(device, 128, 64, 15), "point_match(128, 64, 15) failed, expected point size 31.\n");
9775 ok(point_match(device, 192, 64, 15), "point_match(192, 64, 15) failed, expected point size 31.\n");
9777 if (caps.MaxPointSize >= 63.0)
9779 ok(point_match(device, 256, 64, 31), "point_match(256, 64, 31) failed, expected point size 63.\n");
9780 ok(point_match(device, 384, 64, 31), "point_match(384, 64, 31) failed, expected point size 63.\n");
9783 ok(point_match(device, 320, 64, 0), "point_match(320, 64, 0) failed, expected point size 1.\n");
9784 /* ptsize = 15, ptsize_max = 1 --> point has size 1 */
9785 ok(point_match(device, 448, 64, 0), "point_match(448, 64, 0) failed, expected point size 1.\n");
9786 /* ptsize = 1, ptsize_max = default(64), ptsize_min = 15 --> point has size 15 */
9787 ok(point_match(device, 512, 64, 7), "point_match(512, 64, 7) failed, expected point size 15.\n");
9789 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
9791 /* The following code tests point sprites with two textures, to see if each texture coordinate unit
9792 * generates texture coordinates for the point(result: Yes, it does)
9794 * However, not all GL implementations support point sprites(they need GL_ARB_point_sprite), but there
9795 * is no point sprite cap bit in d3d because native d3d software emulates point sprites. Until the
9796 * SW emulation is implemented in wined3d, this test will fail on GL drivers that does not support them.
9798 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff0000ff, 1.0f, 0);
9799 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed, hr=%08x\n", hr);
9801 hr = IDirect3DDevice9_CreateTexture(device, 2, 2, 1, 0, D3DFMT_A8R8G8B8, D3DPOOL_MANAGED, &tex1, NULL);
9802 ok(hr == D3D_OK, "IDirect3DDevice9_CreateTexture failed hr=%08x\n", hr);
9803 hr = IDirect3DDevice9_CreateTexture(device, 2, 2, 1, 0, D3DFMT_A8R8G8B8, D3DPOOL_MANAGED, &tex2, NULL);
9804 ok(hr == D3D_OK, "IDirect3DDevice9_CreateTexture failed hr=%08x\n", hr);
9805 memset(&lr, 0, sizeof(lr));
9806 hr = IDirect3DTexture9_LockRect(tex1, 0, &lr, NULL, 0);
9807 ok(hr == D3D_OK, "IDirect3DTexture9_LockRect failed hr=%08x\n", hr);
9808 memcpy(lr.pBits, tex1_data, sizeof(tex1_data));
9809 hr = IDirect3DTexture9_UnlockRect(tex1, 0);
9810 ok(hr == D3D_OK, "IDirect3DTexture9_UnlockRect failed hr=%08x\n", hr);
9811 memset(&lr, 0, sizeof(lr));
9812 hr = IDirect3DTexture9_LockRect(tex2, 0, &lr, NULL, 0);
9813 ok(hr == D3D_OK, "IDirect3DTexture9_LockRect failed hr=%08x\n", hr);
9814 memcpy(lr.pBits, tex2_data, sizeof(tex2_data));
9815 hr = IDirect3DTexture9_UnlockRect(tex2, 0);
9816 ok(hr == D3D_OK, "IDirect3DTexture9_UnlockRect failed hr=%08x\n", hr);
9817 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *) tex1);
9818 ok(hr == D3D_OK, "IDirect3DDevice9_SetTexture failed hr=%08x\n", hr);
9819 hr = IDirect3DDevice9_SetTexture(device, 1, (IDirect3DBaseTexture9 *) tex2);
9820 ok(hr == D3D_OK, "IDirect3DDevice9_SetTexture failed hr=%08x\n", hr);
9821 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
9822 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed hr=%08x\n", hr);
9823 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
9824 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed hr=%08x\n", hr);
9825 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_COLOROP, D3DTOP_ADD);
9826 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed hr=%08x\n", hr);
9827 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_COLORARG1, D3DTA_TEXTURE);
9828 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed hr=%08x\n", hr);
9829 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_COLORARG2, D3DTA_CURRENT);
9830 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed hr=%08x\n", hr);
9832 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_POINTSPRITEENABLE, TRUE);
9833 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState failed hr=%08x\n", hr);
9834 ptsize = 32.0;
9835 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_POINTSIZE, *((DWORD *) (&ptsize)));
9836 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState failed, hr=%08x\n", hr);
9838 hr = IDirect3DDevice9_BeginScene(device);
9839 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
9840 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_POINTLIST, 1, &vertices[0], sizeof(float) * 3);
9841 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
9842 hr = IDirect3DDevice9_EndScene(device);
9843 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
9845 color = getPixelColor(device, 64-4, 64-4);
9846 ok(color == 0x00ff0000, "pSprite: Pixel (64-4),(64-4) has color 0x%08x, expected 0x00ff0000\n", color);
9847 color = getPixelColor(device, 64-4, 64+4);
9848 ok(color == 0x00000000, "pSprite: Pixel (64-4),(64+4) has color 0x%08x, expected 0x00000000\n", color);
9849 color = getPixelColor(device, 64+4, 64+4);
9850 ok(color == 0x0000ff00, "pSprite: Pixel (64+4),(64+4) has color 0x%08x, expected 0x0000ff00\n", color);
9851 color = getPixelColor(device, 64+4, 64-4);
9852 ok(color == 0x00ffff00, "pSprite: Pixel (64+4),(64-4) has color 0x%08x, expected 0x00ffff00\n", color);
9853 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
9855 U(matrix).m[0][0] = 1.0f / 64.0f;
9856 U(matrix).m[1][1] = -1.0f / 64.0f;
9857 hr = IDirect3DDevice9_SetTransform(device, D3DTS_PROJECTION, &matrix);
9858 ok(SUCCEEDED(hr), "SetTransform failed, hr %#x.\n", hr);
9860 hr = IDirect3DDevice9_GetRenderTarget(device, 0, &backbuffer);
9861 ok(SUCCEEDED(hr), "GetRenderTarget failed, hr %#x.\n", hr);
9863 hr = IDirect3DDevice9_CreateRenderTarget(device, 128, 128, D3DFMT_A8R8G8B8,
9864 D3DMULTISAMPLE_NONE, 0, TRUE, &rt, NULL );
9865 ok(SUCCEEDED(hr), "CreateRenderTarget failed, hr %#x.\n", hr);
9867 hr = IDirect3DDevice9_SetRenderTarget(device, 0, rt);
9868 ok(SUCCEEDED(hr), "SetRenderTarget failed, hr %#x.\n", hr);
9869 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff00ffff, 1.0f, 0);
9870 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
9872 hr = IDirect3DDevice9_BeginScene(device);
9873 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
9874 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_POINTLIST, 1, &vertices[0], sizeof(float) * 3);
9875 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
9876 hr = IDirect3DDevice9_EndScene(device);
9877 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
9879 hr = IDirect3DDevice9_StretchRect(device, rt, &rect, backbuffer, &rect, D3DTEXF_NONE);
9880 ok(SUCCEEDED(hr), "StretchRect failed, hr %#x.\n", hr);
9881 hr = IDirect3DDevice9_SetRenderTarget(device, 0, backbuffer);
9882 ok(SUCCEEDED(hr), "SetRenderTarget failed, hr %#x.\n", hr);
9883 IDirect3DSurface9_Release(backbuffer);
9884 IDirect3DSurface9_Release(rt);
9886 color = getPixelColor(device, 64-4, 64-4);
9887 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0xff, 0x00, 0x00), 0),
9888 "Expected color 0x00ff0000, got 0x%08x.\n", color);
9889 color = getPixelColor(device, 64+4, 64-4);
9890 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0xff, 0xff, 0x00), 0),
9891 "Expected color 0x00ffff00, got 0x%08x.\n", color);
9892 color = getPixelColor(device, 64-4, 64+4);
9893 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x00, 0x00, 0x00), 0),
9894 "Expected color 0x00000000, got 0x%08x.\n", color);
9895 color = getPixelColor(device, 64+4, 64+4);
9896 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x00, 0xff, 0x00), 0),
9897 "Expected color 0x0000ff00, got 0x%08x.\n", color);
9899 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
9900 ok(SUCCEEDED(hr), "Present failed, hr %#x.\n", hr);
9902 IDirect3DTexture9_Release(tex1);
9903 IDirect3DTexture9_Release(tex2);
9904 refcount = IDirect3DDevice9_Release(device);
9905 ok(!refcount, "Device has %u references left.\n", refcount);
9906 done:
9907 IDirect3D9_Release(d3d);
9908 DestroyWindow(window);
9911 static void multiple_rendertargets_test(void)
9913 IDirect3DSurface9 *surf1, *surf2, *backbuf, *readback;
9914 IDirect3DPixelShader9 *ps1, *ps2;
9915 IDirect3DTexture9 *tex1, *tex2;
9916 IDirect3DVertexShader9 *vs;
9917 IDirect3DDevice9 *device;
9918 IDirect3D9 *d3d;
9919 ULONG refcount;
9920 D3DCAPS9 caps;
9921 DWORD color;
9922 HWND window;
9923 HRESULT hr;
9924 UINT i, j;
9926 static const DWORD vshader_code[] =
9928 0xfffe0300, /* vs_3_0 */
9929 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
9930 0x0200001f, 0x80000000, 0xe00f0000, /* dcl_position o0 */
9931 0x02000001, 0xe00f0000, 0x90e40000, /* mov o0, v0 */
9932 0x0000ffff /* end */
9934 static const DWORD pshader_code1[] =
9936 0xffff0300, /* ps_3_0 */
9937 0x05000051, 0xa00f0000, 0x00000000, 0x3f800000, 0x00000000, 0x00000000, /* def c0, 0.0, 1.0, 0.0, 0.0 */
9938 0x02000001, 0x800f0800, 0xa0e40000, /* mov oC0, c0 */
9939 0x0000ffff /* end */
9941 static const DWORD pshader_code2[] =
9943 0xffff0300, /* ps_3_0 */
9944 0x05000051, 0xa00f0000, 0x00000000, 0x3f800000, 0x00000000, 0x00000000, /* def c0, 0.0, 1.0, 0.0, 0.0 */
9945 0x05000051, 0xa00f0001, 0x00000000, 0x00000000, 0x3f800000, 0x00000000, /* def c1, 0.0, 0.0, 1.0, 0.0 */
9946 0x02000001, 0x800f0800, 0xa0e40000, /* mov oC0, c0 */
9947 0x02000001, 0x800f0801, 0xa0e40001, /* mov oC1, c1 */
9948 0x0000ffff /* end */
9950 static const float quad[] =
9952 -1.0f, -1.0f, 0.1f,
9953 -1.0f, 1.0f, 0.1f,
9954 1.0f, -1.0f, 0.1f,
9955 1.0f, 1.0f, 0.1f,
9957 static const float texquad[] =
9959 -1.0f, -1.0f, 0.1f, 0.0f, 0.0f,
9960 -1.0f, 1.0f, 0.1f, 0.0f, 1.0f,
9961 0.0f, -1.0f, 0.1f, 1.0f, 0.0f,
9962 0.0f, 1.0f, 0.1f, 1.0f, 1.0f,
9964 0.0f, -1.0f, 0.1f, 0.0f, 0.0f,
9965 0.0f, 1.0f, 0.1f, 0.0f, 1.0f,
9966 1.0f, -1.0f, 0.1f, 1.0f, 0.0f,
9967 1.0f, 1.0f, 0.1f, 1.0f, 1.0f,
9970 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
9971 0, 0, 640, 480, NULL, NULL, NULL, NULL);
9972 d3d = Direct3DCreate9(D3D_SDK_VERSION);
9973 ok(!!d3d, "Failed to create a D3D object.\n");
9974 if (!(device = create_device(d3d, window, window, TRUE)))
9976 skip("Failed to create a D3D device, skipping tests.\n");
9977 goto done;
9980 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
9981 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
9982 if (caps.NumSimultaneousRTs < 2)
9984 skip("Only 1 simultaneous render target supported, skipping MRT test.\n");
9985 IDirect3DDevice9_Release(device);
9986 goto done;
9988 if (caps.PixelShaderVersion < D3DPS_VERSION(3, 0) || caps.VertexShaderVersion < D3DVS_VERSION(3, 0))
9990 skip("No shader model 3 support, skipping tests.\n");
9991 IDirect3DDevice9_Release(device);
9992 goto done;
9995 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffff0000, 1.0f, 0);
9996 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed, hr=%08x\n", hr);
9998 hr = IDirect3DDevice9_CreateOffscreenPlainSurface(device, 16, 16,
9999 D3DFMT_A8R8G8B8, D3DPOOL_SYSTEMMEM, &readback, NULL);
10000 ok(SUCCEEDED(hr), "CreateOffscreenPlainSurface failed, hr %#x.\n", hr);
10002 hr = IDirect3DDevice9_CreateTexture(device, 16, 16, 1, D3DUSAGE_RENDERTARGET,
10003 D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &tex1, NULL);
10004 ok(hr == D3D_OK, "IDirect3DDevice9_CreateTexture failed, hr=%08x\n", hr);
10005 hr = IDirect3DDevice9_CreateTexture(device, 16, 16, 1, D3DUSAGE_RENDERTARGET,
10006 D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &tex2, NULL);
10007 ok(hr == D3D_OK, "IDirect3DDevice9_CreateTexture failed, hr=%08x\n", hr);
10008 hr = IDirect3DDevice9_CreateVertexShader(device, vshader_code, &vs);
10009 ok(SUCCEEDED(hr), "CreateVertexShader failed, hr %#x.\n", hr);
10010 hr = IDirect3DDevice9_CreatePixelShader(device, pshader_code1, &ps1);
10011 ok(SUCCEEDED(hr), "Failed to create pixel shader, hr %#x.\n", hr);
10012 hr = IDirect3DDevice9_CreatePixelShader(device, pshader_code2, &ps2);
10013 ok(SUCCEEDED(hr), "Failed to create pixel shader, hr %#x.\n", hr);
10015 hr = IDirect3DDevice9_GetRenderTarget(device, 0, &backbuf);
10016 ok(hr == D3D_OK, "IDirect3DDevice9_GetRenderTarget failed, hr=%08x\n", hr);
10017 hr = IDirect3DTexture9_GetSurfaceLevel(tex1, 0, &surf1);
10018 ok(hr == D3D_OK, "IDirect3DTexture9_GetSurfaceLevel failed, hr=%08x\n", hr);
10019 hr = IDirect3DTexture9_GetSurfaceLevel(tex2, 0, &surf2);
10020 ok(hr == D3D_OK, "IDirect3DTexture9_GetSurfaceLevel failed, hr=%08x\n", hr);
10022 hr = IDirect3DDevice9_SetVertexShader(device, vs);
10023 ok(SUCCEEDED(hr), "SetVertexShader failed, hr %#x.\n", hr);
10024 hr = IDirect3DDevice9_SetRenderTarget(device, 0, surf1);
10025 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderTarget failed, hr=%08x\n", hr);
10026 hr = IDirect3DDevice9_SetRenderTarget(device, 1, surf2);
10027 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderTarget failed, hr=%08x\n", hr);
10028 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ);
10029 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed, hr=%08x\n", hr);
10031 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff0000ff, 0.0f, 0);
10032 ok(SUCCEEDED(hr), "Clear failed, hr %#x,\n", hr);
10033 hr = IDirect3DDevice9_GetRenderTargetData(device, surf1, readback);
10034 ok(SUCCEEDED(hr), "GetRenderTargetData failed, hr %#x.\n", hr);
10035 color = getPixelColorFromSurface(readback, 8, 8);
10036 ok(color_match(color, D3DCOLOR_ARGB(0xff, 0x00, 0x00, 0xff), 0),
10037 "Expected color 0x000000ff, got 0x%08x.\n", color);
10038 hr = IDirect3DDevice9_GetRenderTargetData(device, surf2, readback);
10039 ok(SUCCEEDED(hr), "GetRenderTargetData failed, hr %#x.\n", hr);
10040 color = getPixelColorFromSurface(readback, 8, 8);
10041 ok(color_match(color, D3DCOLOR_ARGB(0xff, 0x00, 0x00, 0xff), 0),
10042 "Expected color 0x000000ff, got 0x%08x.\n", color);
10044 /* Render targets not written by the pixel shader should be unmodified. */
10045 hr = IDirect3DDevice9_SetPixelShader(device, ps1);
10046 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
10047 hr = IDirect3DDevice9_BeginScene(device);
10048 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
10049 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, 3 * sizeof(float));
10050 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
10051 hr = IDirect3DDevice9_EndScene(device);
10052 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
10053 hr = IDirect3DDevice9_GetRenderTargetData(device, surf1, readback);
10054 ok(SUCCEEDED(hr), "GetRenderTargetData failed, hr %#x.\n", hr);
10055 color = getPixelColorFromSurface(readback, 8, 8);
10056 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x00, 0xff, 0x00), 0),
10057 "Expected color 0xff00ff00, got 0x%08x.\n", color);
10058 hr = IDirect3DDevice9_GetRenderTargetData(device, surf2, readback);
10059 ok(SUCCEEDED(hr), "GetRenderTargetData failed, hr %#x.\n", hr);
10060 for (i = 6; i < 10; ++i)
10062 for (j = 6; j < 10; ++j)
10064 color = getPixelColorFromSurface(readback, j, i);
10065 ok(color_match(color, D3DCOLOR_ARGB(0xff, 0x00, 0x00, 0xff), 0),
10066 "Expected color 0xff0000ff, got 0x%08x at %u, %u.\n", color, j, i);
10070 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff00ff00, 0.0f, 0);
10071 ok(SUCCEEDED(hr), "Clear failed, hr %#x,\n", hr);
10072 hr = IDirect3DDevice9_GetRenderTargetData(device, surf1, readback);
10073 ok(SUCCEEDED(hr), "GetRenderTargetData failed, hr %#x.\n", hr);
10074 color = getPixelColorFromSurface(readback, 8, 8);
10075 ok(color_match(color, D3DCOLOR_ARGB(0xff, 0x00, 0xff, 0x00), 0),
10076 "Expected color 0x0000ff00, got 0x%08x.\n", color);
10077 hr = IDirect3DDevice9_GetRenderTargetData(device, surf2, readback);
10078 ok(SUCCEEDED(hr), "GetRenderTargetData failed, hr %#x.\n", hr);
10079 color = getPixelColorFromSurface(readback, 8, 8);
10080 ok(color_match(color, D3DCOLOR_ARGB(0xff, 0x00, 0xff, 0x00), 0),
10081 "Expected color 0x0000ff00, got 0x%08x.\n", color);
10083 hr = IDirect3DDevice9_SetPixelShader(device, ps2);
10084 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
10086 hr = IDirect3DDevice9_BeginScene(device);
10087 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
10089 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, 3 * sizeof(float));
10090 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
10092 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
10093 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
10094 hr = IDirect3DDevice9_SetVertexShader(device, NULL);
10095 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
10096 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
10097 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
10098 hr = IDirect3DDevice9_SetRenderTarget(device, 0, backbuf);
10099 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
10100 hr = IDirect3DDevice9_SetRenderTarget(device, 1, NULL);
10101 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
10102 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1);
10103 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
10105 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *) tex1);
10106 ok(SUCCEEDED(hr), "Failed to set texture, hr %#x.\n", hr);
10107 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &texquad[0], 5 * sizeof(float));
10108 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
10110 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *) tex2);
10111 ok(SUCCEEDED(hr), "Failed to set texture, hr %#x.\n", hr);
10112 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &texquad[20], 5 * sizeof(float));
10113 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
10115 hr = IDirect3DDevice9_EndScene(device);
10116 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
10118 color = getPixelColor(device, 160, 240);
10119 ok(color == 0x0000ff00, "Texture 1(output color 1) has color 0x%08x, expected 0x0000ff00\n", color);
10120 color = getPixelColor(device, 480, 240);
10121 ok(color == 0x000000ff, "Texture 2(output color 2) has color 0x%08x, expected 0x000000ff\n", color);
10122 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
10124 IDirect3DPixelShader9_Release(ps2);
10125 IDirect3DPixelShader9_Release(ps1);
10126 IDirect3DVertexShader9_Release(vs);
10127 IDirect3DTexture9_Release(tex1);
10128 IDirect3DTexture9_Release(tex2);
10129 IDirect3DSurface9_Release(surf1);
10130 IDirect3DSurface9_Release(surf2);
10131 IDirect3DSurface9_Release(backbuf);
10132 IDirect3DSurface9_Release(readback);
10133 refcount = IDirect3DDevice9_Release(device);
10134 ok(!refcount, "Device has %u references left.\n", refcount);
10135 done:
10136 IDirect3D9_Release(d3d);
10137 DestroyWindow(window);
10140 static void pixelshader_blending_test(void)
10142 IDirect3DSurface9 *backbuffer = NULL, *offscreen = NULL;
10143 IDirect3DTexture9 *offscreenTexture = NULL;
10144 IDirect3DDevice9 *device;
10145 IDirect3D9 *d3d;
10146 ULONG refcount;
10147 int fmt_index;
10148 DWORD color;
10149 HWND window;
10150 HRESULT hr;
10152 static const struct
10154 const char *fmtName;
10155 D3DFORMAT textureFormat;
10156 D3DCOLOR resultColorBlending;
10157 D3DCOLOR resultColorNoBlending;
10159 test_formats[] =
10161 {"D3DFMT_G16R16", D3DFMT_G16R16, 0x001818ff, 0x002010ff},
10162 {"D3DFMT_R16F", D3DFMT_R16F, 0x0018ffff, 0x0020ffff},
10163 {"D3DFMT_G16R16F", D3DFMT_G16R16F, 0x001818ff, 0x002010ff},
10164 {"D3DFMT_A16B16G16R16F", D3DFMT_A16B16G16R16F, 0x00181800, 0x00201000},
10165 {"D3DFMT_R32F", D3DFMT_R32F, 0x0018ffff, 0x0020ffff},
10166 {"D3DFMT_G32R32F", D3DFMT_G32R32F, 0x001818ff, 0x002010ff},
10167 {"D3DFMT_A32B32G32R32F", D3DFMT_A32B32G32R32F, 0x00181800, 0x00201000},
10169 static const float quad[][5] =
10171 {-0.5f, -0.5f, 0.1f, 0.0f, 0.0f},
10172 {-0.5f, 0.5f, 0.1f, 0.0f, 1.0f},
10173 { 0.5f, -0.5f, 0.1f, 1.0f, 0.0f},
10174 { 0.5f, 0.5f, 0.1f, 1.0f, 1.0f},
10176 static const struct
10178 struct vec3 position;
10179 DWORD diffuse;
10181 /* Quad with R=0x10, G=0x20 */
10182 quad1[] =
10184 {{-1.0f, -1.0f, 0.1f}, 0x80102000},
10185 {{-1.0f, 1.0f, 0.1f}, 0x80102000},
10186 {{ 1.0f, -1.0f, 0.1f}, 0x80102000},
10187 {{ 1.0f, 1.0f, 0.1f}, 0x80102000},
10189 /* Quad with R=0x20, G=0x10 */
10190 quad2[] =
10192 {{-1.0f, -1.0f, 0.1f}, 0x80201000},
10193 {{-1.0f, 1.0f, 0.1f}, 0x80201000},
10194 {{ 1.0f, -1.0f, 0.1f}, 0x80201000},
10195 {{ 1.0f, 1.0f, 0.1f}, 0x80201000},
10198 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
10199 0, 0, 640, 480, NULL, NULL, NULL, NULL);
10200 d3d = Direct3DCreate9(D3D_SDK_VERSION);
10201 ok(!!d3d, "Failed to create a D3D object.\n");
10202 if (!(device = create_device(d3d, window, window, TRUE)))
10204 skip("Failed to create a D3D device, skipping tests.\n");
10205 goto done;
10208 hr = IDirect3DDevice9_GetBackBuffer(device, 0, 0, D3DBACKBUFFER_TYPE_MONO, &backbuffer);
10209 ok(hr == D3D_OK, "Can't get back buffer, hr = %08x\n", hr);
10211 for (fmt_index = 0; fmt_index < sizeof(test_formats) / sizeof(*test_formats); ++fmt_index)
10213 D3DFORMAT fmt = test_formats[fmt_index].textureFormat;
10215 if (IDirect3D9_CheckDeviceFormat(d3d, 0, D3DDEVTYPE_HAL, D3DFMT_X8R8G8B8,
10216 D3DUSAGE_RENDERTARGET, D3DRTYPE_TEXTURE, fmt) != D3D_OK)
10218 skip("%s textures not supported as render targets.\n", test_formats[fmt_index].fmtName);
10219 continue;
10222 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffffffff, 1.0f, 0);
10223 ok(hr == D3D_OK, "Clear failed, hr = %08x\n", hr);
10225 hr = IDirect3DDevice9_CreateTexture(device, 128, 128, 1, D3DUSAGE_RENDERTARGET, fmt, D3DPOOL_DEFAULT, &offscreenTexture, NULL);
10226 ok(hr == D3D_OK || hr == D3DERR_INVALIDCALL, "Creating the offscreen render target failed, hr = %08x\n", hr);
10227 if(!offscreenTexture) {
10228 continue;
10231 hr = IDirect3DTexture9_GetSurfaceLevel(offscreenTexture, 0, &offscreen);
10232 ok(hr == D3D_OK, "Can't get offscreen surface, hr = %08x\n", hr);
10233 if(!offscreen) {
10234 continue;
10237 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
10238 ok(hr == D3D_OK, "SetFVF failed, hr = %08x\n", hr);
10240 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
10241 ok(hr == D3D_OK, "SetTextureStageState failed, hr = %08x\n", hr);
10242 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
10243 ok(hr == D3D_OK, "SetTextureStageState failed, hr = %08x\n", hr);
10244 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MINFILTER, D3DTEXF_POINT);
10245 ok(SUCCEEDED(hr), "SetSamplerState D3DSAMP_MINFILTER failed (0x%08x)\n", hr);
10246 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAGFILTER, D3DTEXF_POINT);
10247 ok(SUCCEEDED(hr), "SetSamplerState D3DSAMP_MAGFILTER failed (0x%08x)\n", hr);
10248 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
10249 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState returned %08x\n", hr);
10251 /* Below we will draw two quads with different colors and try to blend
10252 * them together. The result color is compared with the expected
10253 * outcome. */
10254 hr = IDirect3DDevice9_BeginScene(device);
10255 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
10257 hr = IDirect3DDevice9_SetRenderTarget(device, 0, offscreen);
10258 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
10259 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0x00ffffff, 1.0f, 0);
10260 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
10262 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ALPHABLENDENABLE, TRUE);
10263 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
10265 /* Draw a quad using color 0x0010200. */
10266 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_SRCBLEND, D3DBLEND_ONE);
10267 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
10268 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_DESTBLEND, D3DBLEND_ZERO);
10269 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
10270 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, sizeof(quad1[0]));
10271 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
10273 /* Draw a quad using color 0x0020100. */
10274 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_SRCBLEND, D3DBLEND_SRCALPHA);
10275 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
10276 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA);
10277 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
10278 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, sizeof(quad2[0]));
10279 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
10281 /* We don't want to blend the result on the backbuffer. */
10282 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ALPHABLENDENABLE, FALSE);
10283 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
10285 /* Prepare rendering the 'blended' texture quad to the backbuffer. */
10286 hr = IDirect3DDevice9_SetRenderTarget(device, 0, backbuffer);
10287 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
10288 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)offscreenTexture);
10289 ok(SUCCEEDED(hr), "Failed to set texture, hr %#x.\n", hr);
10291 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1);
10292 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
10294 /* This time with the texture. */
10295 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(quad[0]));
10296 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
10298 hr = IDirect3DDevice9_EndScene(device);
10299 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
10301 if (IDirect3D9_CheckDeviceFormat(d3d, 0, D3DDEVTYPE_HAL, D3DFMT_X8R8G8B8,
10302 D3DUSAGE_QUERY_POSTPIXELSHADER_BLENDING, D3DRTYPE_TEXTURE, fmt) == D3D_OK)
10304 /* Compare the color of the center quad with our expectation. */
10305 color = getPixelColor(device, 320, 240);
10306 ok(color_match(color, test_formats[fmt_index].resultColorBlending, 1),
10307 "Offscreen failed for %s: Got color 0x%08x, expected 0x%08x.\n",
10308 test_formats[fmt_index].fmtName, color, test_formats[fmt_index].resultColorBlending);
10310 else
10312 /* No pixel shader blending is supported so expect garbage. The
10313 * type of 'garbage' depends on the driver version and OS. E.g. on
10314 * G16R16 ATI reports (on old r9600 drivers) 0x00ffffff and on
10315 * modern ones 0x002010ff which is also what NVIDIA reports. On
10316 * Vista NVIDIA seems to report 0x00ffffff on Geforce7 cards. */
10317 color = getPixelColor(device, 320, 240);
10318 ok((color == 0x00ffffff) || (color == test_formats[fmt_index].resultColorNoBlending),
10319 "Offscreen failed for %s: Got unexpected color 0x%08x, expected no color blending.\n",
10320 test_formats[fmt_index].fmtName, color);
10322 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
10324 IDirect3DDevice9_SetTexture(device, 0, NULL);
10325 if(offscreenTexture) {
10326 IDirect3DTexture9_Release(offscreenTexture);
10328 if(offscreen) {
10329 IDirect3DSurface9_Release(offscreen);
10333 IDirect3DSurface9_Release(backbuffer);
10334 refcount = IDirect3DDevice9_Release(device);
10335 ok(!refcount, "Device has %u references left.\n", refcount);
10336 done:
10337 IDirect3D9_Release(d3d);
10338 DestroyWindow(window);
10341 static void tssargtemp_test(void)
10343 IDirect3DDevice9 *device;
10344 IDirect3D9 *d3d;
10345 D3DCOLOR color;
10346 ULONG refcount;
10347 D3DCAPS9 caps;
10348 HWND window;
10349 HRESULT hr;
10351 static const struct
10353 struct vec3 position;
10354 DWORD diffuse;
10356 quad[] =
10358 {{-1.0f, -1.0f, 0.1f}, 0x00ff0000},
10359 {{-1.0f, 1.0f, 0.1f}, 0x00ff0000},
10360 {{ 1.0f, -1.0f, 0.1f}, 0x00ff0000},
10361 {{ 1.0f, 1.0f, 0.1f}, 0x00ff0000},
10364 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
10365 0, 0, 640, 480, NULL, NULL, NULL, NULL);
10366 d3d = Direct3DCreate9(D3D_SDK_VERSION);
10367 ok(!!d3d, "Failed to create a D3D object.\n");
10368 if (!(device = create_device(d3d, window, window, TRUE)))
10370 skip("Failed to create a D3D device, skipping tests.\n");
10371 goto done;
10374 memset(&caps, 0, sizeof(caps));
10375 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
10376 ok(hr == D3D_OK, "IDirect3DDevice9_GetDeviceCaps failed with %08x\n", hr);
10377 if(!(caps.PrimitiveMiscCaps & D3DPMISCCAPS_TSSARGTEMP)) {
10378 skip("D3DPMISCCAPS_TSSARGTEMP not supported\n");
10379 IDirect3DDevice9_Release(device);
10380 goto done;
10383 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff000000, 1.0f, 0);
10384 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
10386 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
10387 ok(hr == D3D_OK, "SetTextureStageState failed, hr = %08x\n", hr);
10388 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_DIFFUSE);
10389 ok(hr == D3D_OK, "SetTextureStageState failed, hr = %08x\n", hr);
10391 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
10392 ok(hr == D3D_OK, "SetTextureStageState failed, hr = %08x\n", hr);
10393 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_COLORARG1, D3DTA_TFACTOR);
10394 ok(hr == D3D_OK, "SetTextureStageState failed, hr = %08x\n", hr);
10395 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_RESULTARG, D3DTA_TEMP);
10396 ok(hr == D3D_OK, "SetTextureStageState failed, hr = %08x\n", hr);
10398 hr = IDirect3DDevice9_SetTextureStageState(device, 2, D3DTSS_COLOROP, D3DTOP_ADD);
10399 ok(hr == D3D_OK, "SetTextureStageState failed, hr = %08x\n", hr);
10400 hr = IDirect3DDevice9_SetTextureStageState(device, 2, D3DTSS_COLORARG1, D3DTA_CURRENT);
10401 ok(hr == D3D_OK, "SetTextureStageState failed, hr = %08x\n", hr);
10402 hr = IDirect3DDevice9_SetTextureStageState(device, 2, D3DTSS_COLORARG2, D3DTA_TEMP);
10403 ok(hr == D3D_OK, "SetTextureStageState failed, hr = %08x\n", hr);
10405 hr = IDirect3DDevice9_SetTextureStageState(device, 3, D3DTSS_COLOROP, D3DTOP_DISABLE);
10406 ok(hr == D3D_OK, "SetTextureStageState failed, hr = %08x\n", hr);
10408 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_TEXTUREFACTOR, 0x0000ff00);
10409 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState failed, hr = %08x\n", hr);
10410 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
10411 ok(SUCCEEDED(hr), "Failed to disable lighting, hr %#x.\n", hr);
10412 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
10413 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed, hr = %08x\n", hr);
10415 hr = IDirect3DDevice9_BeginScene(device);
10416 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
10417 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(quad[0]));
10418 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
10419 hr = IDirect3DDevice9_EndScene(device);
10420 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
10422 color = getPixelColor(device, 320, 240);
10423 ok(color == 0x00ffff00, "TSSARGTEMP test returned color 0x%08x, expected 0x00ffff00\n", color);
10424 IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
10426 refcount = IDirect3DDevice9_Release(device);
10427 ok(!refcount, "Device has %u references left.\n", refcount);
10428 done:
10429 IDirect3D9_Release(d3d);
10430 DestroyWindow(window);
10433 /* Drawing Indexed Geometry with instances*/
10434 static void stream_test(void)
10436 IDirect3DVertexDeclaration9 *pDecl = NULL;
10437 IDirect3DVertexShader9 *shader = NULL;
10438 IDirect3DVertexBuffer9 *vb3 = NULL;
10439 IDirect3DVertexBuffer9 *vb2 = NULL;
10440 IDirect3DVertexBuffer9 *vb = NULL;
10441 IDirect3DIndexBuffer9 *ib = NULL;
10442 IDirect3DDevice9 *device;
10443 IDirect3D9 *d3d;
10444 ULONG refcount;
10445 D3DCAPS9 caps;
10446 DWORD color;
10447 HWND window;
10448 unsigned i;
10449 HRESULT hr;
10450 BYTE *data;
10451 DWORD ind;
10453 static const struct testdata
10455 DWORD idxVertex; /* number of instances in the first stream */
10456 DWORD idxColor; /* number of instances in the second stream */
10457 DWORD idxInstance; /* should be 1 ?? */
10458 DWORD color1; /* color 1 instance */
10459 DWORD color2; /* color 2 instance */
10460 DWORD color3; /* color 3 instance */
10461 DWORD color4; /* color 4 instance */
10462 WORD strVertex; /* specify which stream to use 0-2*/
10463 WORD strColor;
10464 WORD strInstance;
10466 testcases[]=
10468 {4, 4, 1, 0x00ff0000, 0x00ff0000, 0x00ff0000, 0x00ff0000, 0, 1, 2}, /* 0 */
10469 {3, 4, 1, 0x00ff0000, 0x00ff0000, 0x00ff0000, 0x00ffffff, 0, 1, 2}, /* 1 */
10470 {2, 4, 1, 0x00ff0000, 0x00ff0000, 0x00ffffff, 0x00ffffff, 0, 1, 2}, /* 2 */
10471 {1, 4, 1, 0x00ff0000, 0x00ffffff, 0x00ffffff, 0x00ffffff, 0, 1, 2}, /* 3 */
10472 {4, 3, 1, 0x00ff0000, 0x00ff0000, 0x00ff0000, 0x00ff0000, 0, 1, 2}, /* 4 */
10473 {4, 2, 1, 0x00ff0000, 0x00ff0000, 0x00ff0000, 0x00ff0000, 0, 1, 2}, /* 5 */
10474 {4, 1, 1, 0x00ff0000, 0x00ff0000, 0x00ff0000, 0x00ff0000, 0, 1, 2}, /* 6 */
10475 {4, 0, 1, 0x00ff0000, 0x00ff0000, 0x00ff0000, 0x00ff0000, 0, 1, 2}, /* 7 */
10476 {3, 3, 1, 0x00ff0000, 0x00ff0000, 0x00ff0000, 0x00ffffff, 0, 1, 2}, /* 8 */
10477 {4, 4, 1, 0x00ff0000, 0x00ff0000, 0x00ff0000, 0x00ff0000, 1, 0, 2}, /* 9 */
10478 {4, 4, 1, 0x00ff0000, 0x00ff0000, 0x00ff0000, 0x00ff0000, 0, 2, 1}, /* 10 */
10479 {4, 4, 1, 0x00ff0000, 0x00ffffff, 0x00ffffff, 0x00ffffff, 2, 3, 1}, /* 11 */
10480 {4, 4, 1, 0x00ff0000, 0x00ff0000, 0x00ff0000, 0x00ff0000, 2, 0, 1}, /* 12 */
10481 {4, 4, 1, 0x00ff0000, 0x00ff0000, 0x00ff0000, 0x00ff0000, 1, 2, 3}, /* 13 */
10482 #if 0
10483 /* This draws one instance on some machines, no instance on others. */
10484 {0, 4, 1, 0x00ff0000, 0x00ffffff, 0x00ffffff, 0x00ffffff, 0, 1, 2}, /* 14 */
10485 /* This case is handled in a stand alone test,
10486 * SetStreamSourceFreq(0, (D3DSTREAMSOURCE_INSTANCEDATA | 1)) has to
10487 * return D3DERR_INVALIDCALL. */
10488 {4, 4, 1, 0x00ffffff, 0x00ffffff, 0x00ffffff, 0x00ffffff, 2, 1, 0}, /* 15 */
10489 #endif
10491 static const DWORD shader_code[] =
10493 0xfffe0101, /* vs_1_1 */
10494 0x0000001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
10495 0x0000001f, 0x8000000a, 0x900f0001, /* dcl_color0 v1 */
10496 0x0000001f, 0x80000005, 0x900f0002, /* dcl_texcoord v2 */
10497 0x00000001, 0x800f0000, 0x90e40000, /* mov r0, v0 */
10498 0x00000002, 0xc00f0000, 0x80e40000, 0x90e40002, /* add oPos, r0, v2 */
10499 0x00000001, 0xd00f0000, 0x90e40001, /* mov oD0, v1 */
10500 0x0000ffff
10502 static const float quad[][3] =
10504 {-0.5f, -0.5f, 1.1f}, /*0 */
10505 {-0.5f, 0.5f, 1.1f}, /*1 */
10506 { 0.5f, -0.5f, 1.1f}, /*2 */
10507 { 0.5f, 0.5f, 1.1f}, /*3 */
10509 static const float vertcolor[][4] =
10511 {1.0f, 0.0f, 0.0f, 1.0f}, /*0 */
10512 {1.0f, 0.0f, 0.0f, 1.0f}, /*1 */
10513 {1.0f, 0.0f, 0.0f, 1.0f}, /*2 */
10514 {1.0f, 0.0f, 0.0f, 1.0f}, /*3 */
10516 /* 4 position for 4 instances */
10517 static const float instancepos[][3] =
10519 {-0.6f,-0.6f, 0.0f},
10520 { 0.6f,-0.6f, 0.0f},
10521 { 0.6f, 0.6f, 0.0f},
10522 {-0.6f, 0.6f, 0.0f},
10524 static const short indices[] = {0, 1, 2, 2, 1, 3};
10525 D3DVERTEXELEMENT9 decl[] =
10527 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
10528 {1, 0, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR, 0},
10529 {2, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
10530 D3DDECL_END()
10533 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
10534 0, 0, 640, 480, NULL, NULL, NULL, NULL);
10535 d3d = Direct3DCreate9(D3D_SDK_VERSION);
10536 ok(!!d3d, "Failed to create a D3D object.\n");
10537 if (!(device = create_device(d3d, window, window, TRUE)))
10539 skip("Failed to create a D3D device, skipping tests.\n");
10540 goto done;
10543 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
10544 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
10545 if (caps.VertexShaderVersion < D3DVS_VERSION(3, 0))
10547 skip("No vs_3_0 support, skipping tests.\n");
10548 IDirect3DDevice9_Release(device);
10549 goto done;
10552 /* set the default value because it isn't done in wine? */
10553 hr = IDirect3DDevice9_SetStreamSourceFreq(device, 1, 1);
10554 ok(hr == D3D_OK, "IDirect3DDevice9_SetStreamSourceFreq failed with %08x\n", hr);
10556 /* check for D3DSTREAMSOURCE_INDEXEDDATA at stream0 */
10557 hr = IDirect3DDevice9_SetStreamSourceFreq(device, 0, (D3DSTREAMSOURCE_INSTANCEDATA | 1));
10558 ok(hr == D3DERR_INVALIDCALL, "IDirect3DDevice9_SetStreamSourceFreq failed with %08x\n", hr);
10560 /* check wrong cases */
10561 hr = IDirect3DDevice9_SetStreamSourceFreq(device, 1, 0);
10562 ok(hr == D3DERR_INVALIDCALL, "IDirect3DDevice9_SetStreamSourceFreq failed with %08x\n", hr);
10563 hr = IDirect3DDevice9_GetStreamSourceFreq(device, 1, &ind);
10564 ok(hr == D3D_OK && ind == 1, "IDirect3DDevice9_GetStreamSourceFreq failed with %08x\n", hr);
10565 hr = IDirect3DDevice9_SetStreamSourceFreq(device, 1, 2);
10566 ok(hr == D3D_OK, "IDirect3DDevice9_SetStreamSourceFreq failed with %08x\n", hr);
10567 hr = IDirect3DDevice9_GetStreamSourceFreq(device, 1, &ind);
10568 ok(hr == D3D_OK && ind == 2, "IDirect3DDevice9_GetStreamSourceFreq failed with %08x\n", hr);
10569 hr = IDirect3DDevice9_SetStreamSourceFreq(device, 1, (D3DSTREAMSOURCE_INDEXEDDATA | 0));
10570 ok(hr == D3D_OK, "IDirect3DDevice9_SetStreamSourceFreq failed with %08x\n", hr);
10571 hr = IDirect3DDevice9_GetStreamSourceFreq(device, 1, &ind);
10572 ok(hr == D3D_OK && ind == (D3DSTREAMSOURCE_INDEXEDDATA | 0), "IDirect3DDevice9_GetStreamSourceFreq failed with %08x\n", hr);
10573 hr = IDirect3DDevice9_SetStreamSourceFreq(device, 1, (D3DSTREAMSOURCE_INSTANCEDATA | 0));
10574 ok(hr == D3D_OK, "IDirect3DDevice9_SetStreamSourceFreq failed with %08x\n", hr);
10575 hr = IDirect3DDevice9_GetStreamSourceFreq(device, 1, &ind);
10576 ok(hr == D3D_OK && ind == (0U | D3DSTREAMSOURCE_INSTANCEDATA), "IDirect3DDevice9_GetStreamSourceFreq failed with %08x\n", hr);
10577 hr = IDirect3DDevice9_SetStreamSourceFreq(device, 1, (D3DSTREAMSOURCE_INSTANCEDATA | D3DSTREAMSOURCE_INDEXEDDATA | 0));
10578 ok(hr == D3DERR_INVALIDCALL, "IDirect3DDevice9_SetStreamSourceFreq failed with %08x\n", hr);
10579 hr = IDirect3DDevice9_GetStreamSourceFreq(device, 1, &ind);
10580 ok(hr == D3D_OK && ind == (0U | D3DSTREAMSOURCE_INSTANCEDATA), "IDirect3DDevice9_GetStreamSourceFreq failed with %08x\n", hr);
10582 /* set the default value back */
10583 hr = IDirect3DDevice9_SetStreamSourceFreq(device, 1, 1);
10584 ok(hr == D3D_OK, "IDirect3DDevice9_SetStreamSourceFreq failed with %08x\n", hr);
10586 /* create all VertexBuffers*/
10587 hr = IDirect3DDevice9_CreateVertexBuffer(device, sizeof(quad), 0, 0, D3DPOOL_MANAGED, &vb, NULL);
10588 ok(hr == D3D_OK, "CreateVertexBuffer failed with %08x\n", hr);
10589 if(!vb) {
10590 skip("Failed to create a vertex buffer\n");
10591 IDirect3DDevice9_Release(device);
10592 goto done;
10594 hr = IDirect3DDevice9_CreateVertexBuffer(device, sizeof(vertcolor), 0, 0, D3DPOOL_MANAGED, &vb2, NULL);
10595 ok(hr == D3D_OK, "CreateVertexBuffer failed with %08x\n", hr);
10596 if(!vb2) {
10597 skip("Failed to create a vertex buffer\n");
10598 goto out;
10600 hr = IDirect3DDevice9_CreateVertexBuffer(device, sizeof(instancepos), 0, 0, D3DPOOL_MANAGED, &vb3, NULL);
10601 ok(hr == D3D_OK, "CreateVertexBuffer failed with %08x\n", hr);
10602 if(!vb3) {
10603 skip("Failed to create a vertex buffer\n");
10604 goto out;
10607 /* create IndexBuffer*/
10608 hr = IDirect3DDevice9_CreateIndexBuffer(device, sizeof(indices), 0, D3DFMT_INDEX16, D3DPOOL_DEFAULT, &ib, NULL);
10609 ok(hr == D3D_OK, "IDirect3DDevice9_CreateIndexBuffer failed with %08x\n", hr);
10610 if(!ib) {
10611 skip("Failed to create an index buffer\n");
10612 goto out;
10615 /* copy all Buffers (Vertex + Index)*/
10616 hr = IDirect3DVertexBuffer9_Lock(vb, 0, sizeof(quad), (void **) &data, 0);
10617 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Lock failed with %08x\n", hr);
10618 memcpy(data, quad, sizeof(quad));
10619 hr = IDirect3DVertexBuffer9_Unlock(vb);
10620 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Unlock failed with %08x\n", hr);
10621 hr = IDirect3DVertexBuffer9_Lock(vb2, 0, sizeof(vertcolor), (void **) &data, 0);
10622 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Lock failed with %08x\n", hr);
10623 memcpy(data, vertcolor, sizeof(vertcolor));
10624 hr = IDirect3DVertexBuffer9_Unlock(vb2);
10625 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Unlock failed with %08x\n", hr);
10626 hr = IDirect3DVertexBuffer9_Lock(vb3, 0, sizeof(instancepos), (void **) &data, 0);
10627 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Lock failed with %08x\n", hr);
10628 memcpy(data, instancepos, sizeof(instancepos));
10629 hr = IDirect3DVertexBuffer9_Unlock(vb3);
10630 ok(hr == D3D_OK, "IDirect3DVertexBuffer9_Unlock failed with %08x\n", hr);
10631 hr = IDirect3DIndexBuffer9_Lock(ib, 0, sizeof(indices), (void **) &data, 0);
10632 ok(hr == D3D_OK, "IDirect3DIndexBuffer9_Lock failed with %08x\n", hr);
10633 memcpy(data, indices, sizeof(indices));
10634 hr = IDirect3DIndexBuffer9_Unlock(ib);
10635 ok(hr == D3D_OK, "IDirect3DIndexBuffer9_Unlock failed with %08x\n", hr);
10637 /* create VertexShader */
10638 hr = IDirect3DDevice9_CreateVertexShader(device, shader_code, &shader);
10639 ok(SUCCEEDED(hr), "IDirect3DDevice9_CreateVertexShader failed hr=%08x\n", hr);
10640 if(!shader) {
10641 skip("Failed to create a vetex shader\n");
10642 goto out;
10645 hr = IDirect3DDevice9_SetVertexShader(device, shader);
10646 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetVertexShader failed hr=%08x\n", hr);
10648 hr = IDirect3DDevice9_SetIndices(device, ib);
10649 ok(hr == D3D_OK, "IDirect3DDevice9_SetIndices failed with %08x\n", hr);
10651 /* run all tests */
10652 for( i = 0; i < sizeof(testcases)/sizeof(testcases[0]); ++i)
10654 struct testdata act = testcases[i];
10655 decl[0].Stream = act.strVertex;
10656 decl[1].Stream = act.strColor;
10657 decl[2].Stream = act.strInstance;
10658 /* create VertexDeclarations */
10659 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl, &pDecl);
10660 ok(SUCCEEDED(hr), "IDirect3DDevice9_CreateVertexDeclaration failed hr=%08x (case %i)\n", hr, i);
10662 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffffffff, 1.0f, 0);
10663 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x (case %i)\n", hr, i);
10665 hr = IDirect3DDevice9_BeginScene(device);
10666 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
10668 hr = IDirect3DDevice9_SetVertexDeclaration(device, pDecl);
10669 ok(SUCCEEDED(hr), "Failed to set vertex declaration, hr %#x.\n", hr);
10671 hr = IDirect3DDevice9_SetStreamSourceFreq(device, act.strVertex,
10672 (D3DSTREAMSOURCE_INDEXEDDATA | act.idxVertex));
10673 ok(SUCCEEDED(hr), "Failed to set stream source frequency, hr %#x.\n", hr);
10674 hr = IDirect3DDevice9_SetStreamSource(device, act.strVertex, vb, 0, sizeof(quad[0]));
10675 ok(SUCCEEDED(hr), "Failed to set stream source, hr %#x.\n", hr);
10677 hr = IDirect3DDevice9_SetStreamSourceFreq(device, act.strColor,
10678 (D3DSTREAMSOURCE_INDEXEDDATA | act.idxColor));
10679 ok(SUCCEEDED(hr), "Failed to set stream source frequency, hr %#x.\n", hr);
10680 hr = IDirect3DDevice9_SetStreamSource(device, act.strColor, vb2, 0, sizeof(vertcolor[0]));
10681 ok(SUCCEEDED(hr), "Failed to set stream source, hr %#x.\n", hr);
10683 hr = IDirect3DDevice9_SetStreamSourceFreq(device, act.strInstance,
10684 (D3DSTREAMSOURCE_INSTANCEDATA | act.idxInstance));
10685 ok(SUCCEEDED(hr), "Failed to set stream source frequency, hr %#x.\n", hr);
10686 hr = IDirect3DDevice9_SetStreamSource(device, act.strInstance, vb3, 0, sizeof(instancepos[0]));
10687 ok(SUCCEEDED(hr), "Failed to set stream source, hr %#x.\n", hr);
10689 hr = IDirect3DDevice9_DrawIndexedPrimitive(device, D3DPT_TRIANGLELIST, 0, 0, 4, 0, 2);
10690 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
10691 hr = IDirect3DDevice9_EndScene(device);
10692 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
10694 /* set all StreamSource && StreamSourceFreq back to default */
10695 hr = IDirect3DDevice9_SetStreamSourceFreq(device, act.strVertex, 1);
10696 ok(SUCCEEDED(hr), "Failed to set stream source frequency, hr %#x.\n", hr);
10697 hr = IDirect3DDevice9_SetStreamSource(device, act.strVertex, NULL, 0, 0);
10698 ok(SUCCEEDED(hr), "Failed to set stream source, hr %#x.\n", hr);
10699 hr = IDirect3DDevice9_SetStreamSourceFreq(device, act.idxColor, 1);
10700 ok(SUCCEEDED(hr), "Failed to set stream source frequency, hr %#x.\n", hr);
10701 hr = IDirect3DDevice9_SetStreamSource(device, act.idxColor, NULL, 0, 0);
10702 ok(SUCCEEDED(hr), "Failed to set stream source, hr %#x.\n", hr);
10703 hr = IDirect3DDevice9_SetStreamSourceFreq(device, act.idxInstance, 1);
10704 ok(SUCCEEDED(hr), "Failed to set stream source frequency, hr %#x.\n", hr);
10705 hr = IDirect3DDevice9_SetStreamSource(device, act.idxInstance, NULL, 0, 0);
10706 ok(SUCCEEDED(hr), "Failed to set stream source, hr %#x.\n", hr);
10708 hr = IDirect3DVertexDeclaration9_Release(pDecl);
10709 ok(hr == D3D_OK, "IDirect3DVertexDeclaration9_Release failed with %08x (case %i)\n", hr, i);
10711 color = getPixelColor(device, 160, 360);
10712 ok(color == act.color1, "has color 0x%08x, expected 0x%08x (case %i)\n", color, act.color1, i);
10713 color = getPixelColor(device, 480, 360);
10714 ok(color == act.color2, "has color 0x%08x, expected 0x%08x (case %i)\n", color, act.color2, i);
10715 color = getPixelColor(device, 480, 120);
10716 ok(color == act.color3, "has color 0x%08x, expected 0x%08x (case %i)\n", color, act.color3, i);
10717 color = getPixelColor(device, 160, 120);
10718 ok(color == act.color4, "has color 0x%08x, expected 0x%08x (case %i)\n", color, act.color4, i);
10720 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
10721 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x (case %i)\n", hr, i);
10724 out:
10725 if(vb) IDirect3DVertexBuffer9_Release(vb);
10726 if(vb2)IDirect3DVertexBuffer9_Release(vb2);
10727 if(vb3)IDirect3DVertexBuffer9_Release(vb3);
10728 if(ib)IDirect3DIndexBuffer9_Release(ib);
10729 if(shader)IDirect3DVertexShader9_Release(shader);
10730 refcount = IDirect3DDevice9_Release(device);
10731 ok(!refcount, "Device has %u references left.\n", refcount);
10732 done:
10733 IDirect3D9_Release(d3d);
10734 DestroyWindow(window);
10737 static void np2_stretch_rect_test(void)
10739 IDirect3DSurface9 *src = NULL, *dst = NULL, *backbuffer = NULL;
10740 IDirect3DTexture9 *dsttex = NULL;
10741 IDirect3DDevice9 *device;
10742 IDirect3D9 *d3d;
10743 D3DCOLOR color;
10744 ULONG refcount;
10745 HWND window;
10746 HRESULT hr;
10748 static const D3DRECT r1 = {0, 0, 50, 50 };
10749 static const D3DRECT r2 = {50, 0, 100, 50 };
10750 static const D3DRECT r3 = {50, 50, 100, 100};
10751 static const D3DRECT r4 = {0, 50, 50, 100};
10752 static const float quad[] =
10754 -1.0f, -1.0f, 0.1f, 0.0f, 0.0f,
10755 -1.0f, 1.0f, 0.1f, 0.0f, 1.0f,
10756 1.0f, -1.0f, 0.1f, 1.0f, 0.0f,
10757 1.0f, 1.0f, 0.1f, 1.0f, 1.0f,
10760 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
10761 0, 0, 640, 480, NULL, NULL, NULL, NULL);
10762 d3d = Direct3DCreate9(D3D_SDK_VERSION);
10763 ok(!!d3d, "Failed to create a D3D object.\n");
10764 if (!(device = create_device(d3d, window, window, TRUE)))
10766 skip("Failed to create a D3D device, skipping tests.\n");
10767 goto done;
10770 hr = IDirect3DDevice9_GetBackBuffer(device, 0, 0, D3DBACKBUFFER_TYPE_MONO, &backbuffer);
10771 ok(hr == D3D_OK, "IDirect3DDevice9_GetBackBuffer failed with %08x\n", hr);
10773 hr = IDirect3DDevice9_CreateRenderTarget(device, 100, 100, D3DFMT_A8R8G8B8, D3DMULTISAMPLE_NONE, 0, TRUE, &src, NULL );
10774 ok(hr == D3D_OK || hr == D3DERR_INVALIDCALL, "IDirect3DDevice9_CreateRenderTarget failed with %08x\n", hr);
10775 hr = IDirect3DDevice9_CreateTexture(device, 25, 25, 1, D3DUSAGE_RENDERTARGET, D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &dsttex, NULL);
10776 ok(hr == D3D_OK || hr == D3DERR_INVALIDCALL, "IDirect3DDevice9_CreateTexture failed with %08x\n", hr);
10778 if(!src || !dsttex) {
10779 skip("One or more test resources could not be created\n");
10780 goto cleanup;
10783 hr = IDirect3DTexture9_GetSurfaceLevel(dsttex, 0, &dst);
10784 ok(hr == D3D_OK, "IDirect3DTexture9_GetSurfaceLevel failed with %08x\n", hr);
10786 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff00ffff, 1.0f, 0);
10787 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
10789 /* Clear the StretchRect destination for debugging */
10790 hr = IDirect3DDevice9_SetRenderTarget(device, 0, dst);
10791 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderTarget failed with %08x\n", hr);
10792 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffff00ff, 0.0, 0);
10793 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
10795 hr = IDirect3DDevice9_SetRenderTarget(device, 0, src);
10796 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderTarget failed with %08x\n", hr);
10798 hr = IDirect3DDevice9_Clear(device, 1, &r1, D3DCLEAR_TARGET, 0xffff0000, 0.0, 0);
10799 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
10800 hr = IDirect3DDevice9_Clear(device, 1, &r2, D3DCLEAR_TARGET, 0xff00ff00, 0.0, 0);
10801 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
10802 hr = IDirect3DDevice9_Clear(device, 1, &r3, D3DCLEAR_TARGET, 0xff0000ff, 0.0, 0);
10803 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
10804 hr = IDirect3DDevice9_Clear(device, 1, &r4, D3DCLEAR_TARGET, 0xff000000, 0.0, 0);
10805 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %08x\n", hr);
10807 /* Stretchrect before setting the render target back to the backbuffer. This will make Wine use
10808 * the target -> texture GL blit path
10810 hr = IDirect3DDevice9_StretchRect(device, src, NULL, dst, NULL, D3DTEXF_POINT);
10811 ok(hr == D3D_OK, "IDirect3DDevice9_StretchRect failed with %08x\n", hr);
10812 IDirect3DSurface9_Release(dst);
10814 hr = IDirect3DDevice9_SetRenderTarget(device, 0, backbuffer);
10815 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderTarget failed with %08x\n", hr);
10817 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *) dsttex);
10818 ok(hr == D3D_OK, "IDirect3DDevice9_SetTexture failed with %08x\n", hr);
10819 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1);
10820 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed with %08x\n", hr);
10821 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
10822 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed with %08x\n", hr);
10823 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
10824 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed with %08x\n", hr);
10826 hr = IDirect3DDevice9_BeginScene(device);
10827 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
10828 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(float) * 5);
10829 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
10830 hr = IDirect3DDevice9_EndScene(device);
10831 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
10833 color = getPixelColor(device, 160, 360);
10834 ok(color == 0x00ff0000, "stretchrect: Pixel 160,360 has color 0x%08x, expected 0x00ff0000\n", color);
10835 color = getPixelColor(device, 480, 360);
10836 ok(color == 0x0000ff00, "stretchrect: Pixel 480,360 has color 0x%08x, expected 0x0000ff00\n", color);
10837 color = getPixelColor(device, 480, 120);
10838 ok(color == 0x000000ff, "stretchrect: Pixel 480,120 has color 0x%08x, expected 0x000000ff\n", color);
10839 color = getPixelColor(device, 160, 120);
10840 ok(color == 0x00000000, "stretchrect: Pixel 160,120 has color 0x%08x, expected 0x00000000\n", color);
10841 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
10842 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
10844 cleanup:
10845 if(src) IDirect3DSurface9_Release(src);
10846 if(backbuffer) IDirect3DSurface9_Release(backbuffer);
10847 if(dsttex) IDirect3DTexture9_Release(dsttex);
10848 refcount = IDirect3DDevice9_Release(device);
10849 ok(!refcount, "Device has %u references left.\n", refcount);
10850 done:
10851 IDirect3D9_Release(d3d);
10852 DestroyWindow(window);
10855 static void texop_test(void)
10857 IDirect3DVertexDeclaration9 *vertex_declaration = NULL;
10858 IDirect3DTexture9 *texture = NULL;
10859 D3DLOCKED_RECT locked_rect;
10860 IDirect3DDevice9 *device;
10861 IDirect3D9 *d3d;
10862 D3DCOLOR color;
10863 ULONG refcount;
10864 D3DCAPS9 caps;
10865 HWND window;
10866 HRESULT hr;
10867 unsigned i;
10869 static const struct {
10870 float x, y, z;
10871 float s, t;
10872 D3DCOLOR diffuse;
10873 } quad[] = {
10874 {-1.0f, -1.0f, 0.1f, -1.0f, -1.0f, D3DCOLOR_ARGB(0x55, 0xff, 0x00, 0x00)},
10875 {-1.0f, 1.0f, 0.1f, -1.0f, 1.0f, D3DCOLOR_ARGB(0x55, 0xff, 0x00, 0x00)},
10876 { 1.0f, -1.0f, 0.1f, 1.0f, -1.0f, D3DCOLOR_ARGB(0x55, 0xff, 0x00, 0x00)},
10877 { 1.0f, 1.0f, 0.1f, 1.0f, 1.0f, D3DCOLOR_ARGB(0x55, 0xff, 0x00, 0x00)}
10880 static const D3DVERTEXELEMENT9 decl_elements[] = {
10881 {0, 0, D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
10882 {0, 12, D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
10883 {0, 20, D3DDECLTYPE_D3DCOLOR, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR, 0},
10884 D3DDECL_END()
10887 static const struct {
10888 D3DTEXTUREOP op;
10889 const char *name;
10890 DWORD caps_flag;
10891 D3DCOLOR result;
10892 } test_data[] = {
10893 {D3DTOP_SELECTARG1, "SELECTARG1", D3DTEXOPCAPS_SELECTARG1, D3DCOLOR_ARGB(0x00, 0x00, 0xff, 0x00)},
10894 {D3DTOP_SELECTARG2, "SELECTARG2", D3DTEXOPCAPS_SELECTARG2, D3DCOLOR_ARGB(0x00, 0x33, 0x33, 0x33)},
10895 {D3DTOP_MODULATE, "MODULATE", D3DTEXOPCAPS_MODULATE, D3DCOLOR_ARGB(0x00, 0x00, 0x33, 0x00)},
10896 {D3DTOP_MODULATE2X, "MODULATE2X", D3DTEXOPCAPS_MODULATE2X, D3DCOLOR_ARGB(0x00, 0x00, 0x66, 0x00)},
10897 {D3DTOP_MODULATE4X, "MODULATE4X", D3DTEXOPCAPS_MODULATE4X, D3DCOLOR_ARGB(0x00, 0x00, 0xcc, 0x00)},
10898 {D3DTOP_ADD, "ADD", D3DTEXOPCAPS_ADD, D3DCOLOR_ARGB(0x00, 0x33, 0xff, 0x33)},
10899 {D3DTOP_ADDSIGNED, "ADDSIGNED", D3DTEXOPCAPS_ADDSIGNED, D3DCOLOR_ARGB(0x00, 0x00, 0xb2, 0x00)},
10900 {D3DTOP_ADDSIGNED2X, "ADDSIGNED2X", D3DTEXOPCAPS_ADDSIGNED2X, D3DCOLOR_ARGB(0x00, 0x00, 0xff, 0x00)},
10901 {D3DTOP_SUBTRACT, "SUBTRACT", D3DTEXOPCAPS_SUBTRACT, D3DCOLOR_ARGB(0x00, 0x00, 0xcc, 0x00)},
10902 {D3DTOP_ADDSMOOTH, "ADDSMOOTH", D3DTEXOPCAPS_ADDSMOOTH, D3DCOLOR_ARGB(0x00, 0x33, 0xff, 0x33)},
10903 {D3DTOP_BLENDDIFFUSEALPHA, "BLENDDIFFUSEALPHA", D3DTEXOPCAPS_BLENDDIFFUSEALPHA, D3DCOLOR_ARGB(0x00, 0x22, 0x77, 0x22)},
10904 {D3DTOP_BLENDTEXTUREALPHA, "BLENDTEXTUREALPHA", D3DTEXOPCAPS_BLENDTEXTUREALPHA, D3DCOLOR_ARGB(0x00, 0x14, 0xad, 0x14)},
10905 {D3DTOP_BLENDFACTORALPHA, "BLENDFACTORALPHA", D3DTEXOPCAPS_BLENDFACTORALPHA, D3DCOLOR_ARGB(0x00, 0x07, 0xe4, 0x07)},
10906 {D3DTOP_BLENDTEXTUREALPHAPM, "BLENDTEXTUREALPHAPM", D3DTEXOPCAPS_BLENDTEXTUREALPHAPM, D3DCOLOR_ARGB(0x00, 0x14, 0xff, 0x14)},
10907 {D3DTOP_BLENDCURRENTALPHA, "BLENDCURRENTALPHA", D3DTEXOPCAPS_BLENDCURRENTALPHA, D3DCOLOR_ARGB(0x00, 0x22, 0x77, 0x22)},
10908 {D3DTOP_MODULATEALPHA_ADDCOLOR, "MODULATEALPHA_ADDCOLOR", D3DTEXOPCAPS_MODULATEALPHA_ADDCOLOR, D3DCOLOR_ARGB(0x00, 0x1f, 0xff, 0x1f)},
10909 {D3DTOP_MODULATECOLOR_ADDALPHA, "MODULATECOLOR_ADDALPHA", D3DTEXOPCAPS_MODULATECOLOR_ADDALPHA, D3DCOLOR_ARGB(0x00, 0x99, 0xcc, 0x99)},
10910 {D3DTOP_MODULATEINVALPHA_ADDCOLOR, "MODULATEINVALPHA_ADDCOLOR", D3DTEXOPCAPS_MODULATEINVALPHA_ADDCOLOR, D3DCOLOR_ARGB(0x00, 0x14, 0xff, 0x14)},
10911 {D3DTOP_MODULATEINVCOLOR_ADDALPHA, "MODULATEINVCOLOR_ADDALPHA", D3DTEXOPCAPS_MODULATEINVCOLOR_ADDALPHA, D3DCOLOR_ARGB(0x00, 0xcc, 0x99, 0xcc)},
10912 /* BUMPENVMAP & BUMPENVMAPLUMINANCE have their own tests */
10913 {D3DTOP_DOTPRODUCT3, "DOTPRODUCT3", D3DTEXOPCAPS_DOTPRODUCT3, D3DCOLOR_ARGB(0x00, 0x99, 0x99, 0x99)},
10914 {D3DTOP_MULTIPLYADD, "MULTIPLYADD", D3DTEXOPCAPS_MULTIPLYADD, D3DCOLOR_ARGB(0x00, 0xff, 0x33, 0x00)},
10915 {D3DTOP_LERP, "LERP", D3DTEXOPCAPS_LERP, D3DCOLOR_ARGB(0x00, 0x00, 0x33, 0x33)},
10918 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
10919 0, 0, 640, 480, NULL, NULL, NULL, NULL);
10920 d3d = Direct3DCreate9(D3D_SDK_VERSION);
10921 ok(!!d3d, "Failed to create a D3D object.\n");
10922 if (!(device = create_device(d3d, window, window, TRUE)))
10924 skip("Failed to create a D3D device, skipping tests.\n");
10925 goto done;
10928 memset(&caps, 0, sizeof(caps));
10929 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
10930 ok(SUCCEEDED(hr), "GetDeviceCaps failed with 0x%08x\n", hr);
10932 hr = IDirect3DDevice9_CreateVertexDeclaration(device, decl_elements, &vertex_declaration);
10933 ok(SUCCEEDED(hr), "CreateVertexDeclaration failed with 0x%08x\n", hr);
10934 hr = IDirect3DDevice9_SetVertexDeclaration(device, vertex_declaration);
10935 ok(SUCCEEDED(hr), "SetVertexDeclaration failed with 0x%08x\n", hr);
10937 hr = IDirect3DDevice9_CreateTexture(device, 1, 1, 1, 0, D3DFMT_A8R8G8B8, D3DPOOL_MANAGED, &texture, NULL);
10938 ok(SUCCEEDED(hr), "IDirect3DDevice9_CreateTexture failed with 0x%08x\n", hr);
10939 hr = IDirect3DTexture9_LockRect(texture, 0, &locked_rect, NULL, 0);
10940 ok(SUCCEEDED(hr), "LockRect failed with 0x%08x\n", hr);
10941 *((DWORD *)locked_rect.pBits) = D3DCOLOR_ARGB(0x99, 0x00, 0xff, 0x00);
10942 hr = IDirect3DTexture9_UnlockRect(texture, 0);
10943 ok(SUCCEEDED(hr), "UnlockRect failed with 0x%08x\n", hr);
10944 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)texture);
10945 ok(SUCCEEDED(hr), "SetTexture failed with 0x%08x\n", hr);
10947 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG0, D3DTA_DIFFUSE);
10948 ok(SUCCEEDED(hr), "SetTextureStageState failed with 0x%08x\n", hr);
10949 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
10950 ok(SUCCEEDED(hr), "SetTextureStageState failed with 0x%08x\n", hr);
10951 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG2, D3DTA_TFACTOR);
10952 ok(SUCCEEDED(hr), "SetTextureStageState failed with 0x%08x\n", hr);
10954 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_COLOROP, D3DTOP_DISABLE);
10955 ok(SUCCEEDED(hr), "SetTextureStageState failed with 0x%08x\n", hr);
10957 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
10958 ok(SUCCEEDED(hr), "SetRenderState failed with 0x%08x\n", hr);
10959 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_TEXTUREFACTOR, 0xdd333333);
10960 ok(SUCCEEDED(hr), "SetRenderState failed with 0x%08x\n", hr);
10961 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_COLORWRITEENABLE, D3DCOLORWRITEENABLE_RED | D3DCOLORWRITEENABLE_GREEN | D3DCOLORWRITEENABLE_BLUE | D3DCOLORWRITEENABLE_ALPHA);
10962 ok(SUCCEEDED(hr), "SetRenderState failed with 0x%08x\n", hr);
10964 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x00000000, 1.0f, 0);
10965 ok(SUCCEEDED(hr), "IDirect3DDevice9_Clear failed with 0x%08x\n", hr);
10967 for (i = 0; i < sizeof(test_data) / sizeof(*test_data); ++i)
10969 if (!(caps.TextureOpCaps & test_data[i].caps_flag))
10971 skip("tex operation %s not supported\n", test_data[i].name);
10972 continue;
10975 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, test_data[i].op);
10976 ok(SUCCEEDED(hr), "SetTextureStageState (%s) failed with 0x%08x\n", test_data[i].name, hr);
10978 hr = IDirect3DDevice9_BeginScene(device);
10979 ok(SUCCEEDED(hr), "BeginScene failed with 0x%08x\n", hr);
10981 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
10982 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed with 0x%08x\n", hr);
10984 hr = IDirect3DDevice9_EndScene(device);
10985 ok(SUCCEEDED(hr), "EndScene failed with 0x%08x\n", hr);
10987 color = getPixelColor(device, 320, 240);
10988 ok(color_match(color, test_data[i].result, 3), "Operation %s returned color 0x%08x, expected 0x%08x\n",
10989 test_data[i].name, color, test_data[i].result);
10991 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
10992 ok(SUCCEEDED(hr), "Present failed with 0x%08x\n", hr);
10995 IDirect3DTexture9_Release(texture);
10996 IDirect3DVertexDeclaration9_Release(vertex_declaration);
10997 refcount = IDirect3DDevice9_Release(device);
10998 ok(!refcount, "Device has %u references left.\n", refcount);
10999 done:
11000 IDirect3D9_Release(d3d);
11001 DestroyWindow(window);
11004 static void yuv_color_test(void)
11006 HRESULT hr;
11007 IDirect3DSurface9 *surface, *target;
11008 unsigned int i;
11009 D3DLOCKED_RECT lr;
11010 IDirect3D9 *d3d;
11011 D3DCOLOR color;
11012 D3DFORMAT skip_once = D3DFMT_UNKNOWN;
11013 IDirect3DDevice9 *device;
11014 D3DSURFACE_DESC desc;
11015 ULONG refcount;
11016 HWND window;
11018 static const struct
11020 DWORD in;
11021 D3DFORMAT format;
11022 const char *fmt_string;
11023 D3DCOLOR left, right;
11025 test_data[] =
11027 {0x00000000, D3DFMT_UYVY, "D3DFMT_UYVY", 0x00008700, 0x00008700},
11028 {0xff000000, D3DFMT_UYVY, "D3DFMT_UYVY", 0x00008700, 0x004bff1c},
11029 {0x00ff0000, D3DFMT_UYVY, "D3DFMT_UYVY", 0x00b30000, 0x00b30000},
11030 {0x0000ff00, D3DFMT_UYVY, "D3DFMT_UYVY", 0x004bff1c, 0x00008700},
11031 {0x000000ff, D3DFMT_UYVY, "D3DFMT_UYVY", 0x000030e1, 0x000030e1},
11032 {0xffff0000, D3DFMT_UYVY, "D3DFMT_UYVY", 0x00b30000, 0x00ffd01c},
11033 {0xff00ff00, D3DFMT_UYVY, "D3DFMT_UYVY", 0x004bff1c, 0x004bff1c},
11034 {0xff0000ff, D3DFMT_UYVY, "D3DFMT_UYVY", 0x000030e1, 0x004bffff},
11035 {0x00ffff00, D3DFMT_UYVY, "D3DFMT_UYVY", 0x00ffd01c, 0x00b30000},
11036 {0x00ff00ff, D3DFMT_UYVY, "D3DFMT_UYVY", 0x00b300e1, 0x00b300e1},
11037 {0x0000ffff, D3DFMT_UYVY, "D3DFMT_UYVY", 0x004bffff, 0x001030e1},
11038 {0xffffff00, D3DFMT_UYVY, "D3DFMT_UYVY", 0x00ffd01c, 0x00ffd01c},
11039 {0xffff00ff, D3DFMT_UYVY, "D3DFMT_UYVY", 0x00b300e1, 0x00ff79ff},
11040 {0xffffffff, D3DFMT_UYVY, "D3DFMT_UYVY", 0x00ff79ff, 0x00ff79ff},
11041 {0x4cff4c54, D3DFMT_UYVY, "D3DFMT_UYVY", 0x00ff0000, 0x00ff0000},
11042 {0x00800080, D3DFMT_UYVY, "D3DFMT_UYVY", 0x00000000, 0x00000000},
11043 {0xff80ff80, D3DFMT_UYVY, "D3DFMT_UYVY", 0x00ffffff, 0x00ffffff},
11044 {0x1c6b1cff, D3DFMT_UYVY, "D3DFMT_UYVY", 0x000000fd, 0x000000fd},
11046 {0x00000000, D3DFMT_YUY2, "D3DFMT_YUY2", 0x00008700, 0x00008700},
11047 {0xff000000, D3DFMT_YUY2, "D3DFMT_YUY2", 0x00b30000, 0x00b30000},
11048 {0x00ff0000, D3DFMT_YUY2, "D3DFMT_YUY2", 0x00008700, 0x004bff1c},
11049 {0x0000ff00, D3DFMT_YUY2, "D3DFMT_YUY2", 0x000030e1, 0x000030e1},
11050 {0x000000ff, D3DFMT_YUY2, "D3DFMT_YUY2", 0x004bff1c, 0x00008700},
11051 {0xffff0000, D3DFMT_YUY2, "D3DFMT_YUY2", 0x00b30000, 0x00ffd01c},
11052 {0xff00ff00, D3DFMT_YUY2, "D3DFMT_YUY2", 0x00b300e1, 0x00b300e1},
11053 {0xff0000ff, D3DFMT_YUY2, "D3DFMT_YUY2", 0x00ffd01c, 0x00b30000},
11054 {0x00ffff00, D3DFMT_YUY2, "D3DFMT_YUY2", 0x000030e1, 0x004bffff},
11055 {0x00ff00ff, D3DFMT_YUY2, "D3DFMT_YUY2", 0x004bff1c, 0x004bff1c},
11056 {0x0000ffff, D3DFMT_YUY2, "D3DFMT_YUY2", 0x004bffff, 0x000030e1},
11057 {0xffffff00, D3DFMT_YUY2, "D3DFMT_YUY2", 0x00b300e1, 0x00ff79ff},
11058 {0xffff00ff, D3DFMT_YUY2, "D3DFMT_YUY2", 0x00ffd01c, 0x00ffd01c},
11059 {0xffffffff, D3DFMT_YUY2, "D3DFMT_YUY2", 0x00ff79ff, 0x00ff79ff},
11060 {0x4cff4c54, D3DFMT_YUY2, "D3DFMT_YUY2", 0x000b8b00, 0x00b6ffa3},
11061 {0x00800080, D3DFMT_YUY2, "D3DFMT_YUY2", 0x0000ff00, 0x0000ff00},
11062 {0xff80ff80, D3DFMT_YUY2, "D3DFMT_YUY2", 0x00ff00ff, 0x00ff00ff},
11063 {0x1c6b1cff, D3DFMT_YUY2, "D3DFMT_YUY2", 0x006dff45, 0x0000d500},
11066 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
11067 0, 0, 640, 480, NULL, NULL, NULL, NULL);
11068 d3d = Direct3DCreate9(D3D_SDK_VERSION);
11069 ok(!!d3d, "Failed to create a D3D object.\n");
11070 if (!(device = create_device(d3d, window, window, TRUE)))
11072 skip("Failed to create a D3D device, skipping tests.\n");
11073 goto done;
11076 hr = IDirect3DDevice9_GetRenderTarget(device, 0, &target);
11077 ok(SUCCEEDED(hr), "Failed to get render target, hr %#x.\n", hr);
11078 hr = IDirect3DSurface9_GetDesc(target, &desc);
11079 ok(SUCCEEDED(hr), "Failed to get surface description, hr %#x.\n", hr);
11081 for (i = 0; i < sizeof(test_data) / sizeof(test_data[0]); i++)
11083 /* Some(all?) Windows drivers do not support YUV 3D textures, only 2D surfaces in StretchRect.
11084 * Thus use StretchRect to draw the YUV surface onto the screen instead of drawPrimitive. */
11085 if (FAILED(IDirect3D9_CheckDeviceFormat(d3d, 0, D3DDEVTYPE_HAL,
11086 D3DFMT_X8R8G8B8, 0, D3DRTYPE_SURFACE, test_data[i].format)))
11088 if (skip_once != test_data[i].format)
11090 skip("%s is not supported.\n", test_data[i].fmt_string);
11091 skip_once = test_data[i].format;
11093 continue;
11095 if (FAILED(IDirect3D9_CheckDeviceFormatConversion(d3d, 0,
11096 D3DDEVTYPE_HAL, test_data[i].format, desc.Format)))
11098 if (skip_once != test_data[i].format)
11100 skip("Driver cannot blit %s surfaces.\n", test_data[i].fmt_string);
11101 skip_once = test_data[i].format;
11103 continue;
11106 /* A pixel is effectively 16 bit large, but two pixels are stored together, so the minimum size is 2x1.
11107 * However, Nvidia Windows drivers have problems with 2x1 YUY2/UYVY surfaces, so use a 4x1 surface and
11108 * fill the second block with dummy data. If the surface has a size of 2x1, those drivers ignore the
11109 * second luminance value, resulting in an incorrect color in the right pixel. */
11110 hr = IDirect3DDevice9_CreateOffscreenPlainSurface(device, 4, 1, test_data[i].format,
11111 D3DPOOL_DEFAULT, &surface, NULL);
11112 ok(SUCCEEDED(hr), "Failed to create surface, hr %#x.\n", hr);
11115 hr = IDirect3DSurface9_LockRect(surface, &lr, NULL, 0);
11116 ok(SUCCEEDED(hr), "Failed to lock surface, hr %#x.\n", hr);
11117 ((DWORD *)lr.pBits)[0] = test_data[i].in;
11118 ((DWORD *)lr.pBits)[1] = 0x00800080;
11119 hr = IDirect3DSurface9_UnlockRect(surface);
11120 ok(SUCCEEDED(hr), "Failed to unlock surface, hr %#x.\n", hr);
11122 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0x00000000, 1.0f, 0);
11123 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
11124 hr = IDirect3DDevice9_StretchRect(device, surface, NULL, target, NULL, D3DTEXF_POINT);
11125 ok(SUCCEEDED(hr), "Failed to draw surface onto backbuffer, hr %#x.\n", hr);
11127 /* Some Windows drivers (mostly Nvidia, but also some VM drivers) insist on doing linear filtering
11128 * although we asked for point filtering. Be careful when reading the results and use the pixel
11129 * centers. In the future we may want to add tests for the filtered pixels as well.
11131 * Unfortunately different implementations(Windows-Nvidia and Mac-AMD tested) interpret some colors
11132 * vastly differently, so we need a max diff of 18. */
11133 color = getPixelColor(device, 1, 240);
11134 ok(color_match(color, test_data[i].left, 18),
11135 "Input 0x%08x: Got color 0x%08x for pixel 1/1, expected 0x%08x, format %s.\n",
11136 test_data[i].in, color, test_data[i].left, test_data[i].fmt_string);
11137 color = getPixelColor(device, 318, 240);
11138 ok(color_match(color, test_data[i].right, 18),
11139 "Input 0x%08x: Got color 0x%08x for pixel 2/1, expected 0x%08x, format %s.\n",
11140 test_data[i].in, color, test_data[i].right, test_data[i].fmt_string);
11141 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
11142 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
11143 IDirect3DSurface9_Release(surface);
11146 IDirect3DSurface9_Release(target);
11147 refcount = IDirect3DDevice9_Release(device);
11148 ok(!refcount, "Device has %u references left.\n", refcount);
11149 done:
11150 IDirect3D9_Release(d3d);
11151 DestroyWindow(window);
11154 static void yuv_layout_test(void)
11156 HRESULT hr;
11157 IDirect3DSurface9 *surface, *target;
11158 unsigned int fmt, i, x, y;
11159 D3DFORMAT format;
11160 const char *fmt_string;
11161 D3DLOCKED_RECT lr;
11162 IDirect3D9 *d3d;
11163 D3DCOLOR color;
11164 DWORD ref_color;
11165 BYTE *buf, *chroma_buf, *u_buf, *v_buf;
11166 UINT width = 20, height = 16;
11167 IDirect3DDevice9 *device;
11168 ULONG refcount;
11169 D3DCAPS9 caps;
11170 D3DSURFACE_DESC desc;
11171 HWND window;
11173 static const struct
11175 DWORD color1, color2;
11176 DWORD rgb1, rgb2;
11178 test_data[] =
11180 { 0x000000, 0xffffff, 0x00008800, 0x00ff7dff },
11181 { 0xff0000, 0x00ffff, 0x004aff14, 0x00b800ee },
11182 { 0x00ff00, 0xff00ff, 0x000024ee, 0x00ffe114 },
11183 { 0x0000ff, 0xffff00, 0x00b80000, 0x004affff },
11184 { 0xffff00, 0x0000ff, 0x004affff, 0x00b80000 },
11185 { 0xff00ff, 0x00ff00, 0x00ffe114, 0x000024ee },
11186 { 0x00ffff, 0xff0000, 0x00b800ee, 0x004aff14 },
11187 { 0xffffff, 0x000000, 0x00ff7dff, 0x00008800 },
11190 static const struct
11192 D3DFORMAT format;
11193 const char *str;
11195 formats[] =
11197 { D3DFMT_UYVY, "D3DFMT_UYVY", },
11198 { D3DFMT_YUY2, "D3DFMT_YUY2", },
11199 { MAKEFOURCC('Y','V','1','2'), "D3DFMT_YV12", },
11200 { MAKEFOURCC('N','V','1','2'), "D3DFMT_NV12", },
11203 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
11204 0, 0, 640, 480, NULL, NULL, NULL, NULL);
11205 d3d = Direct3DCreate9(D3D_SDK_VERSION);
11206 ok(!!d3d, "Failed to create a D3D object.\n");
11207 if (!(device = create_device(d3d, window, window, TRUE)))
11209 skip("Failed to create a D3D device, skipping tests.\n");
11210 goto done;
11213 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
11214 ok(SUCCEEDED(hr), "GetDeviceCaps failed, hr %#x.\n", hr);
11215 if (caps.TextureCaps & D3DPTEXTURECAPS_POW2
11216 && !(caps.TextureCaps & D3DPTEXTURECAPS_NONPOW2CONDITIONAL))
11218 skip("No NP2 texture support, skipping YUV texture layout test.\n");
11219 IDirect3DDevice9_Release(device);
11220 goto done;
11223 hr = IDirect3DDevice9_GetRenderTarget(device, 0, &target);
11224 ok(hr == D3D_OK, "IDirect3DDevice9_GetRenderTarget failed, hr = %#x.\n", hr);
11225 hr = IDirect3DSurface9_GetDesc(target, &desc);
11226 ok(SUCCEEDED(hr), "Failed to get surface description, hr %#x.\n", hr);
11228 for (fmt = 0; fmt < sizeof(formats) / sizeof(formats[0]); fmt++)
11230 format = formats[fmt].format;
11231 fmt_string = formats[fmt].str;
11233 /* Some (all?) Windows drivers do not support YUV 3D textures, only 2D surfaces in
11234 * StretchRect. Thus use StretchRect to draw the YUV surface onto the screen instead
11235 * of drawPrimitive. */
11236 if (IDirect3D9_CheckDeviceFormat(d3d, 0, D3DDEVTYPE_HAL, D3DFMT_X8R8G8B8, 0,
11237 D3DRTYPE_SURFACE, format) != D3D_OK)
11239 skip("%s is not supported.\n", fmt_string);
11240 continue;
11242 if (FAILED(IDirect3D9_CheckDeviceFormatConversion(d3d, 0,
11243 D3DDEVTYPE_HAL, format, desc.Format)))
11245 skip("Driver cannot blit %s surfaces.\n", fmt_string);
11246 continue;
11249 hr = IDirect3DDevice9_CreateOffscreenPlainSurface(device, width, height, format, D3DPOOL_DEFAULT, &surface, NULL);
11250 ok(hr == D3D_OK, "IDirect3DDevice9_CreateOffscreenPlainSurface failed, hr = %#x.\n", hr);
11252 for (i = 0; i < sizeof(test_data) / sizeof(test_data[0]); i++)
11254 hr = IDirect3DSurface9_LockRect(surface, &lr, NULL, 0);
11255 ok(hr == D3D_OK, "IDirect3DSurface9_LockRect failed, hr = %#x.\n", hr);
11256 buf = lr.pBits;
11257 chroma_buf = buf + lr.Pitch * height;
11258 if (format == MAKEFOURCC('Y','V','1','2'))
11260 v_buf = chroma_buf;
11261 u_buf = chroma_buf + height / 2 * lr.Pitch/2;
11263 /* Draw the top left quarter of the screen with color1, the rest with color2 */
11264 for (y = 0; y < height; y++)
11266 for (x = 0; x < width; x += 2)
11268 DWORD color = (x < width / 2 && y < height / 2) ? test_data[i].color1 : test_data[i].color2;
11269 BYTE Y = (color >> 16) & 0xff;
11270 BYTE U = (color >> 8) & 0xff;
11271 BYTE V = (color >> 0) & 0xff;
11272 if (format == D3DFMT_UYVY)
11274 buf[y * lr.Pitch + 2 * x + 0] = U;
11275 buf[y * lr.Pitch + 2 * x + 1] = Y;
11276 buf[y * lr.Pitch + 2 * x + 2] = V;
11277 buf[y * lr.Pitch + 2 * x + 3] = Y;
11279 else if (format == D3DFMT_YUY2)
11281 buf[y * lr.Pitch + 2 * x + 0] = Y;
11282 buf[y * lr.Pitch + 2 * x + 1] = U;
11283 buf[y * lr.Pitch + 2 * x + 2] = Y;
11284 buf[y * lr.Pitch + 2 * x + 3] = V;
11286 else if (format == MAKEFOURCC('Y','V','1','2'))
11288 buf[y * lr.Pitch + x + 0] = Y;
11289 buf[y * lr.Pitch + x + 1] = Y;
11290 u_buf[(y / 2) * (lr.Pitch / 2) + (x / 2)] = U;
11291 v_buf[(y / 2) * (lr.Pitch / 2) + (x / 2)] = V;
11293 else if (format == MAKEFOURCC('N','V','1','2'))
11295 buf[y * lr.Pitch + x + 0] = Y;
11296 buf[y * lr.Pitch + x + 1] = Y;
11297 chroma_buf[(y / 2) * lr.Pitch + 2 * (x / 2) + 0] = U;
11298 chroma_buf[(y / 2) * lr.Pitch + 2 * (x / 2) + 1] = V;
11302 hr = IDirect3DSurface9_UnlockRect(surface);
11303 ok(hr == D3D_OK, "IDirect3DSurface9_UnlockRect failed, hr = %#x.\n", hr);
11305 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0x00000000, 1.0f, 0);
11306 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with %#x.\n", hr);
11307 hr = IDirect3DDevice9_StretchRect(device, surface, NULL, target, NULL, D3DTEXF_POINT);
11308 ok(hr == D3D_OK, "IDirect3DDevice9_StretchRect failed with %#x.\n", hr);
11310 /* Some Windows drivers (mostly Nvidia, but also some VM drivers) insist on doing linear filtering
11311 * although we asked for point filtering. To prevent running into precision problems, read at points
11312 * with some margin within each quadrant.
11314 * Unfortunately different implementations(Windows-Nvidia and Mac-AMD tested) interpret some colors
11315 * vastly differently, so we need a max diff of 18. */
11316 for (y = 0; y < 4; y++)
11318 for (x = 0; x < 4; x++)
11320 UINT xcoord = (1 + 2 * x) * 640 / 8;
11321 UINT ycoord = (1 + 2 * y) * 480 / 8;
11322 ref_color = (y < 2 && x < 2) ? test_data[i].rgb1 : test_data[i].rgb2;
11323 color = getPixelColor(device, xcoord, ycoord);
11324 ok(color_match(color, ref_color, 18),
11325 "Format %s: Got color %#x for pixel (%d/%d)/(%d/%d), pixel %d %d, expected %#x.\n",
11326 fmt_string, color, x, 4, y, 4, xcoord, ycoord, ref_color);
11329 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
11331 ok(SUCCEEDED(hr), "Present failed with %#x.\n", hr);
11333 IDirect3DSurface9_Release(surface);
11336 IDirect3DSurface9_Release(target);
11337 refcount = IDirect3DDevice9_Release(device);
11338 ok(!refcount, "Device has %u references left.\n", refcount);
11339 done:
11340 IDirect3D9_Release(d3d);
11341 DestroyWindow(window);
11344 static void texop_range_test(void)
11346 IDirect3DTexture9 *texture;
11347 D3DLOCKED_RECT locked_rect;
11348 IDirect3DDevice9 *device;
11349 IDirect3D9 *d3d;
11350 ULONG refcount;
11351 D3DCAPS9 caps;
11352 DWORD color;
11353 HWND window;
11354 HRESULT hr;
11356 static const struct
11358 float x, y, z;
11359 D3DCOLOR diffuse;
11361 quad[] =
11363 {-1.0f, -1.0f, 0.1f, D3DCOLOR_ARGB(0xff, 0xff, 0xff, 0xff)},
11364 {-1.0f, 1.0f, 0.1f, D3DCOLOR_ARGB(0xff, 0xff, 0xff, 0xff)},
11365 { 1.0f, -1.0f, 0.1f, D3DCOLOR_ARGB(0xff, 0xff, 0xff, 0xff)},
11366 { 1.0f, 1.0f, 0.1f, D3DCOLOR_ARGB(0xff, 0xff, 0xff, 0xff)}
11369 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
11370 0, 0, 640, 480, NULL, NULL, NULL, NULL);
11371 d3d = Direct3DCreate9(D3D_SDK_VERSION);
11372 ok(!!d3d, "Failed to create a D3D object.\n");
11373 if (!(device = create_device(d3d, window, window, TRUE)))
11375 skip("Failed to create a D3D device, skipping tests.\n");
11376 goto done;
11379 /* We need ADD and SUBTRACT operations */
11380 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
11381 ok(SUCCEEDED(hr), "GetDeviceCaps failed with 0x%08x\n", hr);
11382 if (!(caps.TextureOpCaps & D3DTEXOPCAPS_ADD))
11384 skip("D3DTOP_ADD is not supported, skipping value range test.\n");
11385 IDirect3DDevice9_Release(device);
11386 goto done;
11388 if (!(caps.TextureOpCaps & D3DTEXOPCAPS_SUBTRACT))
11390 skip("D3DTEXOPCAPS_SUBTRACT is not supported, skipping value range test.\n");
11391 IDirect3DDevice9_Release(device);
11392 goto done;
11395 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
11396 ok(SUCCEEDED(hr), "SetFVF failed with 0x%08x\n", hr);
11397 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
11398 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
11399 /* Stage 1: result = diffuse(=1.0) + diffuse
11400 * stage 2: result = result - tfactor(= 0.5)
11402 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_TEXTUREFACTOR, 0x80808080);
11403 ok(SUCCEEDED(hr), "SetRenderState failed with 0x%08x\n", hr);
11404 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_DIFFUSE);
11405 ok(SUCCEEDED(hr), "SetTextureStageState failed with 0x%08x\n", hr);
11406 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG2, D3DTA_DIFFUSE);
11407 ok(SUCCEEDED(hr), "SetTextureStageState failed with 0x%08x\n", hr);
11408 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_ADD);
11409 ok(SUCCEEDED(hr), "SetTextureStageState failed with 0x%08x\n", hr);
11410 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_COLORARG1, D3DTA_CURRENT);
11411 ok(SUCCEEDED(hr), "SetTextureStageState failed with 0x%08x\n", hr);
11412 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_COLORARG2, D3DTA_TFACTOR);
11413 ok(SUCCEEDED(hr), "SetTextureStageState failed with 0x%08x\n", hr);
11414 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_COLOROP, D3DTOP_SUBTRACT);
11415 ok(SUCCEEDED(hr), "SetTextureStageState failed with 0x%08x\n", hr);
11417 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x00000000, 1.0f, 0);
11418 ok(SUCCEEDED(hr), "Failed to clear device, hr %#x.\n\n", hr);
11419 hr = IDirect3DDevice9_BeginScene(device);
11420 ok(SUCCEEDED(hr), "BeginScene failed with 0x%08x\n", hr);
11421 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
11422 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed with 0x%08x\n", hr);
11423 hr = IDirect3DDevice9_EndScene(device);
11424 ok(SUCCEEDED(hr), "EndScene failed with 0x%08x\n", hr);
11426 color = getPixelColor(device, 320, 240);
11427 ok(color_match(color, 0x00808080, 1), "texop Range > 1.0 returned 0x%08x, expected 0x00808080\n",
11428 color);
11429 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
11430 ok(SUCCEEDED(hr), "Present failed with 0x%08x\n", hr);
11432 hr = IDirect3DDevice9_CreateTexture(device, 1, 1, 1, 0, D3DFMT_A8R8G8B8, D3DPOOL_MANAGED, &texture, NULL);
11433 ok(SUCCEEDED(hr), "IDirect3DDevice9_CreateTexture failed with 0x%08x\n", hr);
11434 hr = IDirect3DTexture9_LockRect(texture, 0, &locked_rect, NULL, 0);
11435 ok(SUCCEEDED(hr), "LockRect failed with 0x%08x\n", hr);
11436 *((DWORD *)locked_rect.pBits) = D3DCOLOR_ARGB(0x00, 0x00, 0x00, 0x00);
11437 hr = IDirect3DTexture9_UnlockRect(texture, 0);
11438 ok(SUCCEEDED(hr), "UnlockRect failed with 0x%08x\n", hr);
11439 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)texture);
11440 ok(SUCCEEDED(hr), "SetTexture failed with 0x%08x\n", hr);
11442 /* Stage 1: result = texture(=0.0) - tfactor(= 0.5)
11443 * stage 2: result = result + diffuse(1.0)
11445 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_TEXTUREFACTOR, 0x80808080);
11446 ok(SUCCEEDED(hr), "SetRenderState failed with 0x%08x\n", hr);
11447 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
11448 ok(SUCCEEDED(hr), "SetTextureStageState failed with 0x%08x\n", hr);
11449 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG2, D3DTA_TFACTOR);
11450 ok(SUCCEEDED(hr), "SetTextureStageState failed with 0x%08x\n", hr);
11451 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_SUBTRACT);
11452 ok(SUCCEEDED(hr), "SetTextureStageState failed with 0x%08x\n", hr);
11453 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_COLORARG1, D3DTA_CURRENT);
11454 ok(SUCCEEDED(hr), "SetTextureStageState failed with 0x%08x\n", hr);
11455 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_COLORARG2, D3DTA_DIFFUSE);
11456 ok(SUCCEEDED(hr), "SetTextureStageState failed with 0x%08x\n", hr);
11457 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_COLOROP, D3DTOP_ADD);
11458 ok(SUCCEEDED(hr), "SetTextureStageState failed with 0x%08x\n", hr);
11460 hr = IDirect3DDevice9_BeginScene(device);
11461 ok(SUCCEEDED(hr), "BeginScene failed with 0x%08x\n", hr);
11462 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
11463 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed with 0x%08x\n", hr);
11464 hr = IDirect3DDevice9_EndScene(device);
11465 ok(SUCCEEDED(hr), "EndScene failed with 0x%08x\n", hr);
11467 color = getPixelColor(device, 320, 240);
11468 ok(color_match(color, 0x00ffffff, 1), "texop Range < 0.0 returned 0x%08x, expected 0x00ffffff\n",
11469 color);
11470 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
11471 ok(SUCCEEDED(hr), "Present failed with 0x%08x\n", hr);
11473 IDirect3DTexture9_Release(texture);
11474 refcount = IDirect3DDevice9_Release(device);
11475 ok(!refcount, "Device has %u references left.\n", refcount);
11476 done:
11477 IDirect3D9_Release(d3d);
11478 DestroyWindow(window);
11481 static void alphareplicate_test(void)
11483 IDirect3DDevice9 *device;
11484 IDirect3D9 *d3d;
11485 ULONG refcount;
11486 DWORD color;
11487 HWND window;
11488 HRESULT hr;
11490 static const struct
11492 struct vec3 position;
11493 DWORD diffuse;
11495 quad[] =
11497 {{-1.0f, -1.0f, 0.1f}, 0x80ff00ff},
11498 {{-1.0f, 1.0f, 0.1f}, 0x80ff00ff},
11499 {{ 1.0f, -1.0f, 0.1f}, 0x80ff00ff},
11500 {{ 1.0f, 1.0f, 0.1f}, 0x80ff00ff},
11503 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
11504 0, 0, 640, 480, NULL, NULL, NULL, NULL);
11505 d3d = Direct3DCreate9(D3D_SDK_VERSION);
11506 ok(!!d3d, "Failed to create a D3D object.\n");
11507 if (!(device = create_device(d3d, window, window, TRUE)))
11509 skip("Failed to create a D3D device, skipping tests.\n");
11510 goto done;
11513 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x00000000, 1.0f, 0);
11514 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with 0x%08x\n", hr);
11516 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
11517 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed with 0x%08x\n", hr);
11519 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
11520 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed with 0x%08x\n", hr);
11521 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_DIFFUSE | D3DTA_ALPHAREPLICATE);
11522 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed with 0x%08x\n", hr);
11524 hr = IDirect3DDevice9_BeginScene(device);
11525 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
11526 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
11527 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
11528 hr = IDirect3DDevice9_EndScene(device);
11529 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
11531 color = getPixelColor(device, 320, 240);
11532 ok(color_match(color, 0x00808080, 1), "alphareplicate test 0x%08x, expected 0x00808080\n",
11533 color);
11534 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
11535 ok(SUCCEEDED(hr), "Present failed with 0x%08x\n", hr);
11537 refcount = IDirect3DDevice9_Release(device);
11538 ok(!refcount, "Device has %u references left.\n", refcount);
11539 done:
11540 IDirect3D9_Release(d3d);
11541 DestroyWindow(window);
11544 static void dp3_alpha_test(void)
11546 IDirect3DDevice9 *device;
11547 IDirect3D9 *d3d;
11548 ULONG refcount;
11549 D3DCAPS9 caps;
11550 DWORD color;
11551 HWND window;
11552 HRESULT hr;
11554 static const struct
11556 struct vec3 position;
11557 DWORD diffuse;
11559 quad[] =
11561 {{-1.0f, -1.0f, 0.1f}, 0x408080c0},
11562 {{-1.0f, 1.0f, 0.1f}, 0x408080c0},
11563 {{ 1.0f, -1.0f, 0.1f}, 0x408080c0},
11564 {{ 1.0f, 1.0f, 0.1f}, 0x408080c0},
11567 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
11568 0, 0, 640, 480, NULL, NULL, NULL, NULL);
11569 d3d = Direct3DCreate9(D3D_SDK_VERSION);
11570 ok(!!d3d, "Failed to create a D3D object.\n");
11571 if (!(device = create_device(d3d, window, window, TRUE)))
11573 skip("Failed to create a D3D device, skipping tests.\n");
11574 goto done;
11577 memset(&caps, 0, sizeof(caps));
11578 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
11579 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
11580 if (!(caps.TextureOpCaps & D3DTEXOPCAPS_DOTPRODUCT3))
11582 skip("D3DTOP_DOTPRODUCT3 not supported\n");
11583 IDirect3DDevice9_Release(device);
11584 goto done;
11587 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x00000000, 1.0f, 0);
11588 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with 0x%08x\n", hr);
11590 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
11591 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed with 0x%08x\n", hr);
11593 /* dp3_x4 r0, diffuse_bias, tfactor_bias
11594 * mov r0.a, diffuse.a
11595 * mov r0, r0.a
11597 * It turns out that the 2nd line is ignored, and the dp3 result written into r0.a instead
11598 * thus with input vec4(0.5, 0.5, 0.75, 0.25) and vec4(1.0, 1.0, 1.0, 1.0) the result is
11599 * (0.0 * 0.5 + 0.0 * 0.5 + 0.25 * 0.5) * 4 = 0.125 * 4 = 0.5, with a bunch of inprecision.
11601 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_DOTPRODUCT3);
11602 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed with 0x%08x\n", hr);
11603 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_DIFFUSE);
11604 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed with 0x%08x\n", hr);
11605 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG2, D3DTA_TFACTOR);
11606 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed with 0x%08x\n", hr);
11607 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_ALPHAOP, D3DTOP_SELECTARG1);
11608 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed with 0x%08x\n", hr);
11609 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_ALPHAARG1, D3DTA_DIFFUSE);
11610 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed with 0x%08x\n", hr);
11611 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
11612 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed with 0x%08x\n", hr);
11613 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_COLORARG1, D3DTA_CURRENT | D3DTA_ALPHAREPLICATE);
11614 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed with 0x%08x\n", hr);
11615 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_ALPHAOP, D3DTOP_DISABLE);
11616 ok(hr == D3D_OK, "IDirect3DDevice9_SetTextureStageState failed with 0x%08x\n", hr);
11617 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_TEXTUREFACTOR, 0xffffffff);
11618 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetRenderState failed with 0x%08x\n", hr);
11619 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
11620 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
11622 hr = IDirect3DDevice9_BeginScene(device);
11623 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
11624 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
11625 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
11626 hr = IDirect3DDevice9_EndScene(device);
11627 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
11629 color = getPixelColor(device, 320, 240);
11630 ok(color_match(color, 0x00808080, 4), "dp3 alpha test 0x%08x, expected 0x00808080\n",
11631 color);
11632 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
11633 ok(SUCCEEDED(hr), "IDirect3DDevice9_Present failed with 0x%08x\n", hr);
11635 refcount = IDirect3DDevice9_Release(device);
11636 ok(!refcount, "Device has %u references left.\n", refcount);
11637 done:
11638 IDirect3D9_Release(d3d);
11639 DestroyWindow(window);
11642 static void zwriteenable_test(void)
11644 IDirect3DDevice9 *device;
11645 IDirect3D9 *d3d;
11646 D3DCOLOR color;
11647 ULONG refcount;
11648 HWND window;
11649 HRESULT hr;
11651 static const struct
11653 struct vec3 position;
11654 DWORD diffuse;
11656 quad1[] =
11658 {{-1.0f, -1.0f, 0.1f}, 0x00ff0000},
11659 {{-1.0f, 1.0f, 0.1f}, 0x00ff0000},
11660 {{ 1.0f, -1.0f, 0.1f}, 0x00ff0000},
11661 {{ 1.0f, 1.0f, 0.1f}, 0x00ff0000},
11663 quad2[] =
11665 {{-1.0f, -1.0f, 0.9f}, 0x0000ff00},
11666 {{-1.0f, 1.0f, 0.9f}, 0x0000ff00},
11667 {{ 1.0f, -1.0f, 0.9f}, 0x0000ff00},
11668 {{ 1.0f, 1.0f, 0.9f}, 0x0000ff00},
11671 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
11672 0, 0, 640, 480, NULL, NULL, NULL, NULL);
11673 d3d = Direct3DCreate9(D3D_SDK_VERSION);
11674 ok(!!d3d, "Failed to create a D3D object.\n");
11675 if (!(device = create_device(d3d, window, window, TRUE)))
11677 skip("Failed to create a D3D device, skipping tests.\n");
11678 goto done;
11681 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x000000ff, 1.0f, 0);
11682 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with 0x%08x\n", hr);
11684 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
11685 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed with 0x%08x\n", hr);
11686 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, D3DZB_FALSE);
11687 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState failed with 0x%08x\n", hr);
11688 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, TRUE);
11689 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState failed with 0x%08x\n", hr);
11690 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZFUNC, D3DCMP_LESSEQUAL);
11691 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState failed with 0x%08x\n", hr);
11692 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
11693 ok(SUCCEEDED(hr), "Failed to disable lighting, hr %#x.\n", hr);
11695 hr = IDirect3DDevice9_BeginScene(device);
11696 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
11697 /* The Z buffer is filled with 1.0. Draw a red quad with z = 0.1,
11698 * zenable = D3DZB_FALSE, zwriteenable = TRUE. The red color is written
11699 * because the z test is disabled. The question is whether the z = 0.1
11700 * values are written into the Z buffer. After the draw, set
11701 * zenable = TRUE and draw a green quad at z = 0.9. If the values are
11702 * written, the z test will fail(0.9 > 0.1) and the red color remains. If
11703 * the values are not written, the z test succeeds(0.9 < 1.0) and the
11704 * green color is written. It turns out that the screen is green, so
11705 * zenable = D3DZB_FALSE and zwriteenable = TRUE does NOT write to the z
11706 * buffer. */
11707 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, sizeof(*quad1));
11708 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
11709 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, D3DZB_TRUE);
11710 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
11711 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, sizeof(*quad2));
11712 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
11713 hr = IDirect3DDevice9_EndScene(device);
11714 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
11716 color = getPixelColor(device, 320, 240);
11717 ok(color_match(color, 0x0000ff00, 1), "zwriteenable test returned 0x%08x, expected 0x0000ff00\n",
11718 color);
11719 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
11720 ok(SUCCEEDED(hr), "IDirect3DDevice9_Present failed with 0x%08x\n", hr);
11722 refcount = IDirect3DDevice9_Release(device);
11723 ok(!refcount, "Device has %u references left.\n", refcount);
11724 done:
11725 IDirect3D9_Release(d3d);
11726 DestroyWindow(window);
11729 static void alphatest_test(void)
11731 #define ALPHATEST_PASSED 0x0000ff00
11732 #define ALPHATEST_FAILED 0x00ff0000
11733 IDirect3DDevice9 *device;
11734 unsigned int i, j;
11735 IDirect3D9 *d3d;
11736 D3DCOLOR color;
11737 ULONG refcount;
11738 D3DCAPS9 caps;
11739 HWND window;
11740 HRESULT hr;
11742 static const struct
11744 D3DCMPFUNC func;
11745 D3DCOLOR color_less;
11746 D3DCOLOR color_equal;
11747 D3DCOLOR color_greater;
11749 testdata[] =
11751 {D3DCMP_NEVER, ALPHATEST_FAILED, ALPHATEST_FAILED, ALPHATEST_FAILED},
11752 {D3DCMP_LESS, ALPHATEST_PASSED, ALPHATEST_FAILED, ALPHATEST_FAILED},
11753 {D3DCMP_EQUAL, ALPHATEST_FAILED, ALPHATEST_PASSED, ALPHATEST_FAILED},
11754 {D3DCMP_LESSEQUAL, ALPHATEST_PASSED, ALPHATEST_PASSED, ALPHATEST_FAILED},
11755 {D3DCMP_GREATER, ALPHATEST_FAILED, ALPHATEST_FAILED, ALPHATEST_PASSED},
11756 {D3DCMP_NOTEQUAL, ALPHATEST_PASSED, ALPHATEST_FAILED, ALPHATEST_PASSED},
11757 {D3DCMP_GREATEREQUAL, ALPHATEST_FAILED, ALPHATEST_PASSED, ALPHATEST_PASSED},
11758 {D3DCMP_ALWAYS, ALPHATEST_PASSED, ALPHATEST_PASSED, ALPHATEST_PASSED},
11760 static const struct
11762 struct vec3 position;
11763 DWORD diffuse;
11765 quad[] =
11767 {{-1.0f, -1.0f, 0.1f}, ALPHATEST_PASSED | 0x80000000},
11768 {{-1.0f, 1.0f, 0.1f}, ALPHATEST_PASSED | 0x80000000},
11769 {{ 1.0f, -1.0f, 0.1f}, ALPHATEST_PASSED | 0x80000000},
11770 {{ 1.0f, 1.0f, 0.1f}, ALPHATEST_PASSED | 0x80000000},
11773 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
11774 0, 0, 640, 480, NULL, NULL, NULL, NULL);
11775 d3d = Direct3DCreate9(D3D_SDK_VERSION);
11776 ok(!!d3d, "Failed to create a D3D object.\n");
11777 if (!(device = create_device(d3d, window, window, TRUE)))
11779 skip("Failed to create a D3D device, skipping tests.\n");
11780 goto done;
11783 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff0000ff, 1.0f, 0);
11784 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
11786 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
11787 ok(SUCCEEDED(hr), "Failed to disable lighting, hr %#x.\n", hr);
11788 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ALPHATESTENABLE, TRUE);
11789 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState failed with 0x%08x\n", hr);
11790 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
11791 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed with 0x%08x\n", hr);
11793 for (j = 0; j < 2; ++j)
11795 if (j == 1)
11797 /* Try a pixel shader instead of fixed function. The wined3d code
11798 * may emulate the alpha test either for performance reasons
11799 * (floating point RTs) or to work around driver bugs (GeForce
11800 * 7x00 cards on MacOS). There may be a different codepath for ffp
11801 * and shader in this case, and the test should cover both. */
11802 IDirect3DPixelShader9 *ps;
11803 static const DWORD shader_code[] =
11805 0xffff0101, /* ps_1_1 */
11806 0x00000001, 0x800f0000, 0x90e40000, /* mov r0, v0 */
11807 0x0000ffff /* end */
11809 memset(&caps, 0, sizeof(caps));
11810 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
11811 ok(hr == D3D_OK, "IDirect3DDevice9_GetDeviceCaps failed with 0x%08x\n", hr);
11812 if(caps.PixelShaderVersion < D3DPS_VERSION(1, 1)) {
11813 break;
11816 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code, &ps);
11817 ok(hr == D3D_OK, "IDirect3DDevice9_CreatePixelShader failed with 0x%08x\n", hr);
11818 hr = IDirect3DDevice9_SetPixelShader(device, ps);
11819 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShader failed with 0x%08x\n", hr);
11820 IDirect3DPixelShader9_Release(ps);
11823 for(i = 0; i < (sizeof(testdata)/sizeof(testdata[0])); i++) {
11824 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ALPHAFUNC, testdata[i].func);
11825 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState failed with 0x%08x\n", hr);
11827 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, ALPHATEST_FAILED, 0.0, 0);
11828 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with 0x%08x\n", hr);
11829 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ALPHAREF, 0x90);
11830 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState failed with 0x%08x\n", hr);
11831 hr = IDirect3DDevice9_BeginScene(device);
11832 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
11833 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
11834 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
11835 hr = IDirect3DDevice9_EndScene(device);
11836 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
11837 color = getPixelColor(device, 320, 240);
11838 ok(color_match(color, testdata[i].color_less, 1), "Alphatest failed. Got color 0x%08x, expected 0x%08x. alpha < ref, func %u\n",
11839 color, testdata[i].color_less, testdata[i].func);
11840 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
11841 ok(SUCCEEDED(hr), "IDirect3DDevice9_Present failed with 0x%08x\n", hr);
11843 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, ALPHATEST_FAILED, 0.0, 0);
11844 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with 0x%08x\n", hr);
11845 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ALPHAREF, 0x80);
11846 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState failed with 0x%08x\n", hr);
11847 hr = IDirect3DDevice9_BeginScene(device);
11848 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
11849 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
11850 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
11851 hr = IDirect3DDevice9_EndScene(device);
11852 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
11853 color = getPixelColor(device, 320, 240);
11854 ok(color_match(color, testdata[i].color_equal, 1), "Alphatest failed. Got color 0x%08x, expected 0x%08x. alpha == ref, func %u\n",
11855 color, testdata[i].color_equal, testdata[i].func);
11856 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
11857 ok(SUCCEEDED(hr), "IDirect3DDevice9_Present failed with 0x%08x\n", hr);
11859 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, ALPHATEST_FAILED, 0.0, 0);
11860 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with 0x%08x\n", hr);
11861 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ALPHAREF, 0x70);
11862 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderState failed with 0x%08x\n", hr);
11863 hr = IDirect3DDevice9_BeginScene(device);
11864 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
11865 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
11866 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
11867 hr = IDirect3DDevice9_EndScene(device);
11868 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
11869 color = getPixelColor(device, 320, 240);
11870 ok(color_match(color, testdata[i].color_greater, 1), "Alphatest failed. Got color 0x%08x, expected 0x%08x. alpha > ref, func %u\n",
11871 color, testdata[i].color_greater, testdata[i].func);
11872 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
11873 ok(SUCCEEDED(hr), "IDirect3DDevice9_Present failed with 0x%08x\n", hr);
11877 refcount = IDirect3DDevice9_Release(device);
11878 ok(!refcount, "Device has %u references left.\n", refcount);
11879 done:
11880 IDirect3D9_Release(d3d);
11881 DestroyWindow(window);
11884 static void sincos_test(void)
11886 IDirect3DVertexShader9 *sin_shader, *cos_shader;
11887 IDirect3DDevice9 *device;
11888 struct vec3 data[1280];
11889 IDirect3D9 *d3d;
11890 unsigned int i;
11891 ULONG refcount;
11892 D3DCAPS9 caps;
11893 HWND window;
11894 HRESULT hr;
11896 static const DWORD sin_shader_code[] =
11898 0xfffe0200, /* vs_2_0 */
11899 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
11900 0x05000051, 0xa00f0002, 0x40490fdb, 0x3f800000, 0x00000000, 0x3f59999a, /* def c2, 3.14159, 1, 0, 0.85 */
11901 0x03000005, 0x80010001, 0x90000000, 0xa0000002, /* mul r1.x, v0.x, c2.x */
11902 0x04000025, 0x80020000, 0x80000001, 0xa0e40000, 0xa0e40001, /* sincos r0.y, r1.x, c0, c1 */
11903 0x02000001, 0xc00d0000, 0x90e40000, /* mov oPos.xzw, v0 */
11904 0x03000005, 0xc0020000, 0x80550000, 0xa0ff0002, /* mul oPos.y, r0.y, c2.w */
11905 0x02000001, 0xd00f0000, 0xa0a60002, /* mov oD0, c2.zyzz */
11906 0x0000ffff /* end */
11908 static const DWORD cos_shader_code[] =
11910 0xfffe0200, /* vs_2_0 */
11911 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
11912 0x05000051, 0xa00f0002, 0x40490fdb, 0x3f800000, 0x00000000, 0x3f59999a, /* def c2, 3.14159, 1, 0, 0.85 */
11913 0x03000005, 0x80010001, 0x90000000, 0xa0000002, /* mul r1.x, v0.x, c2.x */
11914 0x04000025, 0x80010000, 0x80000001, 0xa0e40000, 0xa0e40001, /* sincos r0.x, r1.x, c0, c1 */
11915 0x02000001, 0xc00d0000, 0x90e40000, /* mov oPos.xzw, v0 */
11916 0x03000005, 0xc0020000, 0x80000000, 0xa0ff0002, /* mul oPos.y, r0.x, c2.w */
11917 0x02000001, 0xd00f0000, 0xa0a90002, /* mov oD0, c2.yzzz */
11918 0x0000ffff /* end */
11920 static const float sincosc1[4] = {D3DSINCOSCONST1};
11921 static const float sincosc2[4] = {D3DSINCOSCONST2};
11923 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
11924 0, 0, 640, 480, NULL, NULL, NULL, NULL);
11925 d3d = Direct3DCreate9(D3D_SDK_VERSION);
11926 ok(!!d3d, "Failed to create a D3D object.\n");
11927 if (!(device = create_device(d3d, window, window, TRUE)))
11929 skip("Failed to create a D3D device, skipping tests.\n");
11930 goto done;
11933 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
11934 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
11935 if (caps.VertexShaderVersion < D3DVS_VERSION(2, 0))
11937 skip("No vs_2_0 support, skipping tests.\n");
11938 IDirect3DDevice9_Release(device);
11939 goto done;
11942 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x00000000, 1.0f, 0);
11943 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with 0x%08x\n", hr);
11945 hr = IDirect3DDevice9_CreateVertexShader(device, sin_shader_code, &sin_shader);
11946 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with 0x%08x\n", hr);
11947 hr = IDirect3DDevice9_CreateVertexShader(device, cos_shader_code, &cos_shader);
11948 ok(hr == D3D_OK, "IDirect3DDevice9_Clear failed with 0x%08x\n", hr);
11949 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ);
11950 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed with 0x%08x\n", hr);
11951 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 0, sincosc1, 1);
11952 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexShaderConstantF failed with 0x%08x\n", hr);
11953 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 1, sincosc2, 1);
11954 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexShaderConstantF failed with 0x%08x\n", hr);
11956 /* Generate a point from -1 to 1 every 0.5 pixels */
11957 for(i = 0; i < 1280; i++) {
11958 data[i].x = (-640.0 + i) / 640.0;
11959 data[i].y = 0.0;
11960 data[i].z = 0.1;
11963 hr = IDirect3DDevice9_BeginScene(device);
11964 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
11966 hr = IDirect3DDevice9_SetVertexShader(device, sin_shader);
11967 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
11968 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_POINTLIST, 1280, data, sizeof(*data));
11969 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
11971 hr = IDirect3DDevice9_SetVertexShader(device, cos_shader);
11972 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
11973 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_POINTLIST, 1280, data, sizeof(*data));
11974 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
11976 hr = IDirect3DDevice9_EndScene(device);
11977 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
11979 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
11980 ok(SUCCEEDED(hr), "IDirect3DDevice9_Present returned %#x.\n", hr);
11981 /* TODO: Find a way to properly validate the lines. Precicion issues make this a kinda nasty task */
11983 IDirect3DVertexShader9_Release(sin_shader);
11984 IDirect3DVertexShader9_Release(cos_shader);
11985 refcount = IDirect3DDevice9_Release(device);
11986 ok(!refcount, "Device has %u references left.\n", refcount);
11987 done:
11988 IDirect3D9_Release(d3d);
11989 DestroyWindow(window);
11992 static void loop_index_test(void)
11994 IDirect3DVertexShader9 *shader;
11995 IDirect3DDevice9 *device;
11996 IDirect3D9 *d3d;
11997 float values[4];
11998 ULONG refcount;
11999 D3DCAPS9 caps;
12000 DWORD color;
12001 HWND window;
12002 HRESULT hr;
12004 static const DWORD shader_code[] =
12006 0xfffe0200, /* vs_2_0 */
12007 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
12008 0x02000001, 0x800f0000, 0xa0e40000, /* mov r0, c0 */
12009 0x0200001b, 0xf0e40800, 0xf0e40000, /* loop aL, i0 */
12010 0x04000002, 0x800f0000, 0x80e40000, 0xa0e42001, 0xf0e40800, /* add r0, r0, c[aL + 1] */
12011 0x0000001d, /* endloop */
12012 0x02000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
12013 0x02000001, 0xd00f0000, 0x80e40000, /* mov oD0, r0 */
12014 0x0000ffff /* END */
12016 static const float quad[] =
12018 -1.0f, -1.0f, 0.1f,
12019 -1.0f, 1.0f, 0.1f,
12020 1.0f, -1.0f, 0.1f,
12021 1.0f, 1.0f, 0.1f,
12023 static const float zero[4] = {0.0f, 0.0f, 0.0f, 0.0f};
12024 static const float one[4] = {1.0f, 1.0f, 1.0f, 1.0f};
12025 static const int i0[4] = {2, 10, -3, 0};
12027 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
12028 0, 0, 640, 480, NULL, NULL, NULL, NULL);
12029 d3d = Direct3DCreate9(D3D_SDK_VERSION);
12030 ok(!!d3d, "Failed to create a D3D object.\n");
12031 if (!(device = create_device(d3d, window, window, TRUE)))
12033 skip("Failed to create a D3D device, skipping tests.\n");
12034 goto done;
12037 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
12038 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
12039 if (caps.VertexShaderVersion < D3DVS_VERSION(2, 0))
12041 skip("No vs_2_0 support, skipping tests.\n");
12042 IDirect3DDevice9_Release(device);
12043 goto done;
12046 hr = IDirect3DDevice9_CreateVertexShader(device, shader_code, &shader);
12047 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader failed with %08x\n", hr);
12048 hr = IDirect3DDevice9_SetVertexShader(device, shader);
12049 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexShader failed with %08x\n", hr);
12050 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ);
12051 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed with %08x\n", hr);
12052 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x00ff0000, 1.0f, 0);
12053 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
12055 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 0, zero, 1);
12056 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetVertexShaderConstantF returned %#x.\n", hr);
12057 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 1, one, 1);
12058 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetVertexShaderConstantF returned %#x.\n", hr);
12059 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 2, one, 1);
12060 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetVertexShaderConstantF returned %#x.\n", hr);
12061 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 3, one, 1);
12062 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetVertexShaderConstantF returned %#x.\n", hr);
12063 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 4, one, 1);
12064 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetVertexShaderConstantF returned %#x.\n", hr);
12065 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 5, one, 1);
12066 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetVertexShaderConstantF returned %#x.\n", hr);
12067 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 6, one, 1);
12068 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetVertexShaderConstantF returned %#x.\n", hr);
12069 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 7, one, 1);
12070 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetVertexShaderConstantF returned %#x.\n", hr);
12071 values[0] = 1.0;
12072 values[1] = 1.0;
12073 values[2] = 0.0;
12074 values[3] = 0.0;
12075 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 8, values, 1);
12076 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetVertexShaderConstantF returned %#x.\n", hr);
12077 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 9, one, 1);
12078 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetVertexShaderConstantF returned %#x.\n", hr);
12079 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 10, one, 1);
12080 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetVertexShaderConstantF returned %#x.\n", hr);
12081 values[0] = -1.0;
12082 values[1] = 0.0;
12083 values[2] = 0.0;
12084 values[3] = 0.0;
12085 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 11, values, 1);
12086 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetVertexShaderConstantF returned %#x.\n", hr);
12087 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 12, one, 1);
12088 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetVertexShaderConstantF returned %#x.\n", hr);
12089 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 13, one, 1);
12090 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetVertexShaderConstantF returned %#x.\n", hr);
12091 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 14, one, 1);
12092 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetVertexShaderConstantF returned %#x.\n", hr);
12093 hr = IDirect3DDevice9_SetVertexShaderConstantF(device, 15, one, 1);
12094 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetVertexShaderConstantF returned %#x.\n", hr);
12096 hr = IDirect3DDevice9_SetVertexShaderConstantI(device, 0, i0, 1);
12097 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetVertexShaderConstantI returned %#x.\n", hr);
12099 hr = IDirect3DDevice9_BeginScene(device);
12100 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, 3 * sizeof(float));
12101 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
12102 hr = IDirect3DDevice9_EndScene(device);
12103 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
12104 color = getPixelColor(device, 320, 240);
12105 ok(color_match(color, 0x0000ff00, 1),
12106 "aL indexing test returned color 0x%08x, expected 0x0000ff00\n", color);
12107 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
12108 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
12110 IDirect3DVertexShader9_Release(shader);
12111 refcount = IDirect3DDevice9_Release(device);
12112 ok(!refcount, "Device has %u references left.\n", refcount);
12113 done:
12114 IDirect3D9_Release(d3d);
12115 DestroyWindow(window);
12118 static void sgn_test(void)
12120 IDirect3DVertexShader9 *shader;
12121 IDirect3DDevice9 *device;
12122 IDirect3D9 *d3d;
12123 ULONG refcount;
12124 D3DCAPS9 caps;
12125 DWORD color;
12126 HWND window;
12127 HRESULT hr;
12129 static const DWORD shader_code[] =
12131 0xfffe0200, /* vs_2_0 */
12132 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position o0 */
12133 0x05000051, 0xa00f0000, 0xbf000000, 0x00000000, 0x3f000000, 0x41400000, /* def c0, -0.5, 0.0, 0.5, 12.0 */
12134 0x05000051, 0xa00f0001, 0x3fc00000, 0x00000000, 0x00000000, 0x00000000, /* def c1, 1.5, 0.0, 0.0, 0.0 */
12135 0x02000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
12136 0x04000022, 0x800f0000, 0xa0e40000, 0x80e40001, 0x80e40002, /* sgn r0, c0, r1, r2 */
12137 0x03000002, 0xd00f0000, 0x80e40000, 0xa0e40001, /* add oD0, r0, c1 */
12138 0x0000ffff /* end */
12140 static const float quad[] =
12142 -1.0f, -1.0f, 0.1f,
12143 -1.0f, 1.0f, 0.1f,
12144 1.0f, -1.0f, 0.1f,
12145 1.0f, 1.0f, 0.1f,
12148 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
12149 0, 0, 640, 480, NULL, NULL, NULL, NULL);
12150 d3d = Direct3DCreate9(D3D_SDK_VERSION);
12151 ok(!!d3d, "Failed to create a D3D object.\n");
12152 if (!(device = create_device(d3d, window, window, TRUE)))
12154 skip("Failed to create a D3D device, skipping tests.\n");
12155 goto done;
12158 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
12159 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
12160 if (caps.VertexShaderVersion < D3DVS_VERSION(2, 0))
12162 skip("No vs_2_0 support, skipping tests.\n");
12163 IDirect3DDevice9_Release(device);
12164 goto done;
12167 hr = IDirect3DDevice9_CreateVertexShader(device, shader_code, &shader);
12168 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader failed with %08x\n", hr);
12169 hr = IDirect3DDevice9_SetVertexShader(device, shader);
12170 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexShader failed with %08x\n", hr);
12171 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ);
12172 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF failed with %08x\n", hr);
12173 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x00ff0000, 1.0f, 0);
12174 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
12176 hr = IDirect3DDevice9_BeginScene(device);
12177 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
12178 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, 3 * sizeof(float));
12179 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
12180 hr = IDirect3DDevice9_EndScene(device);
12181 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
12182 color = getPixelColor(device, 320, 240);
12183 ok(color_match(color, 0x008000ff, 1),
12184 "sgn test returned color 0x%08x, expected 0x008000ff\n", color);
12185 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
12186 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
12188 IDirect3DVertexShader9_Release(shader);
12189 refcount = IDirect3DDevice9_Release(device);
12190 ok(!refcount, "Device has %u references left.\n", refcount);
12191 done:
12192 IDirect3D9_Release(d3d);
12193 DestroyWindow(window);
12196 static void viewport_test(void)
12198 IDirect3DDevice9 *device;
12199 BOOL draw_failed = TRUE;
12200 D3DVIEWPORT9 vp;
12201 IDirect3D9 *d3d;
12202 ULONG refcount;
12203 DWORD color;
12204 HWND window;
12205 HRESULT hr;
12207 static const float quad[] =
12209 -0.5f, -0.5f, 0.1f,
12210 -0.5f, 0.5f, 0.1f,
12211 0.5f, -0.5f, 0.1f,
12212 0.5f, 0.5f, 0.1f,
12215 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
12216 0, 0, 640, 480, NULL, NULL, NULL, NULL);
12217 d3d = Direct3DCreate9(D3D_SDK_VERSION);
12218 ok(!!d3d, "Failed to create a D3D object.\n");
12219 if (!(device = create_device(d3d, window, window, TRUE)))
12221 skip("Failed to create a D3D device, skipping tests.\n");
12222 goto done;
12225 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x00ff0000, 1.0f, 0);
12226 ok(hr == D3D_OK, "IDirect3DDevice9_Clear returned %08x\n", hr);
12228 /* Test a viewport with Width and Height bigger than the surface dimensions
12230 * TODO: Test Width < surface.width, but X + Width > surface.width
12231 * TODO: Test Width < surface.width, what happens with the height?
12233 * The expected behavior is that the viewport behaves like the "default"
12234 * viewport with X = Y = 0, Width = surface_width, Height = surface_height,
12235 * MinZ = 0.0, MaxZ = 1.0.
12237 * Starting with Windows 7 the behavior among driver versions is not
12238 * consistent. The SetViewport call is accepted on all drivers. Some
12239 * drivers(older nvidia ones) refuse to draw and return an error. Newer
12240 * nvidia drivers draw, but use the actual values in the viewport and only
12241 * display the upper left part on the surface.
12243 memset(&vp, 0, sizeof(vp));
12244 vp.X = 0;
12245 vp.Y = 0;
12246 vp.Width = 10000;
12247 vp.Height = 10000;
12248 vp.MinZ = 0.0;
12249 vp.MaxZ = 0.0;
12250 hr = IDirect3DDevice9_SetViewport(device, &vp);
12251 ok(hr == D3D_OK, "IDirect3DDevice9_SetViewport failed with %08x\n", hr);
12253 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
12254 ok(SUCCEEDED(hr), "Failed to disable lighting, hr %#x.\n", hr);
12256 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ);
12257 ok(hr == D3D_OK, "IDirect3DDevice9_SetFVF returned %08x\n", hr);
12258 hr = IDirect3DDevice9_BeginScene(device);
12259 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
12260 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, 3 * sizeof(float));
12261 ok(hr == D3D_OK || broken(hr == D3DERR_INVALIDCALL), "Got unexpected hr %#x.\n", hr);
12262 draw_failed = FAILED(hr);
12263 hr = IDirect3DDevice9_EndScene(device);
12264 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
12266 if(!draw_failed)
12268 color = getPixelColor(device, 158, 118);
12269 ok(color == 0x00ff0000, "viewport test: (158,118) has color %08x\n", color);
12270 color = getPixelColor(device, 162, 118);
12271 ok(color == 0x00ff0000, "viewport test: (162,118) has color %08x\n", color);
12272 color = getPixelColor(device, 158, 122);
12273 ok(color == 0x00ff0000, "viewport test: (158,122) has color %08x\n", color);
12274 color = getPixelColor(device, 162, 122);
12275 ok(color == 0x00ffffff || broken(color == 0x00ff0000), "viewport test: (162,122) has color %08x\n", color);
12277 color = getPixelColor(device, 478, 358);
12278 ok(color == 0x00ffffff || broken(color == 0x00ff0000), "viewport test: (478,358 has color %08x\n", color);
12279 color = getPixelColor(device, 482, 358);
12280 ok(color == 0x00ff0000, "viewport test: (482,358) has color %08x\n", color);
12281 color = getPixelColor(device, 478, 362);
12282 ok(color == 0x00ff0000, "viewport test: (478,362) has color %08x\n", color);
12283 color = getPixelColor(device, 482, 362);
12284 ok(color == 0x00ff0000, "viewport test: (482,362) has color %08x\n", color);
12287 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
12288 ok(hr == D3D_OK, "IDirect3DDevice9_Present failed with %08x\n", hr);
12290 refcount = IDirect3DDevice9_Release(device);
12291 ok(!refcount, "Device has %u references left.\n", refcount);
12292 done:
12293 IDirect3D9_Release(d3d);
12294 DestroyWindow(window);
12297 /* This test tests depth clamping / clipping behaviour:
12298 * - With software vertex processing, depth values are clamped to the
12299 * minimum / maximum z value when D3DRS_CLIPPING is disabled, and clipped
12300 * when D3DRS_CLIPPING is enabled. Pretransformed vertices behave the
12301 * same as regular vertices here.
12302 * - With hardware vertex processing, D3DRS_CLIPPING seems to be ignored.
12303 * Normal vertices are always clipped. Pretransformed vertices are
12304 * clipped when D3DPMISCCAPS_CLIPTLVERTS is set, clamped when it isn't.
12305 * - The viewport's MinZ/MaxZ is irrelevant for this.
12307 static void depth_clamp_test(void)
12309 IDirect3DDevice9 *device;
12310 D3DVIEWPORT9 vp;
12311 IDirect3D9 *d3d;
12312 D3DCOLOR color;
12313 ULONG refcount;
12314 D3DCAPS9 caps;
12315 HWND window;
12316 HRESULT hr;
12318 static const struct
12320 struct vec4 position;
12321 DWORD diffuse;
12323 quad1[] =
12325 {{ 0.0f, 0.0f, 5.0f, 1.0f}, 0xff002b7f},
12326 {{640.0f, 0.0f, 5.0f, 1.0f}, 0xff002b7f},
12327 {{ 0.0f, 480.0f, 5.0f, 1.0f}, 0xff002b7f},
12328 {{640.0f, 480.0f, 5.0f, 1.0f}, 0xff002b7f},
12330 quad2[] =
12332 {{ 0.0f, 300.0f, 10.0f, 1.0f}, 0xfff9e814},
12333 {{640.0f, 300.0f, 10.0f, 1.0f}, 0xfff9e814},
12334 {{ 0.0f, 360.0f, 10.0f, 1.0f}, 0xfff9e814},
12335 {{640.0f, 360.0f, 10.0f, 1.0f}, 0xfff9e814},
12337 quad3[] =
12339 {{112.0f, 108.0f, 5.0f, 1.0f}, 0xffffffff},
12340 {{208.0f, 108.0f, 5.0f, 1.0f}, 0xffffffff},
12341 {{112.0f, 204.0f, 5.0f, 1.0f}, 0xffffffff},
12342 {{208.0f, 204.0f, 5.0f, 1.0f}, 0xffffffff},
12344 quad4[] =
12346 {{ 42.0f, 41.0f, 10.0f, 1.0f}, 0xffffffff},
12347 {{112.0f, 41.0f, 10.0f, 1.0f}, 0xffffffff},
12348 {{ 42.0f, 108.0f, 10.0f, 1.0f}, 0xffffffff},
12349 {{112.0f, 108.0f, 10.0f, 1.0f}, 0xffffffff},
12351 static const struct
12353 struct vec3 position;
12354 DWORD diffuse;
12356 quad5[] =
12358 {{-0.5f, 0.5f, 10.0f}, 0xff14f914},
12359 {{ 0.5f, 0.5f, 10.0f}, 0xff14f914},
12360 {{-0.5f, -0.5f, 10.0f}, 0xff14f914},
12361 {{ 0.5f, -0.5f, 10.0f}, 0xff14f914},
12363 quad6[] =
12365 {{-1.0f, 0.5f, 10.0f}, 0xfff91414},
12366 {{ 1.0f, 0.5f, 10.0f}, 0xfff91414},
12367 {{-1.0f, 0.25f, 10.0f}, 0xfff91414},
12368 {{ 1.0f, 0.25f, 10.0f}, 0xfff91414},
12371 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
12372 0, 0, 640, 480, NULL, NULL, NULL, NULL);
12373 d3d = Direct3DCreate9(D3D_SDK_VERSION);
12374 ok(!!d3d, "Failed to create a D3D object.\n");
12375 if (!(device = create_device(d3d, window, window, TRUE)))
12377 skip("Failed to create a D3D device, skipping tests.\n");
12378 goto done;
12381 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
12382 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
12384 vp.X = 0;
12385 vp.Y = 0;
12386 vp.Width = 640;
12387 vp.Height = 480;
12388 vp.MinZ = 0.0;
12389 vp.MaxZ = 7.5;
12391 hr = IDirect3DDevice9_SetViewport(device, &vp);
12392 if(FAILED(hr))
12394 /* Windows 7 rejects MaxZ > 1.0, Windows XP allows it. This doesn't break
12395 * the tests because the 7.5 is just intended to show that it doesn't have
12396 * any influence on the drawing or D3DRS_CLIPPING = FALSE. Set an accepted
12397 * viewport and continue.
12399 ok(broken(hr == D3DERR_INVALIDCALL), "D3D rejected maxZ > 1.0\n");
12400 vp.MaxZ = 1.0;
12401 hr = IDirect3DDevice9_SetViewport(device, &vp);
12403 ok(SUCCEEDED(hr), "SetViewport failed, hr %#x.\n", hr);
12405 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff00ff00, 1.0, 0);
12406 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
12408 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_CLIPPING, FALSE);
12409 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12410 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
12411 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12412 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, TRUE);
12413 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12414 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZFUNC, D3DCMP_LESSEQUAL);
12415 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12417 hr = IDirect3DDevice9_BeginScene(device);
12418 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
12420 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZRHW | D3DFVF_DIFFUSE);
12421 ok(SUCCEEDED(hr), "SetFVF failed, hr %#x.\n", hr);
12423 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, sizeof(*quad1));
12424 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
12425 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, sizeof(*quad2));
12426 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
12428 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_CLIPPING, TRUE);
12429 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12431 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad3, sizeof(*quad3));
12432 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
12433 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad4, sizeof(*quad4));
12434 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
12436 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_CLIPPING, FALSE);
12437 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12439 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
12440 ok(SUCCEEDED(hr), "SetFVF failed, hr %#x.\n", hr);
12442 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad5, sizeof(*quad5));
12443 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
12445 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_CLIPPING, TRUE);
12446 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12448 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad6, sizeof(*quad6));
12449 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
12451 hr = IDirect3DDevice9_EndScene(device);
12452 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
12454 if (caps.PrimitiveMiscCaps & D3DPMISCCAPS_CLIPTLVERTS)
12456 color = getPixelColor(device, 75, 75);
12457 ok(color_match(color, 0x0000ff00, 1), "color 0x%08x.\n", color);
12458 color = getPixelColor(device, 150, 150);
12459 ok(color_match(color, 0x0000ff00, 1), "color 0x%08x.\n", color);
12460 color = getPixelColor(device, 320, 240);
12461 ok(color_match(color, 0x0000ff00, 1), "color 0x%08x.\n", color);
12462 color = getPixelColor(device, 320, 330);
12463 ok(color_match(color, 0x0000ff00, 1), "color 0x%08x.\n", color);
12464 color = getPixelColor(device, 320, 330);
12465 ok(color_match(color, 0x0000ff00, 1), "color 0x%08x.\n", color);
12467 else
12469 color = getPixelColor(device, 75, 75);
12470 ok(color_match(color, 0x00ffffff, 1), "color 0x%08x.\n", color);
12471 color = getPixelColor(device, 150, 150);
12472 ok(color_match(color, 0x00ffffff, 1), "color 0x%08x.\n", color);
12473 color = getPixelColor(device, 320, 240);
12474 ok(color_match(color, 0x00002b7f, 1), "color 0x%08x.\n", color);
12475 color = getPixelColor(device, 320, 330);
12476 ok(color_match(color, 0x00f9e814, 1), "color 0x%08x.\n", color);
12477 color = getPixelColor(device, 320, 330);
12478 ok(color_match(color, 0x00f9e814, 1), "color 0x%08x.\n", color);
12481 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
12482 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
12484 refcount = IDirect3DDevice9_Release(device);
12485 ok(!refcount, "Device has %u references left.\n", refcount);
12486 done:
12487 IDirect3D9_Release(d3d);
12488 DestroyWindow(window);
12491 static void depth_bounds_test(void)
12493 static const struct
12495 struct vec4 position;
12496 DWORD diffuse;
12498 quad1[] =
12500 {{ 0.0f, 0.0f, 0.0f, 1.0f}, 0xfff9e814},
12501 {{640.0f, 0.0f, 0.0f, 1.0f}, 0xfff9e814},
12502 {{ 0.0f, 480.0f, 1.0f, 1.0f}, 0xfff9e814},
12503 {{640.0f, 480.0f, 1.0f, 1.0f}, 0xfff9e814},
12505 quad2[] =
12507 {{ 0.0f, 0.0f, 0.6f, 1.0f}, 0xff002b7f},
12508 {{640.0f, 0.0f, 0.6f, 1.0f}, 0xff002b7f},
12509 {{ 0.0f, 480.0f, 0.6f, 1.0f}, 0xff002b7f},
12510 {{640.0f, 480.0f, 0.6f, 1.0f}, 0xff002b7f},
12512 quad3[] =
12514 {{ 0.0f, 100.0f, 0.6f, 1.0f}, 0xfff91414},
12515 {{640.0f, 100.0f, 0.6f, 1.0f}, 0xfff91414},
12516 {{ 0.0f, 160.0f, 0.6f, 1.0f}, 0xfff91414},
12517 {{640.0f, 160.0f, 0.6f, 1.0f}, 0xfff91414},
12520 union {
12521 DWORD d;
12522 float f;
12523 } tmpvalue;
12525 IDirect3DSurface9 *offscreen_surface = NULL;
12526 IDirect3DDevice9 *device;
12527 IDirect3D9 *d3d;
12528 D3DCOLOR color;
12529 ULONG refcount;
12530 HWND window;
12531 HRESULT hr;
12533 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
12534 0, 0, 640, 480, NULL, NULL, NULL, NULL);
12535 d3d = Direct3DCreate9(D3D_SDK_VERSION);
12536 ok(!!d3d, "Failed to create a D3D object.\n");
12537 if (IDirect3D9_CheckDeviceFormat(d3d, 0, D3DDEVTYPE_HAL,
12538 D3DFMT_X8R8G8B8, 0, D3DRTYPE_SURFACE, MAKEFOURCC('N','V','D','B')) != D3D_OK)
12540 skip("No NVDB (depth bounds test) support, skipping tests.\n");
12541 goto done;
12543 if (!(device = create_device(d3d, window, window, TRUE)))
12545 skip("Failed to create a D3D device, skipping tests.\n");
12546 goto done;
12549 hr = IDirect3DDevice9_CreateOffscreenPlainSurface(device, 32, 32,
12550 MAKEFOURCC('N','V','D','B'), D3DPOOL_DEFAULT, &offscreen_surface, NULL);
12551 ok(FAILED(hr), "Able to create surface, hr %#x.\n", hr);
12552 if (offscreen_surface) IDirect3DSurface9_Release(offscreen_surface);
12554 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffffffff, 1.0, 0);
12555 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
12557 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
12558 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12559 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, TRUE);
12560 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12561 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, TRUE);
12562 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12563 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZFUNC, D3DCMP_ALWAYS);
12564 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12567 hr = IDirect3DDevice9_BeginScene(device);
12568 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
12570 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZRHW | D3DFVF_DIFFUSE);
12571 ok(SUCCEEDED(hr), "SetFVF failed, hr %#x.\n", hr);
12573 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, sizeof(*quad1));
12574 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
12576 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ADAPTIVETESS_X, MAKEFOURCC('N','V','D','B'));
12577 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12579 tmpvalue.f = 0.625;
12580 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ADAPTIVETESS_Z, tmpvalue.d);
12581 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12583 tmpvalue.f = 0.75;
12584 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ADAPTIVETESS_W, tmpvalue.d);
12585 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12587 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, sizeof(*quad2));
12588 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
12590 tmpvalue.f = 0.75;
12591 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ADAPTIVETESS_Z, tmpvalue.d);
12592 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12594 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad3, sizeof(*quad3));
12595 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
12597 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ADAPTIVETESS_X, 0);
12598 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12600 hr = IDirect3DDevice9_EndScene(device);
12601 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
12603 color = getPixelColor(device, 150, 130);
12604 ok(color_match(color, 0x00f9e814, 1), "color 0x%08x.\n", color);
12605 color = getPixelColor(device, 150, 200);
12606 ok(color_match(color, 0x00f9e814, 1), "color 0x%08x.\n", color);
12607 color = getPixelColor(device, 150, 300-5);
12608 ok(color_match(color, 0x00f9e814, 1), "color 0x%08x.\n", color);
12609 color = getPixelColor(device, 150, 300+5);
12610 ok(color_match(color, 0x00002b7f, 1), "color 0x%08x.\n", color);/**/
12611 color = getPixelColor(device, 150, 330);
12612 ok(color_match(color, 0x00002b7f, 1), "color 0x%08x.\n", color);
12613 color = getPixelColor(device, 150, 360-5);
12614 ok(color_match(color, 0x00002b7f, 1), "color 0x%08x.\n", color);/**/
12615 color = getPixelColor(device, 150, 360+5);
12616 ok(color_match(color, 0x00f9e814, 1), "color 0x%08x.\n", color);
12618 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
12619 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
12620 refcount = IDirect3DDevice9_Release(device);
12621 ok(!refcount, "Device has %u references left.\n", refcount);
12622 done:
12623 IDirect3D9_Release(d3d);
12624 DestroyWindow(window);
12627 static void depth_buffer_test(void)
12629 static const struct
12631 struct vec3 position;
12632 DWORD diffuse;
12634 quad1[] =
12636 {{-1.0, 1.0, 0.33f}, 0xff00ff00},
12637 {{ 1.0, 1.0, 0.33f}, 0xff00ff00},
12638 {{-1.0, -1.0, 0.33f}, 0xff00ff00},
12639 {{ 1.0, -1.0, 0.33f}, 0xff00ff00},
12641 quad2[] =
12643 {{-1.0, 1.0, 0.50f}, 0xffff00ff},
12644 {{ 1.0, 1.0, 0.50f}, 0xffff00ff},
12645 {{-1.0, -1.0, 0.50f}, 0xffff00ff},
12646 {{ 1.0, -1.0, 0.50f}, 0xffff00ff},
12648 quad3[] =
12650 {{-1.0, 1.0, 0.66f}, 0xffff0000},
12651 {{ 1.0, 1.0, 0.66f}, 0xffff0000},
12652 {{-1.0, -1.0, 0.66f}, 0xffff0000},
12653 {{ 1.0, -1.0, 0.66f}, 0xffff0000},
12655 static const DWORD expected_colors[4][4] =
12657 {0x000000ff, 0x000000ff, 0x0000ff00, 0x00ff0000},
12658 {0x000000ff, 0x000000ff, 0x0000ff00, 0x00ff0000},
12659 {0x0000ff00, 0x0000ff00, 0x0000ff00, 0x00ff0000},
12660 {0x00ff0000, 0x00ff0000, 0x00ff0000, 0x00ff0000},
12663 IDirect3DSurface9 *backbuffer, *rt1, *rt2, *rt3;
12664 IDirect3DDevice9 *device;
12665 unsigned int i, j;
12666 D3DVIEWPORT9 vp;
12667 IDirect3D9 *d3d;
12668 D3DCOLOR color;
12669 ULONG refcount;
12670 HWND window;
12671 HRESULT hr;
12673 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
12674 0, 0, 640, 480, NULL, NULL, NULL, NULL);
12675 d3d = Direct3DCreate9(D3D_SDK_VERSION);
12676 ok(!!d3d, "Failed to create a D3D object.\n");
12677 if (!(device = create_device(d3d, window, window, TRUE)))
12679 skip("Failed to create a D3D device, skipping tests.\n");
12680 goto done;
12683 vp.X = 0;
12684 vp.Y = 0;
12685 vp.Width = 640;
12686 vp.Height = 480;
12687 vp.MinZ = 0.0;
12688 vp.MaxZ = 1.0;
12690 hr = IDirect3DDevice9_SetViewport(device, &vp);
12691 ok(SUCCEEDED(hr), "SetViewport failed, hr %#x.\n", hr);
12693 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
12694 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12695 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, D3DZB_TRUE);
12696 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12697 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, TRUE);
12698 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12699 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZFUNC, D3DCMP_LESSEQUAL);
12700 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12701 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
12702 ok(SUCCEEDED(hr), "SetFVF failed, hr %#x.\n", hr);
12704 hr = IDirect3DDevice9_GetRenderTarget(device, 0, &backbuffer);
12705 ok(SUCCEEDED(hr), "GetRenderTarget failed, hr %#x.\n", hr);
12706 hr = IDirect3DDevice9_CreateRenderTarget(device, 320, 240, D3DFMT_A8R8G8B8,
12707 D3DMULTISAMPLE_NONE, 0, FALSE, &rt1, NULL);
12708 ok(SUCCEEDED(hr), "CreateRenderTarget failed, hr %#x.\n", hr);
12709 hr = IDirect3DDevice9_CreateRenderTarget(device, 480, 360, D3DFMT_A8R8G8B8,
12710 D3DMULTISAMPLE_NONE, 0, FALSE, &rt2, NULL);
12711 ok(SUCCEEDED(hr), "CreateRenderTarget failed, hr %#x.\n", hr);
12712 hr = IDirect3DDevice9_CreateRenderTarget(device, 640, 480, D3DFMT_A8R8G8B8,
12713 D3DMULTISAMPLE_NONE, 0, FALSE, &rt3, NULL);
12714 ok(SUCCEEDED(hr), "CreateRenderTarget failed, hr %#x.\n", hr);
12716 hr = IDirect3DDevice9_SetRenderTarget(device, 0, rt3);
12717 ok(SUCCEEDED(hr), "SetRenderTarget failed, hr %#x.\n", hr);
12718 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff0000ff, 0.0f, 0);
12719 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
12721 hr = IDirect3DDevice9_SetRenderTarget(device, 0, backbuffer);
12722 ok(SUCCEEDED(hr), "SetRenderTarget failed, hr %#x.\n", hr);
12723 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff0000ff, 1.0f, 0);
12724 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
12726 hr = IDirect3DDevice9_SetRenderTarget(device, 0, rt1);
12727 ok(SUCCEEDED(hr), "SetRenderTarget failed, hr %#x.\n", hr);
12728 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffffffff, 0.0f, 0);
12729 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
12731 hr = IDirect3DDevice9_SetRenderTarget(device, 0, rt2);
12732 ok(SUCCEEDED(hr), "SetRenderTarget failed, hr %#x.\n", hr);
12733 hr = IDirect3DDevice9_BeginScene(device);
12734 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
12735 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, sizeof(*quad2));
12736 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
12737 hr = IDirect3DDevice9_EndScene(device);
12738 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
12740 hr = IDirect3DDevice9_SetRenderTarget(device, 0, backbuffer);
12741 ok(SUCCEEDED(hr), "SetRenderTarget failed, hr %#x.\n", hr);
12743 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, FALSE);
12744 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12746 hr = IDirect3DDevice9_BeginScene(device);
12747 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
12748 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, sizeof(*quad1));
12749 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
12750 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad3, sizeof(*quad3));
12751 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
12752 hr = IDirect3DDevice9_EndScene(device);
12753 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
12755 for (i = 0; i < 4; ++i)
12757 for (j = 0; j < 4; ++j)
12759 unsigned int x = 80 * ((2 * j) + 1);
12760 unsigned int y = 60 * ((2 * i) + 1);
12761 color = getPixelColor(device, x, y);
12762 ok(color_match(color, expected_colors[i][j], 0),
12763 "Expected color 0x%08x at %u,%u, got 0x%08x.\n", expected_colors[i][j], x, y, color);
12767 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
12768 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
12770 IDirect3DSurface9_Release(backbuffer);
12771 IDirect3DSurface9_Release(rt3);
12772 IDirect3DSurface9_Release(rt2);
12773 IDirect3DSurface9_Release(rt1);
12774 refcount = IDirect3DDevice9_Release(device);
12775 ok(!refcount, "Device has %u references left.\n", refcount);
12776 done:
12777 IDirect3D9_Release(d3d);
12778 DestroyWindow(window);
12781 /* Test that partial depth copies work the way they're supposed to. The clear
12782 * on rt2 only needs a partial copy of the onscreen depth/stencil buffer, and
12783 * the following draw should only copy back the part that was modified. */
12784 static void depth_buffer2_test(void)
12786 static const struct
12788 struct vec3 position;
12789 DWORD diffuse;
12791 quad[] =
12793 {{-1.0f, 1.0f, 0.66f}, 0xffff0000},
12794 {{ 1.0f, 1.0f, 0.66f}, 0xffff0000},
12795 {{-1.0f, -1.0f, 0.66f}, 0xffff0000},
12796 {{ 1.0f, -1.0f, 0.66f}, 0xffff0000},
12799 IDirect3DSurface9 *backbuffer, *rt1, *rt2;
12800 IDirect3DDevice9 *device;
12801 unsigned int i, j;
12802 D3DVIEWPORT9 vp;
12803 IDirect3D9 *d3d;
12804 D3DCOLOR color;
12805 ULONG refcount;
12806 HWND window;
12807 HRESULT hr;
12809 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
12810 0, 0, 640, 480, NULL, NULL, NULL, NULL);
12811 d3d = Direct3DCreate9(D3D_SDK_VERSION);
12812 ok(!!d3d, "Failed to create a D3D object.\n");
12813 if (!(device = create_device(d3d, window, window, TRUE)))
12815 skip("Failed to create a D3D device, skipping tests.\n");
12816 goto done;
12819 vp.X = 0;
12820 vp.Y = 0;
12821 vp.Width = 640;
12822 vp.Height = 480;
12823 vp.MinZ = 0.0;
12824 vp.MaxZ = 1.0;
12826 hr = IDirect3DDevice9_SetViewport(device, &vp);
12827 ok(SUCCEEDED(hr), "SetViewport failed, hr %#x.\n", hr);
12829 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
12830 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12831 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, D3DZB_TRUE);
12832 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12833 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, TRUE);
12834 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12835 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZFUNC, D3DCMP_LESSEQUAL);
12836 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12837 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
12838 ok(SUCCEEDED(hr), "SetFVF failed, hr %#x.\n", hr);
12840 hr = IDirect3DDevice9_CreateRenderTarget(device, 640, 480, D3DFMT_A8R8G8B8,
12841 D3DMULTISAMPLE_NONE, 0, FALSE, &rt1, NULL);
12842 ok(SUCCEEDED(hr), "CreateRenderTarget failed, hr %#x.\n", hr);
12843 hr = IDirect3DDevice9_CreateRenderTarget(device, 480, 360, D3DFMT_A8R8G8B8,
12844 D3DMULTISAMPLE_NONE, 0, FALSE, &rt2, NULL);
12845 ok(SUCCEEDED(hr), "CreateRenderTarget failed, hr %#x.\n", hr);
12846 hr = IDirect3DDevice9_GetRenderTarget(device, 0, &backbuffer);
12847 ok(SUCCEEDED(hr), "GetRenderTarget failed, hr %#x.\n", hr);
12849 hr = IDirect3DDevice9_SetRenderTarget(device, 0, rt1);
12850 ok(SUCCEEDED(hr), "SetRenderTarget failed, hr %#x.\n", hr);
12851 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff0000ff, 1.0f, 0);
12852 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
12854 hr = IDirect3DDevice9_SetRenderTarget(device, 0, backbuffer);
12855 ok(SUCCEEDED(hr), "SetRenderTarget failed, hr %#x.\n", hr);
12856 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff00ff00, 0.5f, 0);
12857 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
12859 hr = IDirect3DDevice9_SetRenderTarget(device, 0, rt2);
12860 ok(SUCCEEDED(hr), "SetRenderTarget failed, hr %#x.\n", hr);
12861 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffffffff, 0.0f, 0);
12862 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
12864 hr = IDirect3DDevice9_SetRenderTarget(device, 0, backbuffer);
12865 ok(SUCCEEDED(hr), "SetRenderTarget failed, hr %#x.\n", hr);
12867 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, FALSE);
12868 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12870 hr = IDirect3DDevice9_BeginScene(device);
12871 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
12872 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
12873 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
12874 hr = IDirect3DDevice9_EndScene(device);
12875 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
12877 for (i = 0; i < 4; ++i)
12879 for (j = 0; j < 4; ++j)
12881 unsigned int x = 80 * ((2 * j) + 1);
12882 unsigned int y = 60 * ((2 * i) + 1);
12883 color = getPixelColor(device, x, y);
12884 ok(color_match(color, D3DCOLOR_ARGB(0x00, 0x00, 0xff, 0x00), 0),
12885 "Expected color 0x0000ff00 at %u,%u, got 0x%08x.\n", x, y, color);
12889 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
12890 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
12892 IDirect3DSurface9_Release(backbuffer);
12893 IDirect3DSurface9_Release(rt2);
12894 IDirect3DSurface9_Release(rt1);
12895 refcount = IDirect3DDevice9_Release(device);
12896 ok(!refcount, "Device has %u references left.\n", refcount);
12897 done:
12898 IDirect3D9_Release(d3d);
12899 DestroyWindow(window);
12902 static void depth_blit_test(void)
12904 static const struct
12906 struct vec3 position;
12907 DWORD diffuse;
12909 quad1[] =
12911 {{-1.0f, 1.0f, 0.33f}, 0xff00ff00},
12912 {{ 1.0f, 1.0f, 0.33f}, 0xff00ff00},
12913 {{-1.0f, -1.0f, 0.33f}, 0xff00ff00},
12914 {{ 1.0f, -1.0f, 0.33f}, 0xff00ff00},
12916 quad2[] =
12918 {{-1.0f, 1.0f, 0.66f}, 0xff0000ff},
12919 {{ 1.0f, 1.0f, 0.66f}, 0xff0000ff},
12920 {{-1.0f, -1.0f, 0.66f}, 0xff0000ff},
12921 {{ 1.0f, -1.0f, 0.66f}, 0xff0000ff},
12923 static const DWORD expected_colors[4][4] =
12925 {0x000000ff, 0x000000ff, 0x0000ff00, 0x00ff0000},
12926 {0x000000ff, 0x000000ff, 0x0000ff00, 0x00ff0000},
12927 {0x0000ff00, 0x0000ff00, 0x0000ff00, 0x00ff0000},
12928 {0x00ff0000, 0x00ff0000, 0x00ff0000, 0x00ff0000},
12931 IDirect3DSurface9 *backbuffer, *ds1, *ds2, *ds3;
12932 IDirect3DDevice9 *device;
12933 RECT src_rect, dst_rect;
12934 unsigned int i, j;
12935 D3DVIEWPORT9 vp;
12936 IDirect3D9 *d3d;
12937 D3DCOLOR color;
12938 ULONG refcount;
12939 HWND window;
12940 HRESULT hr;
12942 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
12943 0, 0, 640, 480, NULL, NULL, NULL, NULL);
12944 d3d = Direct3DCreate9(D3D_SDK_VERSION);
12945 ok(!!d3d, "Failed to create a D3D object.\n");
12946 if (!(device = create_device(d3d, window, window, TRUE)))
12948 skip("Failed to create a D3D device, skipping tests.\n");
12949 goto done;
12952 vp.X = 0;
12953 vp.Y = 0;
12954 vp.Width = 640;
12955 vp.Height = 480;
12956 vp.MinZ = 0.0;
12957 vp.MaxZ = 1.0;
12959 hr = IDirect3DDevice9_SetViewport(device, &vp);
12960 ok(SUCCEEDED(hr), "SetViewport failed, hr %#x.\n", hr);
12962 hr = IDirect3DDevice9_GetRenderTarget(device, 0, &backbuffer);
12963 ok(SUCCEEDED(hr), "GetRenderTarget failed, hr %#x.\n", hr);
12964 hr = IDirect3DDevice9_GetDepthStencilSurface(device, &ds1);
12965 ok(SUCCEEDED(hr), "GetDepthStencilSurface failed, hr %#x.\n", hr);
12966 hr = IDirect3DDevice9_CreateDepthStencilSurface(device, 640, 480, D3DFMT_D24S8, 0, 0, FALSE, &ds2, NULL);
12967 ok(SUCCEEDED(hr), "CreateDepthStencilSurface failed, hr %#x.\n", hr);
12968 hr = IDirect3DDevice9_SetDepthStencilSurface(device, ds2);
12969 ok(SUCCEEDED(hr), "SetDepthStencilSurface failed, hr %#x.\n", hr);
12970 hr = IDirect3DDevice9_CreateDepthStencilSurface(device, 320, 240, D3DFMT_D24S8, 0, 0, FALSE, &ds3, NULL);
12971 ok(SUCCEEDED(hr), "CreateDepthStencilSurface failed, hr %#x.\n", hr);
12973 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
12974 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12975 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, D3DZB_TRUE);
12976 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12977 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZFUNC, D3DCMP_LESSEQUAL);
12978 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
12979 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
12980 ok(SUCCEEDED(hr), "SetFVF failed, hr %#x.\n", hr);
12982 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_ZBUFFER, 0, 0.0f, 0);
12983 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
12984 SetRect(&dst_rect, 0, 0, 480, 360);
12985 hr = IDirect3DDevice9_Clear(device, 1, (D3DRECT *)&dst_rect, D3DCLEAR_ZBUFFER, 0, 0.5f, 0);
12986 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
12987 SetRect(&dst_rect, 0, 0, 320, 240);
12988 hr = IDirect3DDevice9_Clear(device, 1, (D3DRECT *)&dst_rect, D3DCLEAR_ZBUFFER, 0, 1.0f, 0);
12989 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
12991 /* Partial blit. */
12992 SetRect(&src_rect, 0, 0, 320, 240);
12993 SetRect(&dst_rect, 0, 0, 320, 240);
12994 hr = IDirect3DDevice9_StretchRect(device, ds2, &src_rect, ds1, &dst_rect, D3DTEXF_POINT);
12995 ok(hr == D3DERR_INVALIDCALL, "StretchRect returned %#x, expected %#x.\n", hr, D3DERR_INVALIDCALL);
12996 /* Flipped. */
12997 SetRect(&src_rect, 0, 0, 640, 480);
12998 SetRect(&dst_rect, 0, 480, 640, 0);
12999 hr = IDirect3DDevice9_StretchRect(device, ds2, &src_rect, ds1, &dst_rect, D3DTEXF_POINT);
13000 ok(hr == D3DERR_INVALIDCALL, "StretchRect returned %#x, expected %#x.\n", hr, D3DERR_INVALIDCALL);
13001 /* Full, explicit. */
13002 SetRect(&src_rect, 0, 0, 640, 480);
13003 SetRect(&dst_rect, 0, 0, 640, 480);
13004 hr = IDirect3DDevice9_StretchRect(device, ds2, &src_rect, ds1, &dst_rect, D3DTEXF_POINT);
13005 ok(SUCCEEDED(hr), "StretchRect failed, hr %#x.\n", hr);
13006 /* Filtered blit. */
13007 hr = IDirect3DDevice9_StretchRect(device, ds2, NULL, ds1, NULL, D3DTEXF_LINEAR);
13008 ok(SUCCEEDED(hr), "StretchRect failed, hr %#x.\n", hr);
13009 /* Depth -> color blit.*/
13010 hr = IDirect3DDevice9_StretchRect(device, ds2, NULL, backbuffer, NULL, D3DTEXF_POINT);
13011 ok(hr == D3DERR_INVALIDCALL, "StretchRect returned %#x, expected %#x.\n", hr, D3DERR_INVALIDCALL);
13012 IDirect3DSurface9_Release(backbuffer);
13013 /* Full surface, different sizes */
13014 hr = IDirect3DDevice9_StretchRect(device, ds3, NULL, ds1, NULL, D3DTEXF_POINT);
13015 ok(hr == D3DERR_INVALIDCALL, "StretchRect returned %#x, expected %#x.\n", hr, D3DERR_INVALIDCALL);
13016 hr = IDirect3DDevice9_StretchRect(device, ds1, NULL, ds3, NULL, D3DTEXF_POINT);
13017 ok(hr == D3DERR_INVALIDCALL, "StretchRect returned %#x, expected %#x.\n", hr, D3DERR_INVALIDCALL);
13019 hr = IDirect3DDevice9_SetDepthStencilSurface(device, ds1);
13020 ok(SUCCEEDED(hr), "SetDepthStencilSurface failed, hr %#x.\n", hr);
13021 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_ZBUFFER | D3DCLEAR_TARGET, 0xffff0000, 1.0f, 0);
13022 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
13023 hr = IDirect3DDevice9_StretchRect(device, ds2, NULL, ds1, NULL, D3DTEXF_POINT);
13024 ok(SUCCEEDED(hr), "StretchRect failed, hr %#x.\n", hr);
13026 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, FALSE);
13027 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
13028 hr = IDirect3DDevice9_BeginScene(device);
13029 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
13030 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, sizeof(*quad1));
13031 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
13032 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, sizeof(*quad2));
13033 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
13034 hr = IDirect3DDevice9_EndScene(device);
13035 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
13037 for (i = 0; i < 4; ++i)
13039 for (j = 0; j < 4; ++j)
13041 unsigned int x = 80 * ((2 * j) + 1);
13042 unsigned int y = 60 * ((2 * i) + 1);
13043 color = getPixelColor(device, x, y);
13044 ok(color_match(color, expected_colors[i][j], 0),
13045 "Expected color 0x%08x at %u,%u, got 0x%08x.\n", expected_colors[i][j], x, y, color);
13049 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
13050 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
13052 IDirect3DSurface9_Release(ds3);
13053 IDirect3DSurface9_Release(ds2);
13054 IDirect3DSurface9_Release(ds1);
13055 refcount = IDirect3DDevice9_Release(device);
13056 ok(!refcount, "Device has %u references left.\n", refcount);
13057 done:
13058 IDirect3D9_Release(d3d);
13059 DestroyWindow(window);
13062 static void intz_test(void)
13064 static const DWORD ps_code[] =
13066 0xffff0200, /* ps_2_0 */
13067 0x0200001f, 0x90000000, 0xa00f0800, /* dcl_2d s0 */
13068 0x0200001f, 0x80000000, 0xb00f0000, /* dcl t0 */
13069 0x05000051, 0xa00f0000, 0x00000000, 0x00000000, 0x00000000, 0x3f800000, /* def c0, 0.0, 0.0, 0.0, 1.0 */
13070 0x02000001, 0x800f0001, 0xa0e40000, /* mov r1, c0 */
13071 0x03000042, 0x800f0000, 0xb0e40000, 0xa0e40800, /* texld r0, t0, s0 */
13072 0x02000001, 0x80010001, 0x80e40000, /* mov r1.x, r0 */
13073 0x03010042, 0x800f0000, 0xb0e40000, 0xa0e40800, /* texldp r0, t0, s0 */
13074 0x02000001, 0x80020001, 0x80000000, /* mov r1.y, r0.x */
13075 0x02000001, 0x800f0800, 0x80e40001, /* mov oC0, r1 */
13076 0x0000ffff, /* end */
13078 struct
13080 float x, y, z;
13081 float s, t, p, q;
13083 quad[] =
13085 { -1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 1.0f, 0.5f},
13086 { 1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 0.5f},
13087 { -1.0f, -1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.5f},
13088 { 1.0f, -1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 0.5f},
13090 half_quad_1[] =
13092 { -1.0f, 0.0f, 0.0f, 0.0f, 1.0f, 1.0f, 0.5f},
13093 { 1.0f, 0.0f, 1.0f, 1.0f, 1.0f, 1.0f, 0.5f},
13094 { -1.0f, -1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.5f},
13095 { 1.0f, -1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 0.5f},
13097 half_quad_2[] =
13099 { -1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 1.0f, 0.5f},
13100 { 1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 0.5f},
13101 { -1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.5f},
13102 { 1.0f, 0.0f, 1.0f, 1.0f, 0.0f, 0.0f, 0.5f},
13104 struct
13106 UINT x, y;
13107 D3DCOLOR color;
13109 expected_colors[] =
13111 { 80, 100, D3DCOLOR_ARGB(0x00, 0x20, 0x40, 0x00)},
13112 {240, 100, D3DCOLOR_ARGB(0x00, 0x60, 0xbf, 0x00)},
13113 {400, 100, D3DCOLOR_ARGB(0x00, 0x9f, 0x40, 0x00)},
13114 {560, 100, D3DCOLOR_ARGB(0x00, 0xdf, 0xbf, 0x00)},
13115 { 80, 450, D3DCOLOR_ARGB(0x00, 0x20, 0x40, 0x00)},
13116 {240, 450, D3DCOLOR_ARGB(0x00, 0x60, 0xbf, 0x00)},
13117 {400, 450, D3DCOLOR_ARGB(0x00, 0x9f, 0x40, 0x00)},
13118 {560, 450, D3DCOLOR_ARGB(0x00, 0xdf, 0xbf, 0x00)},
13121 IDirect3DSurface9 *original_rt, *rt;
13122 IDirect3DTexture9 *texture;
13123 IDirect3DPixelShader9 *ps;
13124 IDirect3DDevice9 *device;
13125 IDirect3DSurface9 *ds;
13126 IDirect3D9 *d3d;
13127 ULONG refcount;
13128 D3DCAPS9 caps;
13129 HWND window;
13130 HRESULT hr;
13131 UINT i;
13133 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
13134 0, 0, 640, 480, NULL, NULL, NULL, NULL);
13135 d3d = Direct3DCreate9(D3D_SDK_VERSION);
13136 ok(!!d3d, "Failed to create a D3D object.\n");
13137 if (FAILED(IDirect3D9_CheckDeviceFormat(d3d, D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL,
13138 D3DFMT_X8R8G8B8, D3DUSAGE_DEPTHSTENCIL, D3DRTYPE_TEXTURE, MAKEFOURCC('I','N','T','Z'))))
13140 skip("No INTZ support, skipping INTZ test.\n");
13141 goto done;
13143 if (!(device = create_device(d3d, window, window, TRUE)))
13145 skip("Failed to create a D3D device, skipping tests.\n");
13146 goto done;
13149 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
13150 ok(SUCCEEDED(hr), "GetDeviceCaps failed, hr %#x.\n", hr);
13151 if (caps.PixelShaderVersion < D3DPS_VERSION(2, 0))
13153 skip("No pixel shader 2.0 support, skipping INTZ test.\n");
13154 IDirect3DDevice9_Release(device);
13155 goto done;
13157 if (caps.TextureCaps & D3DPTEXTURECAPS_POW2)
13159 skip("No unconditional NP2 texture support, skipping INTZ test.\n");
13160 IDirect3DDevice9_Release(device);
13161 goto done;
13164 hr = IDirect3DDevice9_GetRenderTarget(device, 0, &original_rt);
13165 ok(SUCCEEDED(hr), "GetRenderTarget failed, hr %#x.\n", hr);
13167 hr = IDirect3DDevice9_CreateTexture(device, 640, 480, 1,
13168 D3DUSAGE_DEPTHSTENCIL, MAKEFOURCC('I','N','T','Z'), D3DPOOL_DEFAULT, &texture, NULL);
13169 ok(SUCCEEDED(hr), "CreateTexture failed, hr %#x.\n", hr);
13170 hr = IDirect3DDevice9_CreateRenderTarget(device, 640, 480, D3DFMT_A8R8G8B8,
13171 D3DMULTISAMPLE_NONE, 0, FALSE, &rt, NULL);
13172 ok(SUCCEEDED(hr), "CreateRenderTarget failed, hr %#x.\n", hr);
13173 hr = IDirect3DDevice9_CreatePixelShader(device, ps_code, &ps);
13174 ok(SUCCEEDED(hr), "CreatePixelShader failed, hr %#x.\n", hr);
13176 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1 | D3DFVF_TEXCOORDSIZE4(0));
13177 ok(SUCCEEDED(hr), "SetFVF failed, hr %#x.\n", hr);
13178 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, D3DZB_TRUE);
13179 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
13180 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZFUNC, D3DCMP_ALWAYS);
13181 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
13182 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, TRUE);
13183 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
13184 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
13185 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
13187 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_ADDRESSU, D3DTADDRESS_WRAP);
13188 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
13189 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_ADDRESSV, D3DTADDRESS_WRAP);
13190 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
13191 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAGFILTER, D3DTEXF_POINT);
13192 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
13193 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MINFILTER, D3DTEXF_POINT);
13194 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
13195 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MIPFILTER, D3DTEXF_POINT);
13196 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
13198 /* Render offscreen, using the INTZ texture as depth buffer */
13199 hr = IDirect3DTexture9_GetSurfaceLevel(texture, 0, &ds);
13200 ok(SUCCEEDED(hr), "GetSurfaceLevel failed, hr %#x.\n", hr);
13201 hr = IDirect3DDevice9_SetDepthStencilSurface(device, ds);
13202 ok(SUCCEEDED(hr), "SetDepthStencilSurface failed, hr %#x.\n", hr);
13203 hr = IDirect3DDevice9_SetRenderTarget(device, 0, rt);
13204 ok(SUCCEEDED(hr), "SetRenderTarget failed, hr %#x.\n", hr);
13205 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
13206 ok(SUCCEEDED(hr), "SetPixelShader failed, hr %#x.\n", hr);
13208 /* Setup the depth/stencil surface. */
13209 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_ZBUFFER, 0, 0.0f, 0);
13210 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
13212 hr = IDirect3DDevice9_BeginScene(device);
13213 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
13214 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
13215 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
13216 hr = IDirect3DDevice9_EndScene(device);
13217 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
13219 hr = IDirect3DDevice9_SetDepthStencilSurface(device, NULL);
13220 ok(SUCCEEDED(hr), "SetDepthStencilSurface failed, hr %#x.\n", hr);
13221 IDirect3DSurface9_Release(ds);
13222 hr = IDirect3DDevice9_SetRenderTarget(device, 0, original_rt);
13223 ok(SUCCEEDED(hr), "SetRenderTarget failed, hr %#x.\n", hr);
13224 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)texture);
13225 ok(SUCCEEDED(hr), "SetTexture failed, hr %#x.\n", hr);
13226 hr = IDirect3DDevice9_SetPixelShader(device, ps);
13227 ok(SUCCEEDED(hr), "SetPixelShader failed, hr %#x.\n", hr);
13229 /* Read the depth values back. */
13230 hr = IDirect3DDevice9_BeginScene(device);
13231 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
13232 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
13233 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
13234 hr = IDirect3DDevice9_EndScene(device);
13235 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
13237 for (i = 0; i < sizeof(expected_colors) / sizeof(*expected_colors); ++i)
13239 D3DCOLOR color = getPixelColor(device, expected_colors[i].x, expected_colors[i].y);
13240 ok(color_match(color, expected_colors[i].color, 1),
13241 "Expected color 0x%08x at (%u, %u), got 0x%08x.\n",
13242 expected_colors[i].color, expected_colors[i].x, expected_colors[i].y, color);
13245 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
13246 ok(SUCCEEDED(hr), "Present failed, hr %#x.\n", hr);
13248 hr = IDirect3DDevice9_SetTexture(device, 0, NULL);
13249 ok(SUCCEEDED(hr), "SetTexture failed, hr %#x.\n", hr);
13250 IDirect3DTexture9_Release(texture);
13252 /* Render onscreen while using the INTZ texture as depth buffer */
13253 hr = IDirect3DDevice9_CreateTexture(device, 640, 480, 1,
13254 D3DUSAGE_DEPTHSTENCIL, MAKEFOURCC('I','N','T','Z'), D3DPOOL_DEFAULT, &texture, NULL);
13255 hr = IDirect3DTexture9_GetSurfaceLevel(texture, 0, &ds);
13256 ok(SUCCEEDED(hr), "GetSurfaceLevel failed, hr %#x.\n", hr);
13257 hr = IDirect3DDevice9_SetDepthStencilSurface(device, ds);
13258 ok(SUCCEEDED(hr), "SetDepthStencilSurface failed, hr %#x.\n", hr);
13259 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
13260 ok(SUCCEEDED(hr), "SetPixelShader failed, hr %#x.\n", hr);
13262 /* Setup the depth/stencil surface. */
13263 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_ZBUFFER, 0, 0.0f, 0);
13264 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
13266 hr = IDirect3DDevice9_BeginScene(device);
13267 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
13268 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
13269 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
13270 hr = IDirect3DDevice9_EndScene(device);
13271 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
13273 hr = IDirect3DDevice9_SetDepthStencilSurface(device, NULL);
13274 ok(SUCCEEDED(hr), "SetDepthStencilSurface failed, hr %#x.\n", hr);
13275 IDirect3DSurface9_Release(ds);
13276 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)texture);
13277 ok(SUCCEEDED(hr), "SetTexture failed, hr %#x.\n", hr);
13278 hr = IDirect3DDevice9_SetPixelShader(device, ps);
13279 ok(SUCCEEDED(hr), "SetPixelShader failed, hr %#x.\n", hr);
13281 /* Read the depth values back. */
13282 hr = IDirect3DDevice9_BeginScene(device);
13283 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
13284 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
13285 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
13286 hr = IDirect3DDevice9_EndScene(device);
13287 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
13289 for (i = 0; i < sizeof(expected_colors) / sizeof(*expected_colors); ++i)
13291 D3DCOLOR color = getPixelColor(device, expected_colors[i].x, expected_colors[i].y);
13292 ok(color_match(color, expected_colors[i].color, 1),
13293 "Expected color 0x%08x at (%u, %u), got 0x%08x.\n",
13294 expected_colors[i].color, expected_colors[i].x, expected_colors[i].y, color);
13297 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
13298 ok(SUCCEEDED(hr), "Present failed, hr %#x.\n", hr);
13300 hr = IDirect3DDevice9_SetTexture(device, 0, NULL);
13301 ok(SUCCEEDED(hr), "SetTexture failed, hr %#x.\n", hr);
13302 IDirect3DTexture9_Release(texture);
13304 /* Render offscreen, then onscreen, and finally check the INTZ texture in both areas */
13305 hr = IDirect3DDevice9_CreateTexture(device, 640, 480, 1,
13306 D3DUSAGE_DEPTHSTENCIL, MAKEFOURCC('I','N','T','Z'), D3DPOOL_DEFAULT, &texture, NULL);
13307 hr = IDirect3DTexture9_GetSurfaceLevel(texture, 0, &ds);
13308 ok(SUCCEEDED(hr), "GetSurfaceLevel failed, hr %#x.\n", hr);
13310 hr = IDirect3DDevice9_SetDepthStencilSurface(device, ds);
13311 ok(SUCCEEDED(hr), "SetDepthStencilSurface failed, hr %#x.\n", hr);
13312 hr = IDirect3DDevice9_SetRenderTarget(device, 0, rt);
13313 ok(SUCCEEDED(hr), "SetRenderTarget failed, hr %#x.\n", hr);
13314 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
13315 ok(SUCCEEDED(hr), "SetPixelShader failed, hr %#x.\n", hr);
13317 /* Setup the depth/stencil surface. */
13318 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_ZBUFFER, 0, 0.0f, 0);
13319 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
13321 hr = IDirect3DDevice9_BeginScene(device);
13322 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
13323 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, half_quad_1, sizeof(*half_quad_1));
13324 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
13325 hr = IDirect3DDevice9_EndScene(device);
13326 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
13328 hr = IDirect3DDevice9_SetRenderTarget(device, 0, original_rt);
13329 ok(SUCCEEDED(hr), "SetRenderTarget failed, hr %#x.\n", hr);
13331 hr = IDirect3DDevice9_BeginScene(device);
13332 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
13333 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, half_quad_2, sizeof(*half_quad_2));
13334 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
13335 hr = IDirect3DDevice9_EndScene(device);
13336 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
13338 hr = IDirect3DDevice9_SetDepthStencilSurface(device, NULL);
13339 ok(SUCCEEDED(hr), "SetDepthStencilSurface failed, hr %#x.\n", hr);
13340 IDirect3DSurface9_Release(ds);
13341 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)texture);
13342 ok(SUCCEEDED(hr), "SetTexture failed, hr %#x.\n", hr);
13343 hr = IDirect3DDevice9_SetPixelShader(device, ps);
13344 ok(SUCCEEDED(hr), "SetPixelShader failed, hr %#x.\n", hr);
13346 /* Read the depth values back. */
13347 hr = IDirect3DDevice9_BeginScene(device);
13348 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
13349 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
13350 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
13351 hr = IDirect3DDevice9_EndScene(device);
13352 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
13354 for (i = 0; i < sizeof(expected_colors) / sizeof(*expected_colors); ++i)
13356 D3DCOLOR color = getPixelColor(device, expected_colors[i].x, expected_colors[i].y);
13357 ok(color_match(color, expected_colors[i].color, 1),
13358 "Expected color 0x%08x at (%u, %u), got 0x%08x.\n",
13359 expected_colors[i].color, expected_colors[i].x, expected_colors[i].y, color);
13362 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
13363 ok(SUCCEEDED(hr), "Present failed, hr %#x.\n", hr);
13365 IDirect3DTexture9_Release(texture);
13366 IDirect3DPixelShader9_Release(ps);
13367 IDirect3DSurface9_Release(original_rt);
13368 IDirect3DSurface9_Release(rt);
13369 refcount = IDirect3DDevice9_Release(device);
13370 ok(!refcount, "Device has %u references left.\n", refcount);
13371 done:
13372 IDirect3D9_Release(d3d);
13373 DestroyWindow(window);
13376 static void shadow_test(void)
13378 static const DWORD ps_code[] =
13380 0xffff0200, /* ps_2_0 */
13381 0x0200001f, 0x90000000, 0xa00f0800, /* dcl_2d s0 */
13382 0x0200001f, 0x80000000, 0xb00f0000, /* dcl t0 */
13383 0x05000051, 0xa00f0000, 0x00000000, 0x00000000, 0x00000000, 0x3f800000, /* def c0, 0.0, 0.0, 0.0, 1.0 */
13384 0x02000001, 0x800f0001, 0xa0e40000, /* mov r1, c0 */
13385 0x03000042, 0x800f0000, 0xb0e40000, 0xa0e40800, /* texld r0, t0, s0 */
13386 0x02000001, 0x80010001, 0x80e40000, /* mov r1.x, r0 */
13387 0x03010042, 0x800f0000, 0xb0e40000, 0xa0e40800, /* texldp r0, t0, s0 */
13388 0x02000001, 0x80020001, 0x80000000, /* mov r1.y, r0.x */
13389 0x02000001, 0x800f0800, 0x80e40001, /* mov 0C0, r1 */
13390 0x0000ffff, /* end */
13392 struct
13394 D3DFORMAT format;
13395 const char *name;
13397 formats[] =
13399 {D3DFMT_D16_LOCKABLE, "D3DFMT_D16_LOCKABLE"},
13400 {D3DFMT_D32, "D3DFMT_D32"},
13401 {D3DFMT_D15S1, "D3DFMT_D15S1"},
13402 {D3DFMT_D24S8, "D3DFMT_D24S8"},
13403 {D3DFMT_D24X8, "D3DFMT_D24X8"},
13404 {D3DFMT_D24X4S4, "D3DFMT_D24X4S4"},
13405 {D3DFMT_D16, "D3DFMT_D16"},
13406 {D3DFMT_D32F_LOCKABLE, "D3DFMT_D32F_LOCKABLE"},
13407 {D3DFMT_D24FS8, "D3DFMT_D24FS8"},
13409 struct
13411 float x, y, z;
13412 float s, t, p, q;
13414 quad[] =
13416 { -1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 1.0f, 0.0f},
13417 { 1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 0.0f},
13418 { -1.0f, -1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f},
13419 { 1.0f, -1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 1.0f},
13421 struct
13423 UINT x, y;
13424 D3DCOLOR color;
13426 expected_colors[] =
13428 {400, 60, D3DCOLOR_ARGB(0x00, 0x00, 0x00, 0x00)},
13429 {560, 180, D3DCOLOR_ARGB(0x00, 0xff, 0x00, 0x00)},
13430 {560, 300, D3DCOLOR_ARGB(0x00, 0xff, 0x00, 0x00)},
13431 {400, 420, D3DCOLOR_ARGB(0x00, 0xff, 0xff, 0x00)},
13432 {240, 420, D3DCOLOR_ARGB(0x00, 0xff, 0xff, 0x00)},
13433 { 80, 300, D3DCOLOR_ARGB(0x00, 0x00, 0x00, 0x00)},
13434 { 80, 180, D3DCOLOR_ARGB(0x00, 0x00, 0x00, 0x00)},
13435 {240, 60, D3DCOLOR_ARGB(0x00, 0x00, 0x00, 0x00)},
13438 IDirect3DSurface9 *original_ds, *original_rt, *rt;
13439 IDirect3DPixelShader9 *ps;
13440 IDirect3DDevice9 *device;
13441 IDirect3D9 *d3d;
13442 ULONG refcount;
13443 D3DCAPS9 caps;
13444 HWND window;
13445 HRESULT hr;
13446 UINT i;
13448 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
13449 0, 0, 640, 480, NULL, NULL, NULL, NULL);
13450 d3d = Direct3DCreate9(D3D_SDK_VERSION);
13451 ok(!!d3d, "Failed to create a D3D object.\n");
13452 if (!(device = create_device(d3d, window, window, TRUE)))
13454 skip("Failed to create a D3D device, skipping tests.\n");
13455 goto done;
13458 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
13459 ok(SUCCEEDED(hr), "GetDeviceCaps failed, hr %#x.\n", hr);
13460 if (caps.PixelShaderVersion < D3DPS_VERSION(2, 0))
13462 skip("No pixel shader 2.0 support, skipping shadow test.\n");
13463 IDirect3DDevice9_Release(device);
13464 goto done;
13467 hr = IDirect3DDevice9_GetRenderTarget(device, 0, &original_rt);
13468 ok(SUCCEEDED(hr), "GetRenderTarget failed, hr %#x.\n", hr);
13469 hr = IDirect3DDevice9_GetDepthStencilSurface(device, &original_ds);
13470 ok(SUCCEEDED(hr), "GetDepthStencilSurface failed, hr %#x.\n", hr);
13472 hr = IDirect3DDevice9_CreateRenderTarget(device, 1024, 1024, D3DFMT_A8R8G8B8,
13473 D3DMULTISAMPLE_NONE, 0, FALSE, &rt, NULL);
13474 ok(SUCCEEDED(hr), "CreateRenderTarget failed, hr %#x.\n", hr);
13475 hr = IDirect3DDevice9_CreatePixelShader(device, ps_code, &ps);
13476 ok(SUCCEEDED(hr), "CreatePixelShader failed, hr %#x.\n", hr);
13478 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1 | D3DFVF_TEXCOORDSIZE4(0));
13479 ok(SUCCEEDED(hr), "SetFVF failed, hr %#x.\n", hr);
13480 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, D3DZB_TRUE);
13481 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
13482 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZFUNC, D3DCMP_ALWAYS);
13483 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
13484 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, TRUE);
13485 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
13486 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
13487 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
13489 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_ADDRESSU, D3DTADDRESS_WRAP);
13490 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
13491 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_ADDRESSV, D3DTADDRESS_WRAP);
13492 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
13493 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAGFILTER, D3DTEXF_POINT);
13494 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
13495 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MINFILTER, D3DTEXF_POINT);
13496 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
13497 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MIPFILTER, D3DTEXF_POINT);
13498 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
13500 for (i = 0; i < sizeof(formats) / sizeof(*formats); ++i)
13502 D3DFORMAT format = formats[i].format;
13503 IDirect3DTexture9 *texture;
13504 IDirect3DSurface9 *ds;
13505 unsigned int j;
13507 if (FAILED(IDirect3D9_CheckDeviceFormat(d3d, D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL,
13508 D3DFMT_X8R8G8B8, D3DUSAGE_DEPTHSTENCIL, D3DRTYPE_TEXTURE, format)))
13509 continue;
13511 hr = IDirect3DDevice9_CreateTexture(device, 1024, 1024, 1,
13512 D3DUSAGE_DEPTHSTENCIL, format, D3DPOOL_DEFAULT, &texture, NULL);
13513 ok(SUCCEEDED(hr), "CreateTexture failed, hr %#x.\n", hr);
13515 hr = IDirect3DTexture9_GetSurfaceLevel(texture, 0, &ds);
13516 ok(SUCCEEDED(hr), "GetSurfaceLevel failed, hr %#x.\n", hr);
13518 hr = IDirect3DDevice9_SetDepthStencilSurface(device, ds);
13519 ok(SUCCEEDED(hr), "SetDepthStencilSurface failed, hr %#x.\n", hr);
13521 hr = IDirect3DDevice9_SetRenderTarget(device, 0, rt);
13522 ok(SUCCEEDED(hr), "SetRenderTarget failed, hr %#x.\n", hr);
13524 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
13525 ok(SUCCEEDED(hr), "SetPixelShader failed, hr %#x.\n", hr);
13527 /* Setup the depth/stencil surface. */
13528 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_ZBUFFER, 0, 0.0f, 0);
13529 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
13531 hr = IDirect3DDevice9_BeginScene(device);
13532 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
13533 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
13534 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
13535 hr = IDirect3DDevice9_EndScene(device);
13536 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
13538 hr = IDirect3DDevice9_SetDepthStencilSurface(device, NULL);
13539 ok(SUCCEEDED(hr), "SetDepthStencilSurface failed, hr %#x.\n", hr);
13540 IDirect3DSurface9_Release(ds);
13542 hr = IDirect3DDevice9_SetRenderTarget(device, 0, original_rt);
13543 ok(SUCCEEDED(hr), "SetRenderTarget failed, hr %#x.\n", hr);
13545 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)texture);
13546 ok(SUCCEEDED(hr), "SetTexture failed, hr %#x.\n", hr);
13548 hr = IDirect3DDevice9_SetPixelShader(device, ps);
13549 ok(SUCCEEDED(hr), "SetPixelShader failed, hr %#x.\n", hr);
13551 /* Do the actual shadow mapping. */
13552 hr = IDirect3DDevice9_BeginScene(device);
13553 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
13554 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
13555 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
13556 hr = IDirect3DDevice9_EndScene(device);
13557 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
13559 hr = IDirect3DDevice9_SetTexture(device, 0, NULL);
13560 ok(SUCCEEDED(hr), "SetTexture failed, hr %#x.\n", hr);
13561 IDirect3DTexture9_Release(texture);
13563 for (j = 0; j < sizeof(expected_colors) / sizeof(*expected_colors); ++j)
13565 D3DCOLOR color = getPixelColor(device, expected_colors[j].x, expected_colors[j].y);
13566 ok(color_match(color, expected_colors[j].color, 0),
13567 "Expected color 0x%08x at (%u, %u) for format %s, got 0x%08x.\n",
13568 expected_colors[j].color, expected_colors[j].x, expected_colors[j].y,
13569 formats[i].name, color);
13572 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
13573 ok(SUCCEEDED(hr), "Present failed, hr %#x.\n", hr);
13576 IDirect3DPixelShader9_Release(ps);
13577 IDirect3DSurface9_Release(original_ds);
13578 IDirect3DSurface9_Release(original_rt);
13579 IDirect3DSurface9_Release(rt);
13580 refcount = IDirect3DDevice9_Release(device);
13581 ok(!refcount, "Device has %u references left.\n", refcount);
13582 done:
13583 IDirect3D9_Release(d3d);
13584 DestroyWindow(window);
13587 static void clip_planes(IDirect3DDevice9 *device, const char *test_name)
13589 static const struct
13591 struct vec3 position;
13592 DWORD diffuse;
13594 quad1[] =
13596 {{-1.0f, -1.0f, 0.0f}, 0xfff9e814},
13597 {{-1.0f, 1.0f, 0.0f}, 0xfff9e814},
13598 {{ 1.0f, -1.0f, 0.0f}, 0xfff9e814},
13599 {{ 1.0f, 1.0f, 0.0f}, 0xfff9e814},
13601 quad2[] =
13603 {{-1.0f, -1.0f, 0.0f}, 0xff002b7f},
13604 {{-1.0f, 1.0f, 0.0f}, 0xff002b7f},
13605 {{ 1.0f, -1.0f, 0.0f}, 0xff002b7f},
13606 {{ 1.0f, 1.0f, 0.0f}, 0xff002b7f},
13608 D3DCOLOR color;
13609 HRESULT hr;
13611 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xffffffff, 1.0, 0);
13612 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
13614 hr = IDirect3DDevice9_BeginScene(device);
13615 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
13617 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
13618 ok(SUCCEEDED(hr), "SetFVF failed, hr %#x.\n", hr);
13620 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_CLIPPLANEENABLE, 0);
13621 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
13622 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad1, sizeof(*quad1));
13623 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
13625 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_CLIPPLANEENABLE, 0x1);
13626 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
13627 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad2, sizeof(*quad2));
13628 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
13630 hr = IDirect3DDevice9_EndScene(device);
13631 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
13633 color = getPixelColor(device, 1, 240);
13634 ok(color_match(color, 0x00002b7f, 1), "%s test: color 0x%08x.\n", test_name, color);
13635 color = getPixelColor(device, 638, 240);
13636 ok(color_match(color, 0x00002b7f, 1), "%s test: color 0x%08x.\n", test_name, color);
13638 color = getPixelColor(device, 1, 241);
13639 ok(color_match(color, 0x00f9e814, 1), "%s test: color 0x%08x.\n", test_name, color);
13640 color = getPixelColor(device, 638, 241);
13641 ok(color_match(color, 0x00f9e814, 1), "%s test: color 0x%08x.\n", test_name, color);
13644 static void clip_planes_test(void)
13646 IDirect3DSurface9 *offscreen_surface, *original_rt;
13647 IDirect3DTexture9 *offscreen = NULL;
13648 IDirect3DVertexShader9 *shader;
13649 IDirect3DDevice9 *device;
13650 IDirect3D9 *d3d;
13651 ULONG refcount;
13652 D3DCAPS9 caps;
13653 HWND window;
13654 HRESULT hr;
13656 static const float plane0[4] = {0.0f, 1.0f, 0.0f, 0.5f / 480.0f}; /* a quarter-pixel offset */
13657 static const DWORD shader_code[] =
13659 0xfffe0200, /* vs_2_0 */
13660 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
13661 0x0200001f, 0x8000000a, 0x900f0001, /* dcl_color0 v1 */
13662 0x02000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
13663 0x02000001, 0xd00f0000, 0x90e40001, /* mov oD0, v1 */
13664 0x0000ffff /* end */
13667 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
13668 0, 0, 640, 480, NULL, NULL, NULL, NULL);
13669 d3d = Direct3DCreate9(D3D_SDK_VERSION);
13670 ok(!!d3d, "Failed to create a D3D object.\n");
13671 if (!(device = create_device(d3d, window, window, TRUE)))
13673 skip("Failed to create a D3D device, skipping tests.\n");
13674 goto done;
13677 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
13678 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
13679 if (caps.VertexShaderVersion < D3DVS_VERSION(2, 0))
13681 skip("No vs_2_0 support, skipping tests.\n");
13682 IDirect3DDevice9_Release(device);
13683 goto done;
13686 hr = IDirect3DDevice9_GetRenderTarget(device, 0, &original_rt);
13687 ok(SUCCEEDED(hr), "GetRenderTarget failed, hr %#x.\n", hr);
13689 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
13690 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
13691 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, FALSE);
13692 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
13693 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, FALSE);
13694 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
13695 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_CLIPPING, TRUE);
13696 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
13698 hr = IDirect3DDevice9_SetVertexShader(device, NULL);
13699 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexShader failed, hr=%08x\n", hr);
13700 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
13701 ok(hr == D3D_OK, "IDirect3DDevice9_SetPixelShader failed, hr=%08x\n", hr);
13703 IDirect3DDevice9_SetClipPlane(device, 0, plane0);
13705 clip_planes(device, "Onscreen FFP");
13707 hr = IDirect3DDevice9_CreateTexture(device, 640, 480, 1, D3DUSAGE_RENDERTARGET, D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &offscreen, NULL);
13708 ok(SUCCEEDED(hr), "CreateTexture failed, hr %#x.\n", hr);
13709 hr = IDirect3DTexture9_GetSurfaceLevel(offscreen, 0, &offscreen_surface);
13710 ok(SUCCEEDED(hr), "GetSurfaceLevel failed, hr %#x.\n", hr);
13711 hr = IDirect3DDevice9_SetRenderTarget(device, 0, offscreen_surface);
13712 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderTarget failed, hr=%08x\n", hr);
13714 clip_planes(device, "Offscreen FFP");
13716 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
13717 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
13719 hr = IDirect3DDevice9_CreateVertexShader(device, shader_code, &shader);
13720 ok(hr == D3D_OK, "IDirect3DDevice9_CreateVertexShader returned %08x\n", hr);
13721 hr = IDirect3DDevice9_SetVertexShader(device, shader);
13722 ok(hr == D3D_OK, "IDirect3DDevice9_SetVertexShader returned %08x\n", hr);
13724 hr = IDirect3DDevice9_SetRenderTarget(device, 0, original_rt);
13725 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderTarget failed, hr=%08x\n", hr);
13727 clip_planes(device, "Onscreen vertex shader");
13729 hr = IDirect3DDevice9_SetRenderTarget(device, 0, offscreen_surface);
13730 ok(hr == D3D_OK, "IDirect3DDevice9_SetRenderTarget failed, hr=%08x\n", hr);
13732 clip_planes(device, "Offscreen vertex shader");
13734 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
13735 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
13737 IDirect3DVertexShader9_Release(shader);
13738 IDirect3DSurface9_Release(original_rt);
13739 IDirect3DSurface9_Release(offscreen_surface);
13740 IDirect3DTexture9_Release(offscreen);
13741 refcount = IDirect3DDevice9_Release(device);
13742 ok(!refcount, "Device has %u references left.\n", refcount);
13743 done:
13744 IDirect3D9_Release(d3d);
13745 DestroyWindow(window);
13748 static void fp_special_test(void)
13750 /* Microsoft's assembler generates nan and inf with "1.#QNAN" and "1.#INF." respectively */
13751 static const DWORD vs_header[] =
13753 0xfffe0200, /* vs_2_0 */
13754 0x05000051, 0xa00f0000, 0x00000000, 0x3f000000, 0x3f800000, 0x40000000, /* def c0, 0.0, 0.5, 1.0, 2.0 */
13755 0x05000051, 0xa00f0001, 0x7fc00000, 0xff800000, 0x7f800000, 0x00000000, /* def c1, nan, -inf, inf, 0 */
13756 0x0200001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
13757 0x0200001f, 0x80000005, 0x900f0001, /* dcl_texcoord0 v1 */
13760 static const DWORD vs_log[] = {0x0200000f, 0x80010000, 0x90000001}; /* log r0.x, v1.x */
13761 static const DWORD vs_pow[] =
13762 {0x03000020, 0x80010000, 0x90000001, 0x90000001}; /* pow r0.x, v1.x, v1.x */
13763 static const DWORD vs_nrm[] = {0x02000024, 0x80070000, 0x90000001}; /* nrm r0.xyz, v1.x */
13764 static const DWORD vs_rcp1[] = {0x02000006, 0x80010000, 0x90000001}; /* rcp r0.x, v1.x */
13765 static const DWORD vs_rcp2[] = {0x02000006, 0x80010000, 0x91000001}; /* rcp r0.x, -v1.x */
13766 static const DWORD vs_rsq1[] = {0x02000007, 0x80010000, 0x90000001}; /* rsq r0.x, v1.x */
13767 static const DWORD vs_rsq2[] = {0x02000007, 0x80010000, 0x91000001}; /* rsq r0.x, -v1.x */
13768 static const DWORD vs_lit[] = {0x02000010, 0x800f0000, 0x90000001, /* lit r0, v1.xxxx */
13769 0x02000001, 0x80010000, 0x80aa0000}; /* mov r0.x, v0.z */
13770 static const DWORD vs_def1[] = {0x02000001, 0x80010000, 0xa0000001}; /* mov r0.x, c1.x */
13771 static const DWORD vs_def2[] = {0x02000001, 0x80010000, 0xa0550001}; /* mov r0.x, c1.y */
13772 static const DWORD vs_def3[] = {0x02000001, 0x80010000, 0xa0aa0001}; /* mov r0.x, c1.z */
13774 static const DWORD vs_footer[] =
13776 0x03000005, 0x80020000, 0x80000000, 0xa0ff0000, /* mul r0.y, r0.x, c0.w */
13777 0x0300000d, 0x80040000, 0x80000000, 0x80550000, /* sge r0.z, r0.x, r0.y */
13778 0x0300000d, 0x80020000, 0x80e40000, 0x80000000, /* sge r0.y, r0, r0.x */
13779 0x03000005, 0x80040000, 0x80550000, 0x80e40000, /* mul r0.z, r0.y, r0 */
13780 0x0300000b, 0x80080000, 0x81aa0000, 0x80aa0000, /* max r0.w, -r0.z, r0.z */
13781 0x0300000c, 0x80020000, 0x80000000, 0x80000000, /* slt r0.y, r0.x, r0.x */
13782 0x03000002, 0x80040000, 0x80550000, 0x80550000, /* add r0.z, r0.y, r0.y */
13783 0x0300000c, 0x80020000, 0xa0000000, 0x80ff0000, /* slt r0.y, c0.x, r0.w */
13784 0x0300000b, 0x80080000, 0x81aa0000, 0x80aa0000, /* max r0.w, -r0.z, r0.z */
13785 0x03000002, 0x80040000, 0x81550000, 0xa0e40000, /* add r0.z, -r0.y, c0 */
13786 0x0300000c, 0x80080000, 0xa0000000, 0x80e40000, /* slt r0.w, c0.x, r0 */
13787 0x03000005, 0x80040000, 0x80ff0000, 0x80e40000, /* mul r0.z, r0.w, r0 */
13788 0x04000004, 0x80020000, 0x80aa0000, 0xa0e40000, 0x80e40000, /* mad r0.y, r0.z, c0, r0 */
13789 0x02000001, 0xe0030000, 0x80e40000, /* mov oT0.xy, r0 */
13790 0x02000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
13791 0x0000ffff, /* end */
13794 static const struct
13796 const char *name;
13797 const DWORD *ops;
13798 DWORD size;
13799 D3DCOLOR r500;
13800 D3DCOLOR r600;
13801 D3DCOLOR nv40;
13802 D3DCOLOR nv50;
13803 D3DCOLOR warp;
13805 vs_body[] =
13807 /* The basic ideas here are:
13808 * 2.0 * +/-INF == +/-INF
13809 * NAN != NAN
13811 * The vertex shader value is written to the red component, with 0.0
13812 * and +/-INF mapping to 0xff, and NAN to 0x7f. Anything else should
13813 * result in 0x00. The pixel shader value is written to the green
13814 * component, but here 0.0 also results in 0x00. The actual value is
13815 * written to the blue component.
13817 * There are considerable differences between graphics cards in how
13818 * these are handled, but pow and nrm never generate INF or NAN on
13819 * real hardware. */
13820 {"log", vs_log, sizeof(vs_log), 0x00000000, 0x00000000, 0x00ff0000, 0x00ff7f00, 0x00ff8000},
13821 {"pow", vs_pow, sizeof(vs_pow), 0x000000ff, 0x000000ff, 0x0000ff00, 0x000000ff, 0x00008000},
13822 {"nrm", vs_nrm, sizeof(vs_nrm), 0x00ff0000, 0x00ff0000, 0x0000ff00, 0x00ff0000, 0x00008000},
13823 {"rcp1", vs_rcp1, sizeof(vs_rcp1), 0x000000ff, 0x000000ff, 0x00ff00ff, 0x00ff7f00, 0x00ff8000},
13824 {"rcp2", vs_rcp2, sizeof(vs_rcp2), 0x000000ff, 0x00000000, 0x00ff0000, 0x00ff7f00, 0x00ff8000},
13825 {"rsq1", vs_rsq1, sizeof(vs_rsq1), 0x000000ff, 0x000000ff, 0x00ff00ff, 0x00ff7f00, 0x00ff8000},
13826 {"rsq2", vs_rsq2, sizeof(vs_rsq2), 0x000000ff, 0x000000ff, 0x00ff00ff, 0x00ff7f00, 0x00ff8000},
13827 {"lit", vs_lit, sizeof(vs_lit), 0x00ff0000, 0x00ff0000, 0x00ff0000, 0x00ff0000, 0x00ff0000},
13828 {"def1", vs_def1, sizeof(vs_def1), 0x000000ff, 0x00007f00, 0x0000ff00, 0x00007f00, 0x00008000},
13829 {"def2", vs_def2, sizeof(vs_def2), 0x00ff0000, 0x00ff7f00, 0x00ff0000, 0x00ff7f00, 0x00ff8000},
13830 {"def3", vs_def3, sizeof(vs_def3), 0x00ff00ff, 0x00ff7f00, 0x00ff00ff, 0x00ff7f00, 0x00ff8000},
13833 static const DWORD ps_code[] =
13835 0xffff0200, /* ps_2_0 */
13836 0x05000051, 0xa00f0000, 0x00000000, 0x3f000000, 0x3f800000, 0x40000000, /* def c0, 0.0, 0.5, 1.0, 2.0 */
13837 0x0200001f, 0x80000000, 0xb0030000, /* dcl t0.xy */
13838 0x0300000b, 0x80010001, 0xb0e40000, 0xa0e40000, /* max r1.x, t0, c0 */
13839 0x0300000a, 0x80010000, 0xb0e40000, 0xa0e40000, /* min r0.x, t0, c0 */
13840 0x03000002, 0x80010000, 0x80e40000, 0x81e40001, /* add r0.x, r0, -r1 */
13841 0x04000004, 0x80010001, 0xb0e40000, 0xa0ff0000, 0xb1e40000, /* mad r1.x, t0, c0.w. -t0 */
13842 0x02000023, 0x80010002, 0x80e40001, /* abs r2.x, r1 */
13843 0x02000023, 0x80010000, 0x80e40000, /* abs r0.x, r0 */
13844 0x02000023, 0x80010001, 0xb0e40000, /* abs r1.x, t0 */
13845 0x04000058, 0x80010002, 0x81e40002, 0xa0aa0000, 0xa0e40000, /* cmp r2.x, -r2, c0.z, c0 */
13846 0x02000023, 0x80010002, 0x80e40002, /* abs r2.x, r2 */
13847 0x04000058, 0x80010001, 0x81e40001, 0xa0aa0000, 0xa0e40000, /* cmp r1.x, -r1, c0.z, c0 */
13848 0x02000023, 0x80010001, 0x80e40001, /* abs r1.x, r1 */
13849 0x04000058, 0x80010003, 0x81e40002, 0xa0aa0000, 0xa0e40000, /* cmp r3.x, -r2, c0.z, c0 */
13850 0x04000058, 0x80010002, 0x81e40001, 0xa0aa0000, 0xa0e40000, /* cmp r2.x, -r1, c0.z, c0 */
13851 0x04000058, 0x80010000, 0x81e40000, 0xa0550000, 0xa0e40000, /* cmp r0.x, -r0, c0.y, c0 */
13852 0x03000005, 0x80010002, 0x80e40002, 0x80e40003, /* mul r2.x, r2, r3 */
13853 0x04000058, 0x80010000, 0x81e40002, 0xa0aa0000, 0x80e40000, /* cmp r0.x, -r2, c0.z, r0 */
13854 0x04000058, 0x80020000, 0x81000001, 0x80000000, 0xa0000000, /* cmp r0.y, -r1.x, r0.x, c0.x */
13855 0x02000001, 0x80050000, 0xb0c90000, /* mov r0.xz, t0.yzxw */
13856 0x02000001, 0x80080000, 0xa0aa0000, /* mov r0.w, c0.z */
13857 0x02000001, 0x800f0800, 0x80e40000, /* mov oC0, r0 */
13858 0x0000ffff, /* end */
13861 struct
13863 float x, y, z;
13864 float s;
13866 quad[] =
13868 { -1.0f, 1.0f, 0.0f, 0.0f},
13869 { 1.0f, 1.0f, 1.0f, 0.0f},
13870 { -1.0f, -1.0f, 0.0f, 0.0f},
13871 { 1.0f, -1.0f, 1.0f, 0.0f},
13874 IDirect3DPixelShader9 *ps;
13875 IDirect3DDevice9 *device;
13876 UINT body_size = 0;
13877 IDirect3D9 *d3d;
13878 DWORD *vs_code;
13879 ULONG refcount;
13880 D3DCAPS9 caps;
13881 HWND window;
13882 HRESULT hr;
13883 UINT i;
13885 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
13886 0, 0, 640, 480, NULL, NULL, NULL, NULL);
13887 d3d = Direct3DCreate9(D3D_SDK_VERSION);
13888 ok(!!d3d, "Failed to create a D3D object.\n");
13889 if (!(device = create_device(d3d, window, window, TRUE)))
13891 skip("Failed to create a D3D device, skipping tests.\n");
13892 goto done;
13895 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
13896 ok(SUCCEEDED(hr), "GetDeviceCaps failed, hr %#x.\n", hr);
13897 if (caps.PixelShaderVersion < D3DPS_VERSION(2, 0) || caps.VertexShaderVersion < D3DVS_VERSION(2, 0))
13899 skip("No shader model 2.0 support, skipping floating point specials test.\n");
13900 IDirect3DDevice9_Release(device);
13901 goto done;
13904 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1 | D3DFVF_TEXCOORDSIZE1(0));
13905 ok(SUCCEEDED(hr), "SetFVF failed, hr %#x.\n", hr);
13907 hr = IDirect3DDevice9_CreatePixelShader(device, ps_code, &ps);
13908 ok(SUCCEEDED(hr), "CreatePixelShader failed, hr %#x.\n", hr);
13909 hr = IDirect3DDevice9_SetPixelShader(device, ps);
13910 ok(SUCCEEDED(hr), "SetPixelShader failed, hr %#x.\n", hr);
13912 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, D3DZB_FALSE);
13913 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
13915 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff00ff00, 0.0f, 0);
13916 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
13918 for (i = 0; i < sizeof(vs_body) / sizeof(*vs_body); ++i)
13920 if (vs_body[i].size > body_size) body_size = vs_body[i].size;
13923 vs_code = HeapAlloc(GetProcessHeap(), 0, sizeof(vs_header) + body_size + sizeof(vs_footer));
13924 memcpy(vs_code, vs_header, sizeof(vs_header));
13926 for (i = 0; i < sizeof(vs_body) / sizeof(*vs_body); ++i)
13928 DWORD offset = sizeof(vs_header) / sizeof(*vs_header);
13929 IDirect3DVertexShader9 *vs;
13930 D3DCOLOR color;
13932 memcpy(vs_code + offset, vs_body[i].ops, vs_body[i].size);
13933 offset += vs_body[i].size / sizeof(*vs_body[i].ops);
13934 memcpy(vs_code + offset, vs_footer, sizeof(vs_footer));
13936 hr = IDirect3DDevice9_CreateVertexShader(device, vs_code, &vs);
13937 ok(SUCCEEDED(hr), "CreateVertexShader failed, hr %#x.\n", hr);
13938 hr = IDirect3DDevice9_SetVertexShader(device, vs);
13939 ok(SUCCEEDED(hr), "SetVertexShader failed, hr %#x.\n", hr);
13941 hr = IDirect3DDevice9_BeginScene(device);
13942 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
13943 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
13944 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
13945 hr = IDirect3DDevice9_EndScene(device);
13946 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
13948 color = getPixelColor(device, 320, 240);
13949 ok(color_match(color, vs_body[i].r500, 1)
13950 || color_match(color, vs_body[i].r600, 1)
13951 || color_match(color, vs_body[i].nv40, 1)
13952 || color_match(color, vs_body[i].nv50, 1)
13953 || broken(color_match(color, vs_body[i].warp, 1)),
13954 "Expected color 0x%08x, 0x%08x, 0x%08x or 0x%08x for instruction \"%s\", got 0x%08x.\n",
13955 vs_body[i].r500, vs_body[i].r600, vs_body[i].nv40, vs_body[i].nv50, vs_body[i].name, color);
13957 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
13958 ok(SUCCEEDED(hr), "Present failed, hr %#x.\n", hr);
13960 hr = IDirect3DDevice9_SetVertexShader(device, NULL);
13961 ok(SUCCEEDED(hr), "SetVertexShader failed, hr %#x.\n", hr);
13962 IDirect3DVertexShader9_Release(vs);
13965 HeapFree(GetProcessHeap(), 0, vs_code);
13967 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
13968 ok(SUCCEEDED(hr), "SetPixelShader failed, hr %#x.\n", hr);
13969 IDirect3DPixelShader9_Release(ps);
13970 refcount = IDirect3DDevice9_Release(device);
13971 ok(!refcount, "Device has %u references left.\n", refcount);
13972 done:
13973 IDirect3D9_Release(d3d);
13974 DestroyWindow(window);
13977 static void srgbwrite_format_test(void)
13979 IDirect3D9 *d3d;
13980 IDirect3DSurface9 *rt, *backbuffer;
13981 IDirect3DTexture9 *texture;
13982 IDirect3DDevice9 *device;
13983 ULONG refcount;
13984 HWND window;
13985 HRESULT hr;
13986 int i;
13987 DWORD color_rgb = 0x00808080, color_srgb = 0x00bcbcbc, color;
13988 static const struct
13990 D3DFORMAT fmt;
13991 const char *name;
13993 formats[] =
13995 { D3DFMT_R5G6B5, "D3DFMT_R5G6B5" },
13996 { D3DFMT_X8R8G8B8, "D3DFMT_X8R8G8B8" },
13997 { D3DFMT_A8R8G8B8, "D3DFMT_A8R8G8B8" },
13998 { D3DFMT_A16B16G16R16F, "D3DFMT_A16B16G16R16F" },
13999 { D3DFMT_A32B32G32R32F, "D3DFMT_A32B32G32R32F" },
14001 static const struct
14003 float x, y, z;
14004 float u, v;
14006 quad[] =
14008 {-1.0f, -1.0f, 0.1f, 0.0f, 0.0f},
14009 {-1.0f, 1.0f, 0.1f, 1.0f, 0.0f},
14010 { 1.0f, -1.0f, 0.1f, 0.0f, 1.0f},
14011 { 1.0f, 1.0f, 0.1f, 1.0f, 1.0f}
14014 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
14015 0, 0, 640, 480, NULL, NULL, NULL, NULL);
14016 d3d = Direct3DCreate9(D3D_SDK_VERSION);
14017 ok(!!d3d, "Failed to create a D3D object.\n");
14018 if (!(device = create_device(d3d, window, window, TRUE)))
14020 skip("Failed to create a D3D device, skipping tests.\n");
14021 goto done;
14024 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1);
14025 ok(SUCCEEDED(hr), "SetFVF failed, hr %#x.\n", hr);
14026 hr = IDirect3DDevice9_GetBackBuffer(device, 0, 0, D3DBACKBUFFER_TYPE_MONO, &backbuffer);
14027 ok(SUCCEEDED(hr), "GetBackBuffer failed, hr %#x.\n", hr);
14028 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
14029 ok(SUCCEEDED(hr), "SetTextureStageState failed, hr %#x.\n", hr);
14030 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_TEXTUREFACTOR, 0x80808080);
14031 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
14033 for(i = 0; i < (sizeof(formats) / sizeof(*formats)); i++)
14035 if (FAILED(IDirect3D9_CheckDeviceFormat(d3d, D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, D3DFMT_X8R8G8B8,
14036 D3DUSAGE_RENDERTARGET, D3DRTYPE_TEXTURE, formats[i].fmt)))
14038 skip("Format %s not supported as render target, skipping test.\n",
14039 formats[i].name);
14040 continue;
14043 hr = IDirect3DDevice9_CreateTexture(device, 8, 8, 1, D3DUSAGE_RENDERTARGET,
14044 formats[i].fmt, D3DPOOL_DEFAULT, &texture, NULL);
14045 ok(SUCCEEDED(hr), "CreateTexture failed, hr %#x.\n", hr);
14046 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x00ff0000, 1.0f, 0);
14047 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
14049 hr = IDirect3DTexture9_GetSurfaceLevel(texture, 0, &rt);
14050 ok(SUCCEEDED(hr), "GetSurfaceLevel failed, hr %#x.\n", hr);
14051 hr = IDirect3DDevice9_SetRenderTarget(device, 0, rt);
14052 ok(SUCCEEDED(hr), "SetRenderTarget failed, hr %#x.\n", hr);
14053 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0x000000ff, 0.0f, 0);
14054 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
14056 hr = IDirect3DDevice9_BeginScene(device);
14057 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
14059 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_SRGBWRITEENABLE, TRUE);
14060 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
14061 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_TFACTOR);
14062 ok(SUCCEEDED(hr), "Failed to set texture stage state, hr %#x.\n", hr);
14063 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
14064 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
14066 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_SRGBWRITEENABLE, FALSE);
14067 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
14068 hr = IDirect3DDevice9_SetRenderTarget(device, 0, backbuffer);
14069 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
14070 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *) texture);
14071 ok(SUCCEEDED(hr), "Failed to set texture, hr %#x.\n", hr);
14072 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
14073 ok(SUCCEEDED(hr), "Failed to set texture stage state, hr %#x.\n", hr);
14074 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
14075 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
14076 hr = IDirect3DDevice9_SetTexture(device, 0, NULL);
14077 ok(SUCCEEDED(hr), "Failed to set texture, hr %#x.\n", hr);
14079 hr = IDirect3DDevice9_EndScene(device);
14080 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
14082 IDirect3DSurface9_Release(rt);
14083 IDirect3DTexture9_Release(texture);
14085 color = getPixelColor(device, 360, 240);
14086 if(IDirect3D9_CheckDeviceFormat(d3d, 0, D3DDEVTYPE_HAL, D3DFMT_X8R8G8B8,
14087 D3DUSAGE_QUERY_SRGBWRITE,
14088 D3DRTYPE_TEXTURE, formats[i].fmt) == D3D_OK)
14090 /* Big slop for R5G6B5 */
14091 ok(color_match(color, color_srgb, 5), "Format %s supports srgb, expected color 0x%08x, got 0x%08x\n",
14092 formats[i].name, color_srgb, color);
14094 else
14096 /* Big slop for R5G6B5 */
14097 ok(color_match(color, color_rgb, 5), "Format %s does not support srgb, expected color 0x%08x, got 0x%08x\n",
14098 formats[i].name, color_rgb, color);
14101 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
14102 ok(SUCCEEDED(hr), "Present failed, hr %#x.\n", hr);
14105 IDirect3DSurface9_Release(backbuffer);
14106 refcount = IDirect3DDevice9_Release(device);
14107 ok(!refcount, "Device has %u references left.\n", refcount);
14108 done:
14109 IDirect3D9_Release(d3d);
14110 DestroyWindow(window);
14113 static void ds_size_test(void)
14115 IDirect3DSurface9 *ds, *rt, *old_rt, *old_ds, *readback;
14116 IDirect3DDevice9 *device;
14117 DWORD num_passes;
14118 IDirect3D9 *d3d;
14119 ULONG refcount;
14120 HWND window;
14121 HRESULT hr;
14123 static const struct
14125 float x, y, z;
14127 quad[] =
14129 {-1.0f, -1.0f, 0.0f},
14130 {-1.0f, 1.0f, 0.0f},
14131 { 1.0f, -1.0f, 0.0f},
14132 { 1.0f, 1.0f, 0.0f},
14135 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
14136 0, 0, 640, 480, NULL, NULL, NULL, NULL);
14137 d3d = Direct3DCreate9(D3D_SDK_VERSION);
14138 ok(!!d3d, "Failed to create a D3D object.\n");
14139 if (!(device = create_device(d3d, window, window, TRUE)))
14141 skip("Failed to create a D3D device, skipping tests.\n");
14142 goto done;
14145 hr = IDirect3DDevice9_CreateRenderTarget(device, 64, 64, D3DFMT_A8R8G8B8, D3DMULTISAMPLE_NONE, 0, FALSE, &rt, NULL);
14146 ok(SUCCEEDED(hr), "IDirect3DDevice9_CreateRenderTarget failed, hr %#x.\n", hr);
14147 hr = IDirect3DDevice9_CreateDepthStencilSurface(device, 32, 32, D3DFMT_D24X8, D3DMULTISAMPLE_NONE, 0, TRUE, &ds, NULL);
14148 ok(SUCCEEDED(hr), "IDirect3DDevice9_CreateDepthStencilSurface failed, hr %#x.\n", hr);
14149 hr = IDirect3DDevice9_CreateOffscreenPlainSurface(device, 64, 64, D3DFMT_A8R8G8B8, D3DPOOL_SYSTEMMEM, &readback, NULL);
14150 ok(SUCCEEDED(hr), "IDirect3DDevice9_CreateOffscreenPlainSurface failed, hr %#x.\n", hr);
14152 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ);
14153 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
14155 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, FALSE);
14156 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetRenderState failed, hr %#x.\n", hr);
14157 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_STENCILENABLE, FALSE);
14158 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetRenderState failed, hr %#x.\n", hr);
14159 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, FALSE);
14160 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetRenderState failed, hr %#x.\n", hr);
14161 hr = IDirect3DDevice9_ValidateDevice(device, &num_passes);
14162 ok(SUCCEEDED(hr), "IDirect3DDevice9_ValidateDevice failed, hr %#x.\n", hr);
14163 hr = IDirect3DDevice9_GetRenderTarget(device, 0, &old_rt);
14164 ok(SUCCEEDED(hr), "IDirect3DDevice9_GetRenderTarget failed, hr %#x.\n", hr);
14165 hr = IDirect3DDevice9_GetDepthStencilSurface(device, &old_ds);
14166 ok(SUCCEEDED(hr), "IDirect3DDevice9_GetDepthStencilSurface failed, hr %#x.\n", hr);
14167 hr = IDirect3DDevice9_SetRenderTarget(device, 0, rt);
14168 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetRenderTarget failed, hr %#x.\n", hr);
14169 hr = IDirect3DDevice9_SetDepthStencilSurface(device, ds);
14170 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetDepthStencilSurface failed, hr %#x.\n", hr);
14171 hr = IDirect3DDevice9_ValidateDevice(device, &num_passes);
14172 ok(SUCCEEDED(hr), "IDirect3DDevice9_ValidateDevice failed, hr %#x.\n", hr);
14174 /* The D3DCLEAR_TARGET clear works. D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER returns OK,
14175 * but does not change the surface's contents. */
14176 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0x000000FF, 0.0f, 0);
14177 ok(SUCCEEDED(hr), "Target clear failed, hr %#x.\n", hr);
14178 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_ZBUFFER, 0x00000000, 0.2f, 0);
14179 ok(SUCCEEDED(hr), "Z Buffer clear failed, hr %#x.\n", hr);
14180 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x00ff0000, 0.5f, 0);
14181 ok(SUCCEEDED(hr), "Target and Z Buffer clear failed, hr %#x.\n", hr);
14183 /* Nvidia does not clear the surface(The color is still 0x000000ff), AMD does(the color is 0x00ff0000) */
14185 /* Turning on any depth-related state results in a ValidateDevice failure */
14186 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, D3DZB_TRUE);
14187 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetRenderState failed, hr %#x.\n", hr);
14188 hr = IDirect3DDevice9_ValidateDevice(device, &num_passes);
14189 ok(hr == D3DERR_CONFLICTINGRENDERSTATE || hr == D3D_OK, "IDirect3DDevice9_ValidateDevice returned %#x, expected "
14190 "D3DERR_CONFLICTINGRENDERSTATE.\n", hr);
14191 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, D3DZB_FALSE);
14192 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetRenderState failed, hr %#x.\n", hr);
14193 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, TRUE);
14194 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetRenderState failed, hr %#x.\n", hr);
14195 hr = IDirect3DDevice9_ValidateDevice(device, &num_passes);
14196 ok(hr == D3DERR_CONFLICTINGRENDERSTATE || hr == D3D_OK, "IDirect3DDevice9_ValidateDevice returned %#x, expected "
14197 "D3DERR_CONFLICTINGRENDERSTATE.\n", hr);
14199 /* Try to draw with the device in an invalid state. */
14200 hr = IDirect3DDevice9_BeginScene(device);
14201 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
14202 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
14203 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
14204 hr = IDirect3DDevice9_EndScene(device);
14205 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
14207 /* Don't check the resulting draw unless we find an app that needs it. On
14208 * NVIDIA ValidateDevice() returns CONFLICTINGRENDERSTATE, so the result
14209 * is undefined. On AMD D3D seems to assume the stored Z buffer value is
14210 * 0.0 for all pixels, even those that are covered by the depth buffer. */
14212 hr = IDirect3DDevice9_SetRenderTarget(device, 0, old_rt);
14213 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetRenderTarget failed, hr %#x.\n", hr);
14214 hr = IDirect3DDevice9_SetDepthStencilSurface(device, old_ds);
14215 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetDepthStencilSurface failed, hr %#x.\n", hr);
14216 hr = IDirect3DDevice9_ValidateDevice(device, &num_passes);
14217 ok(SUCCEEDED(hr), "IDirect3DDevice9_ValidateDevice failed, hr %#x.\n", hr);
14219 IDirect3DSurface9_Release(readback);
14220 IDirect3DSurface9_Release(ds);
14221 IDirect3DSurface9_Release(rt);
14222 IDirect3DSurface9_Release(old_rt);
14223 IDirect3DSurface9_Release(old_ds);
14224 refcount = IDirect3DDevice9_Release(device);
14225 ok(!refcount, "Device has %u references left.\n", refcount);
14226 done:
14227 IDirect3D9_Release(d3d);
14228 DestroyWindow(window);
14231 static void unbound_sampler_test(void)
14233 IDirect3DPixelShader9 *ps, *ps_cube, *ps_volume;
14234 IDirect3DSurface9 *rt, *old_rt;
14235 IDirect3DDevice9 *device;
14236 IDirect3D9 *d3d;
14237 ULONG refcount;
14238 D3DCAPS9 caps;
14239 DWORD color;
14240 HWND window;
14241 HRESULT hr;
14243 static const DWORD ps_code[] =
14245 0xffff0200, /* ps_2_0 */
14246 0x0200001f, 0x90000000, 0xa00f0800, /* dcl_2d s0 */
14247 0x0200001f, 0x80000000, 0xb00f0000, /* dcl t0 */
14248 0x03000042, 0x800f0000, 0xb0e40000, 0xa0e40800, /* texld r0, t0, s0 */
14249 0x02000001, 0x800f0800, 0x80e40000, /* mov oC0, r0 */
14250 0x0000ffff, /* end */
14252 static const DWORD ps_code_cube[] =
14254 0xffff0200, /* ps_2_0 */
14255 0x0200001f, 0x98000000, 0xa00f0800, /* dcl_cube s0 */
14256 0x0200001f, 0x80000000, 0xb00f0000, /* dcl t0 */
14257 0x03000042, 0x800f0000, 0xb0e40000, 0xa0e40800, /* texld r0, t0, s0 */
14258 0x02000001, 0x800f0800, 0x80e40000, /* mov oC0, r0 */
14259 0x0000ffff, /* end */
14261 static const DWORD ps_code_volume[] =
14263 0xffff0200, /* ps_2_0 */
14264 0x0200001f, 0xa0000000, 0xa00f0800, /* dcl_volume s0 */
14265 0x0200001f, 0x80000000, 0xb00f0000, /* dcl t0 */
14266 0x03000042, 0x800f0000, 0xb0e40000, 0xa0e40800, /* texld r0, t0, s0 */
14267 0x02000001, 0x800f0800, 0x80e40000, /* mov oC0, r0 */
14268 0x0000ffff, /* end */
14271 static const struct
14273 float x, y, z;
14274 float u, v;
14276 quad[] =
14278 {-1.0f, -1.0f, 0.1f, 0.0f, 0.0f},
14279 {-1.0f, 1.0f, 0.1f, 1.0f, 0.0f},
14280 { 1.0f, -1.0f, 0.1f, 0.0f, 1.0f},
14281 { 1.0f, 1.0f, 0.1f, 1.0f, 1.0f}
14284 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
14285 0, 0, 640, 480, NULL, NULL, NULL, NULL);
14286 d3d = Direct3DCreate9(D3D_SDK_VERSION);
14287 ok(!!d3d, "Failed to create a D3D object.\n");
14288 if (!(device = create_device(d3d, window, window, TRUE)))
14290 skip("Failed to create a D3D device, skipping tests.\n");
14291 goto done;
14294 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
14295 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
14296 if (caps.PixelShaderVersion < D3DPS_VERSION(2, 0))
14298 skip("No ps_2_0 support, skipping tests.\n");
14299 IDirect3DDevice9_Release(device);
14300 goto done;
14302 if (!(caps.TextureCaps & D3DPTEXTURECAPS_CUBEMAP) || !(caps.TextureCaps & D3DPTEXTURECAPS_VOLUMEMAP))
14304 skip("No cube / volume texture support, skipping tests.\n");
14305 IDirect3DDevice9_Release(device);
14306 goto done;
14309 hr = IDirect3DDevice9_SetTexture(device, 0, NULL);
14310 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetTextureStage failed, %#x.\n", hr);
14312 hr = IDirect3DDevice9_CreatePixelShader(device, ps_code, &ps);
14313 ok(SUCCEEDED(hr), "IDirect3DDevice9_CreatePixelShader failed, hr %#x.\n", hr);
14314 hr = IDirect3DDevice9_CreatePixelShader(device, ps_code_cube, &ps_cube);
14315 ok(SUCCEEDED(hr), "IDirect3DDevice9_CreatePixelShader failed, hr %#x.\n", hr);
14316 hr = IDirect3DDevice9_CreatePixelShader(device, ps_code_volume, &ps_volume);
14317 ok(SUCCEEDED(hr), "IDirect3DDevice9_CreatePixelShader failed, hr %#x.\n", hr);
14319 hr = IDirect3DDevice9_CreateRenderTarget(device, 64, 64, D3DFMT_A8R8G8B8, D3DMULTISAMPLE_NONE, 0, TRUE, &rt, NULL);
14320 ok(SUCCEEDED(hr), "IDirect3DDevice9_CreateRenderTarget failed, hr %#x.\n", hr);
14322 hr = IDirect3DDevice9_GetRenderTarget(device, 0, &old_rt);
14323 ok(SUCCEEDED(hr), "IDirect3DDevice9_GetRenderTarget failed, hr %#x.\n", hr);
14325 hr = IDirect3DDevice9_SetRenderTarget(device, 0, rt);
14326 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetRenderTarget failed, hr %#x.\n", hr);
14328 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1 );
14329 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetFVF failed, hr %#x.\n", hr);
14331 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x56ffffff, 1.0f, 0);
14332 ok(SUCCEEDED(hr), "IDirect3DDevice9_Clear failed, hr %#x.\n", hr);
14334 hr = IDirect3DDevice9_SetPixelShader(device, ps);
14335 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetPixelShader failed, hr %#x.\n", hr);
14337 hr = IDirect3DDevice9_BeginScene(device);
14338 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
14339 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
14340 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
14341 hr = IDirect3DDevice9_EndScene(device);
14342 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
14344 color = getPixelColorFromSurface(rt, 32, 32);
14345 ok(color == 0xff000000, "Unbound sampler color is %#x.\n", color);
14347 /* Now try with a cube texture */
14348 hr = IDirect3DDevice9_SetPixelShader(device, ps_cube);
14349 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetPixelShader failed, hr %#x.\n", hr);
14351 hr = IDirect3DDevice9_BeginScene(device);
14352 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
14353 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
14354 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
14355 hr = IDirect3DDevice9_EndScene(device);
14356 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
14358 color = getPixelColorFromSurface(rt, 32, 32);
14359 ok(color == 0xff000000, "Unbound sampler color is %#x.\n", color);
14361 /* And then with a volume texture */
14362 hr = IDirect3DDevice9_SetPixelShader(device, ps_volume);
14363 ok(SUCCEEDED(hr), "IDirect3DDevice9_SetPixelShader failed, hr %#x.\n", hr);
14365 hr = IDirect3DDevice9_BeginScene(device);
14366 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
14367 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
14368 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
14369 hr = IDirect3DDevice9_EndScene(device);
14370 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
14372 color = getPixelColorFromSurface(rt, 32, 32);
14373 ok(color == 0xff000000, "Unbound sampler color is %#x.\n", color);
14375 IDirect3DSurface9_Release(rt);
14376 IDirect3DSurface9_Release(old_rt);
14377 IDirect3DPixelShader9_Release(ps);
14378 IDirect3DPixelShader9_Release(ps_cube);
14379 IDirect3DPixelShader9_Release(ps_volume);
14380 refcount = IDirect3DDevice9_Release(device);
14381 ok(!refcount, "Device has %u references left.\n", refcount);
14382 done:
14383 IDirect3D9_Release(d3d);
14384 DestroyWindow(window);
14387 static void update_surface_test(void)
14389 static const BYTE blocks[][8] =
14391 {0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00}, /* White */
14392 {0x00, 0xf8, 0x00, 0xf8, 0x00, 0x00, 0x00, 0x00}, /* Red */
14393 {0xe0, 0xff, 0xe0, 0xff, 0x00, 0x00, 0x00, 0x00}, /* Yellow */
14394 {0xe0, 0x07, 0xe0, 0x07, 0x00, 0x00, 0x00, 0x00}, /* Green */
14395 {0xff, 0x07, 0xff, 0x07, 0x00, 0x00, 0x00, 0x00}, /* Cyan */
14396 {0x1f, 0x00, 0x1f, 0x00, 0x00, 0x00, 0x00, 0x00}, /* Blue */
14397 {0x1f, 0xf8, 0x1f, 0xf8, 0x00, 0x00, 0x00, 0x00}, /* Magenta */
14399 static const struct
14401 UINT x, y;
14402 D3DCOLOR color;
14404 expected_colors[] =
14406 { 18, 240, D3DCOLOR_ARGB(0x00, 0xff, 0x00, 0xff)},
14407 { 57, 240, D3DCOLOR_ARGB(0x00, 0x00, 0x00, 0xff)},
14408 {109, 240, D3DCOLOR_ARGB(0x00, 0x00, 0xff, 0xff)},
14409 {184, 240, D3DCOLOR_ARGB(0x00, 0x00, 0xff, 0x00)},
14410 {290, 240, D3DCOLOR_ARGB(0x00, 0xff, 0xff, 0x00)},
14411 {440, 240, D3DCOLOR_ARGB(0x00, 0xff, 0x00, 0x00)},
14412 {584, 240, D3DCOLOR_ARGB(0x00, 0xff, 0xff, 0xff)},
14414 static const struct
14416 float x, y, z, w;
14417 float u, v;
14419 tri[] =
14421 { 0.0f, 480.0f, 0.0f, 1.0f, 0.0f, 0.0f},
14422 { 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 1.0f},
14423 {640.0f, 240.0f, 0.0f, 10.0f, 100.0f, 0.5f},
14425 static const RECT rect_2x2 = {0, 0, 2, 2};
14426 static const struct
14428 UINT src_level;
14429 UINT dst_level;
14430 const RECT *r;
14431 HRESULT hr;
14433 block_size_tests[] =
14435 {1, 0, NULL, D3D_OK},
14436 {0, 1, NULL, D3DERR_INVALIDCALL},
14437 {5, 4, NULL, D3DERR_INVALIDCALL},
14438 {4, 5, NULL, D3DERR_INVALIDCALL},
14439 {4, 5, &rect_2x2, D3DERR_INVALIDCALL},
14440 {5, 5, &rect_2x2, D3D_OK},
14443 IDirect3DSurface9 *src_surface, *dst_surface;
14444 IDirect3DTexture9 *src_tex, *dst_tex;
14445 IDirect3DDevice9 *device;
14446 IDirect3D9 *d3d;
14447 ULONG refcount;
14448 UINT count, i;
14449 HWND window;
14450 HRESULT hr;
14452 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
14453 0, 0, 640, 480, NULL, NULL, NULL, NULL);
14454 d3d = Direct3DCreate9(D3D_SDK_VERSION);
14455 ok(!!d3d, "Failed to create a D3D object.\n");
14456 if (FAILED(IDirect3D9_CheckDeviceFormat(d3d, D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL,
14457 D3DFMT_X8R8G8B8, 0, D3DRTYPE_TEXTURE, D3DFMT_DXT1)))
14459 skip("DXT1 not supported, skipping tests.\n");
14460 goto done;
14462 if (!(device = create_device(d3d, window, window, TRUE)))
14464 skip("Failed to create a D3D device, skipping tests.\n");
14465 goto done;
14468 hr = IDirect3DDevice9_CreateTexture(device, 64, 64, 0, 0, D3DFMT_DXT1, D3DPOOL_SYSTEMMEM, &src_tex, NULL);
14469 ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);
14470 hr = IDirect3DDevice9_CreateTexture(device, 64, 64, 0, 0, D3DFMT_DXT1, D3DPOOL_DEFAULT, &dst_tex, NULL);
14471 ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);
14473 count = IDirect3DTexture9_GetLevelCount(src_tex);
14474 ok(count == 7, "Got level count %u, expected 7.\n", count);
14476 for (i = 0; i < count; ++i)
14478 UINT row_count, block_count, x, y;
14479 D3DSURFACE_DESC desc;
14480 BYTE *row, *block;
14481 D3DLOCKED_RECT r;
14483 hr = IDirect3DTexture9_GetLevelDesc(src_tex, i, &desc);
14484 ok(SUCCEEDED(hr), "Failed to get level desc, hr %#x.\n", hr);
14486 hr = IDirect3DTexture9_LockRect(src_tex, i, &r, NULL, 0);
14487 ok(SUCCEEDED(hr), "Failed to lock texture, hr %#x.\n", hr);
14489 row_count = ((desc.Height + 3) & ~3) / 4;
14490 block_count = ((desc.Width + 3) & ~3) / 4;
14491 row = r.pBits;
14493 for (y = 0; y < row_count; ++y)
14495 block = row;
14496 for (x = 0; x < block_count; ++x)
14498 memcpy(block, blocks[i], sizeof(blocks[i]));
14499 block += sizeof(blocks[i]);
14501 row += r.Pitch;
14504 hr = IDirect3DTexture9_UnlockRect(src_tex, i);
14505 ok(SUCCEEDED(hr), "Failed to unlock texture, hr %#x.\n", hr);
14508 for (i = 0; i < sizeof(block_size_tests) / sizeof(*block_size_tests); ++i)
14510 hr = IDirect3DTexture9_GetSurfaceLevel(src_tex, block_size_tests[i].src_level, &src_surface);
14511 ok(SUCCEEDED(hr), "Failed to get texture surface, hr %#x.\n", hr);
14512 hr = IDirect3DTexture9_GetSurfaceLevel(dst_tex, block_size_tests[i].dst_level, &dst_surface);
14513 ok(SUCCEEDED(hr), "Failed to get texture surface, hr %#x.\n", hr);
14515 hr = IDirect3DDevice9_UpdateSurface(device, src_surface, block_size_tests[i].r, dst_surface, NULL);
14516 ok(hr == block_size_tests[i].hr, "Update surface returned %#x for test %u, expected %#x.\n",
14517 hr, i, block_size_tests[i].hr);
14519 IDirect3DSurface9_Release(dst_surface);
14520 IDirect3DSurface9_Release(src_surface);
14523 for (i = 0; i < count; ++i)
14525 hr = IDirect3DTexture9_GetSurfaceLevel(src_tex, i, &src_surface);
14526 ok(SUCCEEDED(hr), "Failed to get texture surface, hr %#x.\n", hr);
14527 hr = IDirect3DTexture9_GetSurfaceLevel(dst_tex, i, &dst_surface);
14528 ok(SUCCEEDED(hr), "Failed to get texture surface, hr %#x.\n", hr);
14530 hr = IDirect3DDevice9_UpdateSurface(device, src_surface, NULL, dst_surface, NULL);
14531 ok(SUCCEEDED(hr), "Failed to update surface at level %u, hr %#x.\n", i, hr);
14533 IDirect3DSurface9_Release(dst_surface);
14534 IDirect3DSurface9_Release(src_surface);
14537 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
14538 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
14539 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MIPFILTER, D3DTEXF_POINT);
14540 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
14541 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZRHW | D3DFVF_TEX1);
14542 ok(SUCCEEDED(hr), "SetFVF failed, hr %#x.\n", hr);
14543 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)dst_tex);
14544 ok(SUCCEEDED(hr), "SetTexture failed, hr %#x.\n", hr);
14545 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
14546 ok(SUCCEEDED(hr), "SetTextureStageState failed, hr %#x.\n", hr);
14547 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
14548 ok(SUCCEEDED(hr), "SetTextureStageState failed, hr %#x.\n", hr);
14550 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff000000, 0.0f, 0);
14551 ok(SUCCEEDED(hr), "Clear failed, hr %#x.\n", hr);
14553 hr = IDirect3DDevice9_BeginScene(device);
14554 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
14555 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLELIST, 1, tri, sizeof(*tri));
14556 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
14557 hr = IDirect3DDevice9_EndScene(device);
14558 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
14560 for (i = 0; i < sizeof(expected_colors) / sizeof(*expected_colors); ++i)
14562 D3DCOLOR color = getPixelColor(device, expected_colors[i].x, expected_colors[i].y);
14563 ok(color_match(color, expected_colors[i].color, 0),
14564 "Expected color 0x%08x at (%u, %u), got 0x%08x.\n",
14565 expected_colors[i].color, expected_colors[i].x, expected_colors[i].y, color);
14568 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
14569 ok(SUCCEEDED(hr), "Present failed, hr %#x.\n", hr);
14571 IDirect3DTexture9_Release(dst_tex);
14572 IDirect3DTexture9_Release(src_tex);
14573 refcount = IDirect3DDevice9_Release(device);
14574 ok(!refcount, "Device has %u references left.\n", refcount);
14575 done:
14576 IDirect3D9_Release(d3d);
14577 DestroyWindow(window);
14580 static void multisample_get_rtdata_test(void)
14582 IDirect3DSurface9 *original_ds, *original_rt, *rt, *readback;
14583 IDirect3DDevice9 *device;
14584 IDirect3D9 *d3d;
14585 ULONG refcount;
14586 HWND window;
14587 HRESULT hr;
14589 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
14590 0, 0, 640, 480, NULL, NULL, NULL, NULL);
14591 d3d = Direct3DCreate9(D3D_SDK_VERSION);
14592 ok(!!d3d, "Failed to create a D3D object.\n");
14593 if (FAILED(IDirect3D9_CheckDeviceMultiSampleType(d3d, D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL,
14594 D3DFMT_A8R8G8B8, TRUE, D3DMULTISAMPLE_2_SAMPLES, NULL)))
14596 skip("Multisampling not supported for D3DFMT_A8R8G8B8, skipping tests.\n");
14597 goto done;
14599 if (!(device = create_device(d3d, window, window, TRUE)))
14601 skip("Failed to create a D3D device, skipping tests.\n");
14602 goto done;
14605 hr = IDirect3DDevice9_CreateRenderTarget(device, 256, 256, D3DFMT_A8R8G8B8,
14606 D3DMULTISAMPLE_2_SAMPLES, 0, FALSE, &rt, NULL);
14607 ok(SUCCEEDED(hr), "Failed to create render target, hr %#x.\n", hr);
14608 hr = IDirect3DDevice9_CreateOffscreenPlainSurface(device, 256, 256, D3DFMT_A8R8G8B8,
14609 D3DPOOL_SYSTEMMEM, &readback, NULL);
14610 ok(SUCCEEDED(hr), "Failed to create readback surface, hr %#x.\n", hr);
14612 hr = IDirect3DDevice9_GetRenderTarget(device, 0, &original_rt);
14613 ok(SUCCEEDED(hr), "Failed to get render target, hr %#x.\n", hr);
14614 hr = IDirect3DDevice9_GetDepthStencilSurface(device, &original_ds);
14615 ok(SUCCEEDED(hr), "Failed to get depth/stencil, hr %#x.\n", hr);
14617 hr = IDirect3DDevice9_SetRenderTarget(device, 0, rt);
14618 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
14619 hr = IDirect3DDevice9_SetDepthStencilSurface(device, NULL);
14620 ok(SUCCEEDED(hr), "Failed to set depth/stencil, hr %#x.\n", hr);
14622 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET, 0xff00ff00, 0.0, 0);
14623 ok(SUCCEEDED(hr), "Failed to clear render target, hr %#x.\n", hr);
14624 hr = IDirect3DDevice9_GetRenderTargetData(device, rt, readback);
14625 ok(hr == D3DERR_INVALIDCALL, "Got unexpected hr %#x.\n", hr);
14627 hr = IDirect3DDevice9_SetDepthStencilSurface(device, original_ds);
14628 ok(SUCCEEDED(hr), "Failed to set depth/stencil, hr %#x.\n", hr);
14629 hr = IDirect3DDevice9_SetRenderTarget(device, 0, original_rt);
14630 ok(SUCCEEDED(hr), "Failed to restore original render target, hr %#x.\n", hr);
14632 IDirect3DSurface9_Release(original_ds);
14633 IDirect3DSurface9_Release(original_rt);
14634 IDirect3DSurface9_Release(readback);
14635 IDirect3DSurface9_Release(rt);
14636 refcount = IDirect3DDevice9_Release(device);
14637 ok(!refcount, "Device has %u references left.\n", refcount);
14638 done:
14639 IDirect3D9_Release(d3d);
14640 DestroyWindow(window);
14643 static void multisampled_depth_buffer_test(void)
14645 IDirect3DDevice9 *device = 0;
14646 IDirect3DSurface9 *original_rt, *rt, *readback, *ds, *original_ds;
14647 IDirect3D9 *d3d;
14648 D3DCAPS9 caps;
14649 HRESULT hr;
14650 D3DPRESENT_PARAMETERS present_parameters;
14651 unsigned int i;
14652 static const struct
14654 float x, y, z;
14655 D3DCOLOR color;
14657 quad_1[] =
14659 { -1.0f, 1.0f, 0.0f, 0xffff0000},
14660 { 1.0f, 1.0f, 1.0f, 0xffff0000},
14661 { -1.0f, -1.0f, 0.0f, 0xffff0000},
14662 { 1.0f, -1.0f, 1.0f, 0xffff0000},
14664 quad_2[] =
14666 { -1.0f, 1.0f, 1.0f, 0xff0000ff},
14667 { 1.0f, 1.0f, 0.0f, 0xff0000ff},
14668 { -1.0f, -1.0f, 1.0f, 0xff0000ff},
14669 { 1.0f, -1.0f, 0.0f, 0xff0000ff},
14671 static const struct
14673 UINT x, y;
14674 D3DCOLOR color;
14676 expected_colors[] =
14678 { 80, 100, D3DCOLOR_ARGB(0xff, 0xff, 0x00, 0x00)},
14679 {240, 100, D3DCOLOR_ARGB(0xff, 0xff, 0x00, 0x00)},
14680 {400, 100, D3DCOLOR_ARGB(0xff, 0x00, 0x00, 0xff)},
14681 {560, 100, D3DCOLOR_ARGB(0xff, 0x00, 0x00, 0xff)},
14682 { 80, 450, D3DCOLOR_ARGB(0xff, 0xff, 0x00, 0x00)},
14683 {240, 450, D3DCOLOR_ARGB(0xff, 0xff, 0x00, 0x00)},
14684 {400, 450, D3DCOLOR_ARGB(0xff, 0x00, 0x00, 0xff)},
14685 {560, 450, D3DCOLOR_ARGB(0xff, 0x00, 0x00, 0xff)},
14688 d3d = Direct3DCreate9(D3D_SDK_VERSION);
14689 ok(!!d3d, "Failed to create a D3D object.\n");
14691 if (FAILED(IDirect3D9_CheckDeviceMultiSampleType(d3d, D3DADAPTER_DEFAULT,
14692 D3DDEVTYPE_HAL, D3DFMT_A8R8G8B8, TRUE, D3DMULTISAMPLE_2_SAMPLES, NULL)))
14694 skip("Multisampling not supported for D3DFMT_A8R8G8B8, skipping multisampled depth buffer test.\n");
14695 IDirect3D9_Release(d3d);
14696 return;
14698 if (FAILED(IDirect3D9_CheckDeviceMultiSampleType(d3d, D3DADAPTER_DEFAULT,
14699 D3DDEVTYPE_HAL, D3DFMT_D24S8, TRUE, D3DMULTISAMPLE_2_SAMPLES, NULL)))
14701 skip("Multisampling not supported for D3DFMT_D24S8, skipping multisampled depth buffer test.\n");
14702 IDirect3D9_Release(d3d);
14703 return;
14706 ZeroMemory(&present_parameters, sizeof(present_parameters));
14707 present_parameters.Windowed = TRUE;
14708 present_parameters.hDeviceWindow = create_window();
14709 present_parameters.SwapEffect = D3DSWAPEFFECT_DISCARD;
14710 present_parameters.BackBufferWidth = 640;
14711 present_parameters.BackBufferHeight = 480;
14712 present_parameters.BackBufferFormat = D3DFMT_A8R8G8B8;
14713 present_parameters.EnableAutoDepthStencil = TRUE;
14714 present_parameters.AutoDepthStencilFormat = D3DFMT_D24S8;
14715 present_parameters.MultiSampleType = D3DMULTISAMPLE_2_SAMPLES;
14717 hr = IDirect3D9_CreateDevice(d3d, D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL,
14718 present_parameters.hDeviceWindow, D3DCREATE_HARDWARE_VERTEXPROCESSING,
14719 &present_parameters, &device);
14720 ok(hr == D3D_OK, "Failed to create a device, hr %#x.\n", hr);
14722 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
14723 ok(SUCCEEDED(hr), "GetDeviceCaps failed, hr %#x.\n", hr);
14724 if (caps.TextureCaps & D3DPTEXTURECAPS_POW2)
14726 skip("No unconditional NP2 texture support, skipping multisampled depth buffer test.\n");
14727 goto cleanup;
14730 hr = IDirect3DDevice9_CreateRenderTarget(device, 640, 480, D3DFMT_A8R8G8B8,
14731 D3DMULTISAMPLE_2_SAMPLES, 0, FALSE, &rt, NULL);
14732 ok(SUCCEEDED(hr), "Failed to create render target, hr %#x.\n", hr);
14733 hr = IDirect3DDevice9_CreateRenderTarget(device, 640, 480, D3DFMT_A8R8G8B8,
14734 D3DMULTISAMPLE_NONE, 0, TRUE, &readback, NULL);
14735 ok(SUCCEEDED(hr), "Failed to create readback surface, hr %#x.\n", hr);
14737 hr = IDirect3DDevice9_GetRenderTarget(device, 0, &original_rt);
14738 ok(SUCCEEDED(hr), "Failed to get render target, hr %#x.\n", hr);
14739 hr = IDirect3DDevice9_GetDepthStencilSurface(device, &ds);
14740 ok(SUCCEEDED(hr), "Failed to get depth/stencil, hr %#x.\n", hr);
14742 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
14743 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
14744 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, D3DZB_TRUE);
14745 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
14746 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, TRUE);
14747 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
14748 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZFUNC, D3DCMP_LESSEQUAL);
14749 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
14750 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
14751 ok(SUCCEEDED(hr), "SetFVF failed, hr %#x.\n", hr);
14753 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff00ff00, 1.0f, 0);
14754 ok(SUCCEEDED(hr), "Failed to clear render target, hr %#x.\n", hr);
14756 /* Render onscreen and then offscreen */
14757 hr = IDirect3DDevice9_BeginScene(device);
14758 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
14759 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad_1, sizeof(*quad_1));
14760 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
14761 hr = IDirect3DDevice9_EndScene(device);
14762 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
14764 hr = IDirect3DDevice9_StretchRect(device, original_rt, NULL, rt, NULL, D3DTEXF_POINT);
14765 ok(SUCCEEDED(hr), "StretchRect failed, hr %#x.\n", hr);
14766 hr = IDirect3DDevice9_SetRenderTarget(device, 0, rt);
14767 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
14769 hr = IDirect3DDevice9_BeginScene(device);
14770 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
14771 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad_2, sizeof(*quad_2));
14772 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
14773 hr = IDirect3DDevice9_EndScene(device);
14774 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
14776 hr = IDirect3DDevice9_StretchRect(device, rt, NULL, readback, NULL, D3DTEXF_POINT);
14777 ok(SUCCEEDED(hr), "StretchRect failed, hr %#x.\n", hr);
14779 for (i = 0; i < sizeof(expected_colors) / sizeof(*expected_colors); ++i)
14781 D3DCOLOR color = getPixelColorFromSurface(readback, expected_colors[i].x, expected_colors[i].y);
14782 ok(color_match(color, expected_colors[i].color, 1),
14783 "Expected color 0x%08x at (%u, %u), got 0x%08x.\n",
14784 expected_colors[i].color, expected_colors[i].x, expected_colors[i].y, color);
14787 hr = IDirect3DDevice9_StretchRect(device, rt, NULL, original_rt, NULL, D3DTEXF_POINT);
14788 ok(SUCCEEDED(hr), "StretchRect failed, hr %#x.\n", hr);
14789 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
14790 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
14792 /* Render offscreen and then onscreen */
14793 hr = IDirect3DDevice9_SetDepthStencilSurface(device, NULL);
14794 ok(SUCCEEDED(hr), "Failed to set depth/stencil, hr %#x.\n", hr);
14795 IDirect3DSurface9_Release(ds);
14796 hr = IDirect3DDevice9_CreateDepthStencilSurface(device, 640, 480, D3DFMT_D24S8,
14797 D3DMULTISAMPLE_2_SAMPLES, 0, TRUE, &ds, NULL);
14798 hr = IDirect3DDevice9_SetDepthStencilSurface(device, ds);
14799 ok(SUCCEEDED(hr), "Failed to set depth/stencil, hr %#x.\n", hr);
14801 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff00ff00, 1.0f, 0);
14802 ok(SUCCEEDED(hr), "Failed to clear render target, hr %#x.\n", hr);
14804 hr = IDirect3DDevice9_BeginScene(device);
14805 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
14806 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad_1, sizeof(*quad_1));
14807 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
14808 hr = IDirect3DDevice9_EndScene(device);
14809 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
14811 hr = IDirect3DDevice9_StretchRect(device, rt, NULL, original_rt, NULL, D3DTEXF_POINT);
14812 ok(SUCCEEDED(hr), "StretchRect failed, hr %#x.\n", hr);
14813 hr = IDirect3DDevice9_SetRenderTarget(device, 0, original_rt);
14814 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
14816 hr = IDirect3DDevice9_BeginScene(device);
14817 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
14818 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad_2, sizeof(*quad_2));
14819 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
14820 hr = IDirect3DDevice9_EndScene(device);
14821 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
14823 hr = IDirect3DDevice9_StretchRect(device, original_rt, NULL, readback, NULL, D3DTEXF_POINT);
14824 ok(SUCCEEDED(hr), "StretchRect failed, hr %#x.\n", hr);
14826 for (i = 0; i < sizeof(expected_colors) / sizeof(*expected_colors); ++i)
14828 D3DCOLOR color = getPixelColorFromSurface(readback, expected_colors[i].x, expected_colors[i].y);
14829 ok(color_match(color, expected_colors[i].color, 1),
14830 "Expected color 0x%08x at (%u, %u), got 0x%08x.\n",
14831 expected_colors[i].color, expected_colors[i].x, expected_colors[i].y, color);
14834 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
14835 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
14837 IDirect3DSurface9_Release(ds);
14838 IDirect3DSurface9_Release(readback);
14839 IDirect3DSurface9_Release(rt);
14840 IDirect3DSurface9_Release(original_rt);
14841 cleanup_device(device);
14843 ZeroMemory(&present_parameters, sizeof(present_parameters));
14844 present_parameters.Windowed = TRUE;
14845 present_parameters.hDeviceWindow = create_window();
14846 present_parameters.SwapEffect = D3DSWAPEFFECT_DISCARD;
14847 present_parameters.BackBufferWidth = 640;
14848 present_parameters.BackBufferHeight = 480;
14849 present_parameters.BackBufferFormat = D3DFMT_A8R8G8B8;
14850 present_parameters.EnableAutoDepthStencil = TRUE;
14851 present_parameters.AutoDepthStencilFormat = D3DFMT_D24S8;
14852 present_parameters.MultiSampleType = D3DMULTISAMPLE_NONE;
14854 hr = IDirect3D9_CreateDevice(d3d, D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL,
14855 present_parameters.hDeviceWindow, D3DCREATE_HARDWARE_VERTEXPROCESSING,
14856 &present_parameters, &device);
14857 ok(hr == D3D_OK, "Failed to create a device, hr %#x.\n", hr);
14859 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff00ffff, 1.0f, 0);
14860 ok(SUCCEEDED(hr), "Failed to clear depth buffer, hr %#x.\n", hr);
14862 hr = IDirect3DDevice9_CreateRenderTarget(device, 640, 480, D3DFMT_A8R8G8B8,
14863 D3DMULTISAMPLE_2_SAMPLES, 0, FALSE, &rt, NULL);
14864 ok(SUCCEEDED(hr), "Failed to create render target, hr %#x.\n", hr);
14865 hr = IDirect3DDevice9_CreateRenderTarget(device, 640, 480, D3DFMT_A8R8G8B8,
14866 D3DMULTISAMPLE_NONE, 0, TRUE, &readback, NULL);
14867 ok(SUCCEEDED(hr), "Failed to create readback surface, hr %#x.\n", hr);
14868 hr = IDirect3DDevice9_CreateDepthStencilSurface(device, 640, 480, D3DFMT_D24S8,
14869 D3DMULTISAMPLE_2_SAMPLES, 0, FALSE, &ds, NULL);
14870 ok(SUCCEEDED(hr), "CreateDepthStencilSurface failed, hr %#x.\n", hr);
14872 hr = IDirect3DDevice9_GetRenderTarget(device, 0, &original_rt);
14873 ok(SUCCEEDED(hr), "Failed to get render target, hr %#x.\n", hr);
14874 hr = IDirect3DDevice9_GetDepthStencilSurface(device, &original_ds);
14875 ok(SUCCEEDED(hr), "Failed to get depth/stencil, hr %#x.\n", hr);
14876 hr = IDirect3DDevice9_SetRenderTarget(device, 0, rt);
14877 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
14878 hr = IDirect3DDevice9_SetDepthStencilSurface(device, ds);
14879 ok(SUCCEEDED(hr), "Failed to set depth/stencil, hr %#x.\n", hr);
14881 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
14882 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
14883 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, D3DZB_TRUE);
14884 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
14885 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, TRUE);
14886 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
14887 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZFUNC, D3DCMP_LESSEQUAL);
14888 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
14889 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
14890 ok(SUCCEEDED(hr), "SetFVF failed, hr %#x.\n", hr);
14892 /* Render to a multisampled offscreen frame buffer and then blit to
14893 * the onscreen (not multisampled) frame buffer. */
14894 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff00ff00, 1.0f, 0);
14895 ok(SUCCEEDED(hr), "Failed to clear render target, hr %#x.\n", hr);
14897 hr = IDirect3DDevice9_BeginScene(device);
14898 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
14899 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad_1, sizeof(*quad_1));
14900 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
14901 hr = IDirect3DDevice9_EndScene(device);
14902 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
14904 hr = IDirect3DDevice9_StretchRect(device, rt, NULL, original_rt, NULL, D3DTEXF_POINT);
14905 ok(SUCCEEDED(hr), "StretchRect failed, hr %#x.\n", hr);
14906 hr = IDirect3DDevice9_StretchRect(device, ds, NULL, original_ds, NULL, D3DTEXF_POINT);
14907 ok(SUCCEEDED(hr), "StretchRect failed, hr %#x.\n", hr);
14909 hr = IDirect3DDevice9_SetRenderTarget(device, 0, original_rt);
14910 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
14911 hr = IDirect3DDevice9_SetDepthStencilSurface(device, original_ds);
14912 ok(SUCCEEDED(hr), "Failed to set depth/stencil, hr %#x.\n", hr);
14914 hr = IDirect3DDevice9_BeginScene(device);
14915 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
14916 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad_2, sizeof(*quad_2));
14917 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
14918 hr = IDirect3DDevice9_EndScene(device);
14919 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
14921 hr = IDirect3DDevice9_StretchRect(device, original_rt, NULL, readback, NULL, D3DTEXF_POINT);
14922 ok(SUCCEEDED(hr), "StretchRect failed, hr %#x.\n", hr);
14924 for (i = 0; i < sizeof(expected_colors) / sizeof(*expected_colors); ++i)
14926 D3DCOLOR color = getPixelColorFromSurface(readback, expected_colors[i].x, expected_colors[i].y);
14927 ok(color_match(color, expected_colors[i].color, 1),
14928 "Expected color 0x%08x at (%u, %u), got 0x%08x.\n",
14929 expected_colors[i].color, expected_colors[i].x, expected_colors[i].y, color);
14932 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
14933 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
14935 hr = IDirect3DDevice9_SetDepthStencilSurface(device, NULL);
14936 ok(SUCCEEDED(hr), "Failed to set depth/stencil, hr %#x.\n", hr);
14937 hr = IDirect3DDevice9_SetRenderTarget(device, 0, original_rt);
14938 ok(SUCCEEDED(hr), "Failed to restore original render target, hr %#x.\n", hr);
14940 IDirect3DSurface9_Release(original_ds);
14941 IDirect3DSurface9_Release(original_rt);
14942 IDirect3DSurface9_Release(ds);
14943 IDirect3DSurface9_Release(readback);
14944 IDirect3DSurface9_Release(rt);
14945 cleanup:
14946 cleanup_device(device);
14947 IDirect3D9_Release(d3d);
14950 static void resz_test(void)
14952 IDirect3DDevice9 *device = 0;
14953 IDirect3DSurface9 *rt, *original_rt, *ds, *readback, *intz_ds;
14954 D3DCAPS9 caps;
14955 HRESULT hr;
14956 D3DPRESENT_PARAMETERS present_parameters;
14957 unsigned int i;
14958 static const DWORD ps_code[] =
14960 0xffff0200, /* ps_2_0 */
14961 0x0200001f, 0x90000000, 0xa00f0800, /* dcl_2d s0 */
14962 0x0200001f, 0x80000000, 0xb00f0000, /* dcl t0 */
14963 0x05000051, 0xa00f0000, 0x00000000, 0x00000000, 0x00000000, 0x3f800000, /* def c0, 0.0, 0.0, 0.0, 1.0 */
14964 0x02000001, 0x800f0001, 0xa0e40000, /* mov r1, c0 */
14965 0x03000042, 0x800f0000, 0xb0e40000, 0xa0e40800, /* texld r0, t0, s0 */
14966 0x02000001, 0x80010001, 0x80e40000, /* mov r1.x, r0 */
14967 0x03010042, 0x800f0000, 0xb0e40000, 0xa0e40800, /* texldp r0, t0, s0 */
14968 0x02000001, 0x80020001, 0x80000000, /* mov r1.y, r0.x */
14969 0x02000001, 0x800f0800, 0x80e40001, /* mov oC0, r1 */
14970 0x0000ffff, /* end */
14972 struct
14974 float x, y, z;
14975 float s, t, p, q;
14977 quad[] =
14979 { -1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 1.0f, 0.5f},
14980 { 1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 0.5f},
14981 { -1.0f, -1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.5f},
14982 { 1.0f, -1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 0.5f},
14984 struct
14986 UINT x, y;
14987 D3DCOLOR color;
14989 expected_colors[] =
14991 { 80, 100, D3DCOLOR_ARGB(0x00, 0x20, 0x40, 0x00)},
14992 {240, 100, D3DCOLOR_ARGB(0x00, 0x60, 0xbf, 0x00)},
14993 {400, 100, D3DCOLOR_ARGB(0x00, 0x9f, 0x40, 0x00)},
14994 {560, 100, D3DCOLOR_ARGB(0x00, 0xdf, 0xbf, 0x00)},
14995 { 80, 450, D3DCOLOR_ARGB(0x00, 0x20, 0x40, 0x00)},
14996 {240, 450, D3DCOLOR_ARGB(0x00, 0x60, 0xbf, 0x00)},
14997 {400, 450, D3DCOLOR_ARGB(0x00, 0x9f, 0x40, 0x00)},
14998 {560, 450, D3DCOLOR_ARGB(0x00, 0xdf, 0xbf, 0x00)},
15000 IDirect3DTexture9 *texture;
15001 IDirect3DPixelShader9 *ps;
15002 IDirect3D9 *d3d;
15003 DWORD value;
15005 d3d = Direct3DCreate9(D3D_SDK_VERSION);
15006 ok(!!d3d, "Failed to create a D3D object.\n");
15008 if (FAILED(IDirect3D9_CheckDeviceMultiSampleType(d3d, D3DADAPTER_DEFAULT,
15009 D3DDEVTYPE_HAL, D3DFMT_A8R8G8B8, TRUE, D3DMULTISAMPLE_2_SAMPLES, NULL)))
15011 skip("Multisampling not supported for D3DFMT_A8R8G8B8, skipping RESZ test.\n");
15012 IDirect3D9_Release(d3d);
15013 return;
15015 if (FAILED(IDirect3D9_CheckDeviceMultiSampleType(d3d, D3DADAPTER_DEFAULT,
15016 D3DDEVTYPE_HAL, D3DFMT_D24S8, TRUE, D3DMULTISAMPLE_2_SAMPLES, NULL)))
15018 skip("Multisampling not supported for D3DFMT_D24S8, skipping RESZ test.\n");
15019 IDirect3D9_Release(d3d);
15020 return;
15023 if (FAILED(IDirect3D9_CheckDeviceFormat(d3d, D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, D3DFMT_X8R8G8B8,
15024 D3DUSAGE_DEPTHSTENCIL, D3DRTYPE_TEXTURE, MAKEFOURCC('I','N','T','Z'))))
15026 skip("No INTZ support, skipping RESZ test.\n");
15027 IDirect3D9_Release(d3d);
15028 return;
15031 if (FAILED(IDirect3D9_CheckDeviceFormat(d3d, D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, D3DFMT_X8R8G8B8,
15032 D3DUSAGE_RENDERTARGET, D3DRTYPE_SURFACE, MAKEFOURCC('R','E','S','Z'))))
15034 skip("No RESZ support, skipping RESZ test.\n");
15035 IDirect3D9_Release(d3d);
15036 return;
15039 ZeroMemory(&present_parameters, sizeof(present_parameters));
15040 present_parameters.Windowed = TRUE;
15041 present_parameters.hDeviceWindow = create_window();
15042 present_parameters.SwapEffect = D3DSWAPEFFECT_DISCARD;
15043 present_parameters.BackBufferWidth = 640;
15044 present_parameters.BackBufferHeight = 480;
15045 present_parameters.BackBufferFormat = D3DFMT_A8R8G8B8;
15046 present_parameters.EnableAutoDepthStencil = FALSE;
15047 present_parameters.AutoDepthStencilFormat = D3DFMT_D24S8;
15048 present_parameters.MultiSampleType = D3DMULTISAMPLE_NONE;
15050 hr = IDirect3D9_CreateDevice(d3d, D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL,
15051 present_parameters.hDeviceWindow, D3DCREATE_HARDWARE_VERTEXPROCESSING, &present_parameters, &device);
15052 ok(hr == D3D_OK, "Failed to create a device, hr %#x.\n", hr);
15054 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
15055 ok(SUCCEEDED(hr), "GetDeviceCaps failed, hr %#x.\n", hr);
15056 if (caps.PixelShaderVersion < D3DPS_VERSION(2, 0))
15058 skip("No pixel shader 2.0 support, skipping INTZ test.\n");
15059 cleanup_device(device);
15060 IDirect3D9_Release(d3d);
15061 return;
15063 if (caps.TextureCaps & D3DPTEXTURECAPS_POW2)
15065 skip("No unconditional NP2 texture support, skipping INTZ test.\n");
15066 cleanup_device(device);
15067 IDirect3D9_Release(d3d);
15068 return;
15071 hr = IDirect3DDevice9_GetRenderTarget(device, 0, &original_rt);
15072 ok(SUCCEEDED(hr), "Failed to get render target, hr %#x.\n", hr);
15074 hr = IDirect3DDevice9_CreateRenderTarget(device, 640, 480, D3DFMT_A8R8G8B8,
15075 D3DMULTISAMPLE_2_SAMPLES, 0, FALSE, &rt, NULL);
15076 ok(SUCCEEDED(hr), "Failed to create render target, hr %#x.\n", hr);
15077 hr = IDirect3DDevice9_CreateDepthStencilSurface(device, 640, 480, D3DFMT_D24S8,
15078 D3DMULTISAMPLE_2_SAMPLES, 0, TRUE, &ds, NULL);
15079 hr = IDirect3DDevice9_CreateRenderTarget(device, 640, 480, D3DFMT_A8R8G8B8,
15080 D3DMULTISAMPLE_NONE, 0, TRUE, &readback, NULL);
15081 ok(SUCCEEDED(hr), "Failed to create readback surface, hr %#x.\n", hr);
15083 hr = IDirect3DDevice9_CreateTexture(device, 640, 480, 1,
15084 D3DUSAGE_DEPTHSTENCIL, MAKEFOURCC('I','N','T','Z'), D3DPOOL_DEFAULT, &texture, NULL);
15085 ok(SUCCEEDED(hr), "CreateTexture failed, hr %#x.\n", hr);
15086 hr = IDirect3DTexture9_GetSurfaceLevel(texture, 0, &intz_ds);
15087 ok(SUCCEEDED(hr), "GetSurfaceLevel failed, hr %#x.\n", hr);
15088 hr = IDirect3DDevice9_SetDepthStencilSurface(device, intz_ds);
15089 ok(SUCCEEDED(hr), "Failed to set depth/stencil, hr %#x.\n", hr);
15090 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_ZBUFFER, 0, 1.0f, 0);
15091 ok(SUCCEEDED(hr), "Failed to clear depth/stencil, hr %#x.\n", hr);
15092 IDirect3DSurface9_Release(intz_ds);
15093 hr = IDirect3DDevice9_CreatePixelShader(device, ps_code, &ps);
15094 ok(SUCCEEDED(hr), "CreatePixelShader failed, hr %#x.\n", hr);
15096 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1 | D3DFVF_TEXCOORDSIZE4(0));
15097 ok(SUCCEEDED(hr), "SetFVF failed, hr %#x.\n", hr);
15098 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, D3DZB_TRUE);
15099 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15100 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZFUNC, D3DCMP_ALWAYS);
15101 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15102 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, TRUE);
15103 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15104 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
15105 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15107 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_ADDRESSU, D3DTADDRESS_WRAP);
15108 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
15109 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_ADDRESSV, D3DTADDRESS_WRAP);
15110 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
15111 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAGFILTER, D3DTEXF_POINT);
15112 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
15113 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MINFILTER, D3DTEXF_POINT);
15114 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
15115 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MIPFILTER, D3DTEXF_POINT);
15116 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
15118 /* Render offscreen (multisampled), blit the depth buffer
15119 * into the INTZ texture and then check its contents */
15120 hr = IDirect3DDevice9_SetRenderTarget(device, 0, rt);
15121 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
15122 hr = IDirect3DDevice9_SetDepthStencilSurface(device, ds);
15123 ok(SUCCEEDED(hr), "Failed to set depth/stencil, hr %#x.\n", hr);
15124 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff00ff00, 1.0f, 0);
15125 ok(SUCCEEDED(hr), "Failed to clear render target, hr %#x.\n", hr);
15127 hr = IDirect3DDevice9_BeginScene(device);
15128 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
15129 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
15130 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
15132 /* The destination depth texture has to be bound to sampler 0 */
15133 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)texture);
15134 ok(SUCCEEDED(hr), "SetTexture failed, hr %#x.\n", hr);
15136 /* the ATI "spec" says you have to do a dummy draw to ensure correct commands ordering */
15137 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, FALSE);
15138 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15139 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, FALSE);
15140 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15141 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_COLORWRITEENABLE, 0);
15142 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15143 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
15144 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
15145 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, TRUE);
15146 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15147 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, TRUE);
15148 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15149 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_COLORWRITEENABLE, 0xf);
15150 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15152 /* The actual multisampled depth buffer resolve happens here */
15153 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_POINTSIZE, 0x7fa05000);
15154 ok(SUCCEEDED(hr), "SetRenderState (multisampled depth buffer resolve) failed, hr %#x.\n", hr);
15155 hr = IDirect3DDevice9_GetRenderState(device, D3DRS_POINTSIZE, &value);
15156 ok(SUCCEEDED(hr) && value == 0x7fa05000, "GetRenderState failed, hr %#x, value %#x.\n", hr, value);
15158 hr = IDirect3DDevice9_SetRenderTarget(device, 0, original_rt);
15159 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
15160 hr = IDirect3DDevice9_SetPixelShader(device, ps);
15161 ok(SUCCEEDED(hr), "SetPixelShader failed, hr %#x.\n", hr);
15163 /* Read the depth values back */
15164 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
15165 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
15166 hr = IDirect3DDevice9_EndScene(device);
15167 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
15169 for (i = 0; i < sizeof(expected_colors) / sizeof(*expected_colors); ++i)
15171 D3DCOLOR color = getPixelColor(device, expected_colors[i].x, expected_colors[i].y);
15172 ok(color_match(color, expected_colors[i].color, 1),
15173 "Expected color 0x%08x at (%u, %u), got 0x%08x.\n",
15174 expected_colors[i].color, expected_colors[i].x, expected_colors[i].y, color);
15177 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
15178 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
15180 hr = IDirect3DDevice9_SetRenderTarget(device, 0, original_rt);
15181 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
15182 hr = IDirect3DDevice9_SetDepthStencilSurface(device, NULL);
15183 ok(SUCCEEDED(hr), "Failed to set depth/stencil, hr %#x.\n", hr);
15184 IDirect3DSurface9_Release(ds);
15185 hr = IDirect3DDevice9_SetTexture(device, 0, NULL);
15186 ok(SUCCEEDED(hr), "SetTexture failed, hr %#x.\n", hr);
15187 IDirect3DTexture9_Release(texture);
15188 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
15189 ok(SUCCEEDED(hr), "SetPixelShader failed, hr %#x.\n", hr);
15190 IDirect3DPixelShader9_Release(ps);
15191 IDirect3DSurface9_Release(readback);
15192 IDirect3DSurface9_Release(original_rt);
15193 IDirect3DSurface9_Release(rt);
15194 cleanup_device(device);
15197 ZeroMemory(&present_parameters, sizeof(present_parameters));
15198 present_parameters.Windowed = TRUE;
15199 present_parameters.hDeviceWindow = create_window();
15200 present_parameters.SwapEffect = D3DSWAPEFFECT_DISCARD;
15201 present_parameters.BackBufferWidth = 640;
15202 present_parameters.BackBufferHeight = 480;
15203 present_parameters.BackBufferFormat = D3DFMT_A8R8G8B8;
15204 present_parameters.EnableAutoDepthStencil = TRUE;
15205 present_parameters.AutoDepthStencilFormat = D3DFMT_D24S8;
15206 present_parameters.MultiSampleType = D3DMULTISAMPLE_2_SAMPLES;
15208 hr = IDirect3D9_CreateDevice(d3d, D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL,
15209 present_parameters.hDeviceWindow, D3DCREATE_HARDWARE_VERTEXPROCESSING, &present_parameters, &device);
15210 ok(hr == D3D_OK, "Failed to create a device, hr %#x.\n", hr);
15212 hr = IDirect3DDevice9_GetRenderTarget(device, 0, &original_rt);
15213 ok(SUCCEEDED(hr), "Failed to get render target, hr %#x.\n", hr);
15214 hr = IDirect3DDevice9_GetDepthStencilSurface(device, &ds);
15215 ok(SUCCEEDED(hr), "Failed to get depth/stencil, hr %#x.\n", hr);
15216 hr = IDirect3DDevice9_CreateRenderTarget(device, 640, 480, D3DFMT_A8R8G8B8,
15217 D3DMULTISAMPLE_NONE, 0, TRUE, &readback, NULL);
15218 ok(SUCCEEDED(hr), "Failed to create readback surface, hr %#x.\n", hr);
15219 hr = IDirect3DDevice9_CreateTexture(device, 640, 480, 1,
15220 D3DUSAGE_DEPTHSTENCIL, MAKEFOURCC('I','N','T','Z'), D3DPOOL_DEFAULT, &texture, NULL);
15221 ok(SUCCEEDED(hr), "CreateTexture failed, hr %#x.\n", hr);
15222 hr = IDirect3DTexture9_GetSurfaceLevel(texture, 0, &intz_ds);
15223 ok(SUCCEEDED(hr), "GetSurfaceLevel failed, hr %#x.\n", hr);
15224 hr = IDirect3DDevice9_SetRenderTarget(device, 0, readback);
15225 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
15226 hr = IDirect3DDevice9_SetDepthStencilSurface(device, intz_ds);
15227 ok(SUCCEEDED(hr), "Failed to set depth/stencil, hr %#x.\n", hr);
15228 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_ZBUFFER, 0, 1.0f, 0);
15229 ok(SUCCEEDED(hr), "Failed to clear depth/stencil, hr %#x.\n", hr);
15230 IDirect3DSurface9_Release(intz_ds);
15231 hr = IDirect3DDevice9_CreatePixelShader(device, ps_code, &ps);
15232 ok(SUCCEEDED(hr), "CreatePixelShader failed, hr %#x.\n", hr);
15234 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1 | D3DFVF_TEXCOORDSIZE4(0));
15235 ok(SUCCEEDED(hr), "SetFVF failed, hr %#x.\n", hr);
15236 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, D3DZB_TRUE);
15237 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15238 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZFUNC, D3DCMP_ALWAYS);
15239 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15240 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, TRUE);
15241 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15242 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
15243 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15245 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_ADDRESSU, D3DTADDRESS_WRAP);
15246 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
15247 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_ADDRESSV, D3DTADDRESS_WRAP);
15248 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
15249 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAGFILTER, D3DTEXF_POINT);
15250 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
15251 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MINFILTER, D3DTEXF_POINT);
15252 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
15253 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MIPFILTER, D3DTEXF_POINT);
15254 ok(SUCCEEDED(hr), "SetSamplerState failed, hr %#x.\n", hr);
15256 /* Render onscreen, blit the depth buffer into the INTZ texture
15257 * and then check its contents */
15258 hr = IDirect3DDevice9_SetRenderTarget(device, 0, original_rt);
15259 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
15260 hr = IDirect3DDevice9_SetDepthStencilSurface(device, ds);
15261 ok(SUCCEEDED(hr), "Failed to set depth/stencil, hr %#x.\n", hr);
15262 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff00ff00, 1.0f, 0);
15263 ok(SUCCEEDED(hr), "Failed to clear render target, hr %#x.\n", hr);
15265 hr = IDirect3DDevice9_BeginScene(device);
15266 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
15267 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
15268 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
15269 hr = IDirect3DDevice9_EndScene(device);
15270 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
15272 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)texture);
15273 ok(SUCCEEDED(hr), "SetTexture failed, hr %#x.\n", hr);
15275 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, FALSE);
15276 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15277 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, FALSE);
15278 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15279 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_COLORWRITEENABLE, 0);
15280 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15281 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
15282 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
15283 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, TRUE);
15284 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15285 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, TRUE);
15286 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15287 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_COLORWRITEENABLE, 0xf);
15288 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15290 /* The actual multisampled depth buffer resolve happens here */
15291 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_POINTSIZE, 0x7fa05000);
15292 ok(SUCCEEDED(hr), "SetRenderState (multisampled depth buffer resolve) failed, hr %#x.\n", hr);
15293 hr = IDirect3DDevice9_GetRenderState(device, D3DRS_POINTSIZE, &value);
15294 ok(SUCCEEDED(hr) && value == 0x7fa05000, "GetRenderState failed, hr %#x, value %#x.\n", hr, value);
15296 hr = IDirect3DDevice9_SetRenderTarget(device, 0, readback);
15297 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
15298 hr = IDirect3DDevice9_SetPixelShader(device, ps);
15299 ok(SUCCEEDED(hr), "SetPixelShader failed, hr %#x.\n", hr);
15301 /* Read the depth values back */
15302 hr = IDirect3DDevice9_BeginScene(device);
15303 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
15304 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
15305 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
15306 hr = IDirect3DDevice9_EndScene(device);
15307 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
15309 for (i = 0; i < sizeof(expected_colors) / sizeof(*expected_colors); ++i)
15311 D3DCOLOR color = getPixelColor(device, expected_colors[i].x, expected_colors[i].y);
15312 ok(color_match(color, expected_colors[i].color, 1),
15313 "Expected color 0x%08x at (%u, %u), got 0x%08x.\n",
15314 expected_colors[i].color, expected_colors[i].x, expected_colors[i].y, color);
15317 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
15318 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
15321 /* Test edge cases - try with no texture at all */
15322 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
15323 ok(SUCCEEDED(hr), "SetPixelShader failed, hr %#x.\n", hr);
15324 hr = IDirect3DDevice9_SetTexture(device, 0, NULL);
15325 ok(SUCCEEDED(hr), "SetTexture failed, hr %#x.\n", hr);
15327 hr = IDirect3DDevice9_BeginScene(device);
15328 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
15329 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
15330 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
15331 hr = IDirect3DDevice9_EndScene(device);
15332 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
15334 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_POINTSIZE, 0x7fa05000);
15335 ok(SUCCEEDED(hr), "SetRenderState (multisampled depth buffer resolve) failed, hr %#x.\n", hr);
15337 /* With a non-multisampled depth buffer */
15338 IDirect3DSurface9_Release(ds);
15339 hr = IDirect3DDevice9_CreateDepthStencilSurface(device, 640, 480, D3DFMT_D24S8,
15340 D3DMULTISAMPLE_NONE, 0, TRUE, &ds, NULL);
15342 hr = IDirect3DDevice9_SetRenderTarget(device, 0, readback);
15343 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
15344 hr = IDirect3DDevice9_SetDepthStencilSurface(device, ds);
15345 ok(SUCCEEDED(hr), "Failed to set depth/stencil, hr %#x.\n", hr);
15346 hr = IDirect3DDevice9_SetTexture(device, 0, NULL);
15347 ok(SUCCEEDED(hr), "SetTexture failed, hr %#x.\n", hr);
15349 hr = IDirect3DDevice9_BeginScene(device);
15350 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
15351 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
15352 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
15354 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)texture);
15355 ok(SUCCEEDED(hr), "SetTexture failed, hr %#x.\n", hr);
15357 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, FALSE);
15358 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15359 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, FALSE);
15360 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15361 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_COLORWRITEENABLE, 0);
15362 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15363 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
15364 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
15365 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, TRUE);
15366 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15367 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZWRITEENABLE, TRUE);
15368 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15369 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_COLORWRITEENABLE, 0xf);
15370 ok(SUCCEEDED(hr), "SetRenderState failed, hr %#x.\n", hr);
15371 hr = IDirect3DDevice9_EndScene(device);
15372 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
15374 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_POINTSIZE, 0x7fa05000);
15375 ok(SUCCEEDED(hr), "SetRenderState (multisampled depth buffer resolve) failed, hr %#x.\n", hr);
15377 hr = IDirect3DDevice9_SetPixelShader(device, ps);
15378 ok(SUCCEEDED(hr), "SetPixelShader failed, hr %#x.\n", hr);
15380 /* Read the depth values back. */
15381 hr = IDirect3DDevice9_BeginScene(device);
15382 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
15383 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
15384 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
15385 hr = IDirect3DDevice9_EndScene(device);
15386 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
15388 for (i = 0; i < sizeof(expected_colors) / sizeof(*expected_colors); ++i)
15390 D3DCOLOR color = getPixelColor(device, expected_colors[i].x, expected_colors[i].y);
15391 ok(color_match(color, expected_colors[i].color, 1),
15392 "Expected color 0x%08x at (%u, %u), got 0x%08x.\n",
15393 expected_colors[i].color, expected_colors[i].x, expected_colors[i].y, color);
15396 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
15397 ok(SUCCEEDED(hr), "Present failed (0x%08x)\n", hr);
15399 /* Without a current depth-stencil buffer set */
15400 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
15401 ok(SUCCEEDED(hr), "SetPixelShader failed, hr %#x.\n", hr);
15402 hr = IDirect3DDevice9_SetDepthStencilSurface(device, NULL);
15403 ok(SUCCEEDED(hr), "Failed to set depth/stencil, hr %#x.\n", hr);
15405 hr = IDirect3DDevice9_BeginScene(device);
15406 ok(SUCCEEDED(hr), "BeginScene failed, hr %#x.\n", hr);
15407 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
15408 ok(SUCCEEDED(hr), "DrawPrimitiveUP failed, hr %#x.\n", hr);
15409 hr = IDirect3DDevice9_EndScene(device);
15410 ok(SUCCEEDED(hr), "EndScene failed, hr %#x.\n", hr);
15412 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_POINTSIZE, 0x7fa05000);
15413 ok(SUCCEEDED(hr), "SetRenderState (multisampled depth buffer resolve) failed, hr %#x.\n", hr);
15415 hr = IDirect3DDevice9_SetDepthStencilSurface(device, NULL);
15416 ok(SUCCEEDED(hr), "Failed to set depth/stencil, hr %#x.\n", hr);
15417 IDirect3DSurface9_Release(ds);
15418 hr = IDirect3DDevice9_SetRenderTarget(device, 0, original_rt);
15419 ok(SUCCEEDED(hr), "Failed to set render target, hr %#x.\n", hr);
15420 hr = IDirect3DDevice9_SetTexture(device, 0, NULL);
15421 ok(SUCCEEDED(hr), "SetTexture failed, hr %#x.\n", hr);
15422 IDirect3DTexture9_Release(texture);
15423 IDirect3DPixelShader9_Release(ps);
15424 IDirect3DSurface9_Release(readback);
15425 IDirect3DSurface9_Release(original_rt);
15426 cleanup_device(device);
15427 IDirect3D9_Release(d3d);
15430 static void zenable_test(void)
15432 static const struct
15434 struct vec4 position;
15435 D3DCOLOR diffuse;
15437 tquad[] =
15439 {{ 0.0f, 480.0f, -0.5f, 1.0f}, 0xff00ff00},
15440 {{ 0.0f, 0.0f, -0.5f, 1.0f}, 0xff00ff00},
15441 {{640.0f, 480.0f, 1.5f, 1.0f}, 0xff00ff00},
15442 {{640.0f, 0.0f, 1.5f, 1.0f}, 0xff00ff00},
15444 IDirect3DDevice9 *device;
15445 IDirect3D9 *d3d;
15446 D3DCOLOR color;
15447 ULONG refcount;
15448 D3DCAPS9 caps;
15449 HWND window;
15450 HRESULT hr;
15451 UINT x, y;
15452 UINT i, j;
15454 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
15455 0, 0, 640, 480, NULL, NULL, NULL, NULL);
15456 d3d = Direct3DCreate9(D3D_SDK_VERSION);
15457 ok(!!d3d, "Failed to create a D3D object.\n");
15458 if (!(device = create_device(d3d, window, window, TRUE)))
15460 skip("Failed to create a D3D device, skipping tests.\n");
15461 goto done;
15464 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ZENABLE, D3DZB_FALSE);
15465 ok(SUCCEEDED(hr), "Failed to disable z-buffering, hr %#x.\n", hr);
15466 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZRHW | D3DFVF_DIFFUSE);
15467 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
15469 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffff0000, 0.0f, 0);
15470 ok(SUCCEEDED(hr), "Failed to clear render target, hr %#x.\n", hr);
15471 hr = IDirect3DDevice9_BeginScene(device);
15472 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
15473 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, tquad, sizeof(*tquad));
15474 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
15475 hr = IDirect3DDevice9_EndScene(device);
15476 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
15478 for (i = 0; i < 4; ++i)
15480 for (j = 0; j < 4; ++j)
15482 x = 80 * ((2 * j) + 1);
15483 y = 60 * ((2 * i) + 1);
15484 color = getPixelColor(device, x, y);
15485 ok(color_match(color, 0x0000ff00, 1),
15486 "Expected color 0x0000ff00 at %u, %u, got 0x%08x.\n", x, y, color);
15490 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
15491 ok(SUCCEEDED(hr), "Failed to present backbuffer, hr %#x.\n", hr);
15493 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
15494 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
15496 if (caps.PixelShaderVersion >= D3DPS_VERSION(1, 1)
15497 && caps.VertexShaderVersion >= D3DVS_VERSION(1, 1))
15499 static const DWORD vs_code[] =
15501 0xfffe0101, /* vs_1_1 */
15502 0x0000001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
15503 0x00000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
15504 0x00000001, 0xd00f0000, 0x90e40000, /* mov oD0, v0 */
15505 0x0000ffff
15507 static const DWORD ps_code[] =
15509 0xffff0101, /* ps_1_1 */
15510 0x00000001, 0x800f0000, 0x90e40000, /* mov r0, v0 */
15511 0x0000ffff /* end */
15513 static const struct vec3 quad[] =
15515 {-1.0f, -1.0f, -0.5f},
15516 {-1.0f, 1.0f, -0.5f},
15517 { 1.0f, -1.0f, 1.5f},
15518 { 1.0f, 1.0f, 1.5f},
15520 static const D3DCOLOR expected[] =
15522 0x00ff0000, 0x0060df60, 0x009fdf9f, 0x00ff0000,
15523 0x00ff0000, 0x00609f60, 0x009f9f9f, 0x00ff0000,
15524 0x00ff0000, 0x00606060, 0x009f609f, 0x00ff0000,
15525 0x00ff0000, 0x00602060, 0x009f209f, 0x00ff0000,
15527 /* The Windows 8 testbot (WARP) appears to not clip z for regular
15528 * vertices either. */
15529 static const D3DCOLOR expected_broken[] =
15531 0x0020df20, 0x0060df60, 0x009fdf9f, 0x00dfdfdf,
15532 0x00209f20, 0x00609f60, 0x009f9f9f, 0x00df9fdf,
15533 0x00206020, 0x00606060, 0x009f609f, 0x00df60df,
15534 0x00202020, 0x00602060, 0x009f209f, 0x00df20df,
15537 IDirect3DVertexShader9 *vs;
15538 IDirect3DPixelShader9 *ps;
15540 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ);
15541 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
15542 hr = IDirect3DDevice9_CreateVertexShader(device, vs_code, &vs);
15543 ok(SUCCEEDED(hr), "Failed to create vertex shader, hr %#x.\n", hr);
15544 hr = IDirect3DDevice9_CreatePixelShader(device, ps_code, &ps);
15545 ok(SUCCEEDED(hr), "Failed to create pixel shader, hr %#x.\n", hr);
15546 hr = IDirect3DDevice9_SetVertexShader(device, vs);
15547 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
15548 hr = IDirect3DDevice9_SetPixelShader(device, ps);
15549 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
15551 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xffff0000, 0.0f, 0);
15552 ok(SUCCEEDED(hr), "Failed to clear render target, hr %#x.\n", hr);
15553 hr = IDirect3DDevice9_BeginScene(device);
15554 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
15555 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
15556 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
15557 hr = IDirect3DDevice9_EndScene(device);
15558 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
15560 for (i = 0; i < 4; ++i)
15562 for (j = 0; j < 4; ++j)
15564 x = 80 * ((2 * j) + 1);
15565 y = 60 * ((2 * i) + 1);
15566 color = getPixelColor(device, x, y);
15567 ok(color_match(color, expected[i * 4 + j], 1)
15568 || broken(color_match(color, expected_broken[i * 4 + j], 1)),
15569 "Expected color 0x%08x at %u, %u, got 0x%08x.\n", expected[i * 4 + j], x, y, color);
15573 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
15574 ok(SUCCEEDED(hr), "Failed to present backbuffer, hr %#x.\n", hr);
15576 IDirect3DPixelShader9_Release(ps);
15577 IDirect3DVertexShader9_Release(vs);
15580 refcount = IDirect3DDevice9_Release(device);
15581 ok(!refcount, "Device has %u references left.\n", refcount);
15582 done:
15583 IDirect3D9_Release(d3d);
15584 DestroyWindow(window);
15587 static void fog_special_test(void)
15589 static const struct
15591 struct vec3 position;
15592 D3DCOLOR diffuse;
15594 quad[] =
15596 {{ -1.0f, -1.0f, 0.0f}, 0xff00ff00},
15597 {{ -1.0f, 1.0f, 0.0f}, 0xff00ff00},
15598 {{ 1.0f, -1.0f, 1.0f}, 0xff00ff00},
15599 {{ 1.0f, 1.0f, 1.0f}, 0xff00ff00}
15601 static const struct
15603 DWORD vertexmode, tablemode;
15604 BOOL vs, ps;
15605 D3DCOLOR color_left, color_right;
15607 tests[] =
15609 {D3DFOG_LINEAR, D3DFOG_NONE, FALSE, FALSE, 0x00ff0000, 0x00ff0000},
15610 {D3DFOG_LINEAR, D3DFOG_NONE, FALSE, TRUE, 0x00ff0000, 0x00ff0000},
15611 {D3DFOG_LINEAR, D3DFOG_NONE, TRUE, FALSE, 0x00ff0000, 0x00ff0000},
15612 {D3DFOG_LINEAR, D3DFOG_NONE, TRUE, TRUE, 0x00ff0000, 0x00ff0000},
15614 {D3DFOG_NONE, D3DFOG_LINEAR, FALSE, FALSE, 0x0000ff00, 0x00ff0000},
15615 {D3DFOG_NONE, D3DFOG_LINEAR, FALSE, TRUE, 0x0000ff00, 0x00ff0000},
15616 {D3DFOG_NONE, D3DFOG_LINEAR, TRUE, FALSE, 0x0000ff00, 0x00ff0000},
15617 {D3DFOG_NONE, D3DFOG_LINEAR, TRUE, TRUE, 0x0000ff00, 0x00ff0000},
15619 static const DWORD pixel_shader_code[] =
15621 0xffff0101, /* ps_1_1 */
15622 0x00000001, 0x800f0000, 0x90e40000, /* mov r0, v0 */
15623 0x0000ffff
15625 static const DWORD vertex_shader_code[] =
15627 0xfffe0101, /* vs_1_1 */
15628 0x0000001f, 0x80000000, 0x900f0000, /* dcl_position v0 */
15629 0x0000001f, 0x8000000a, 0x900f0001, /* dcl_color0 v1 */
15630 0x00000001, 0xc00f0000, 0x90e40000, /* mov oPos, v0 */
15631 0x00000001, 0xd00f0000, 0x90e40001, /* mov oD0, v1 */
15632 0x0000ffff
15634 static const D3DMATRIX identity =
15636 1.0f, 0.0f, 0.0f, 0.0f,
15637 0.0f, 1.0f, 0.0f, 0.0f,
15638 0.0f, 0.0f, 1.0f, 0.0f,
15639 0.0f, 0.0f, 0.0f, 1.0f,
15640 }}};
15641 union
15643 float f;
15644 DWORD d;
15645 } conv;
15646 DWORD color;
15647 HRESULT hr;
15648 unsigned int i;
15649 IDirect3DPixelShader9 *ps;
15650 IDirect3DVertexShader9 *vs;
15651 IDirect3DDevice9 *device;
15652 IDirect3D9 *d3d;
15653 ULONG refcount;
15654 D3DCAPS9 caps;
15655 HWND window;
15657 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
15658 0, 0, 640, 480, NULL, NULL, NULL, NULL);
15659 d3d = Direct3DCreate9(D3D_SDK_VERSION);
15660 ok(!!d3d, "Failed to create a D3D object.\n");
15661 if (!(device = create_device(d3d, window, window, TRUE)))
15663 skip("Failed to create a D3D device, skipping tests.\n");
15664 goto done;
15667 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
15668 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
15669 if (caps.VertexShaderVersion >= D3DVS_VERSION(1, 1))
15671 hr = IDirect3DDevice9_CreateVertexShader(device, vertex_shader_code, &vs);
15672 ok(SUCCEEDED(hr), "Failed to create vertex shader, hr %#x.\n", hr);
15674 else
15676 skip("Vertex Shaders not supported, skipping some fog tests.\n");
15677 vs = NULL;
15679 if (caps.PixelShaderVersion >= D3DPS_VERSION(1, 1))
15681 hr = IDirect3DDevice9_CreatePixelShader(device, pixel_shader_code, &ps);
15682 ok(SUCCEEDED(hr), "Failed to create pixel shader, hr %#x.\n", hr);
15684 else
15686 skip("Pixel Shaders not supported, skipping some fog tests.\n");
15687 ps = NULL;
15690 /* The table fog tests seem to depend on the projection matrix explicitly
15691 * being set to an identity matrix, even though that's the default.
15692 * (AMD Radeon HD 6310, Windows 7) */
15693 hr = IDirect3DDevice9_SetTransform(device, D3DTS_PROJECTION, &identity);
15694 ok(SUCCEEDED(hr), "Failed to set projection transform, hr %#x.\n", hr);
15696 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
15697 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
15698 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
15699 ok(SUCCEEDED(hr), "Failed to disable lighting, hr %#x.\n", hr);
15700 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGENABLE, TRUE);
15701 ok(SUCCEEDED(hr), "Failed to enable fog, hr %#x.\n", hr);
15702 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGCOLOR, 0xffff0000);
15703 ok(SUCCEEDED(hr), "Failed to set fog color, hr %#x.\n", hr);
15705 conv.f = 0.5f;
15706 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGSTART, conv.d);
15707 ok(SUCCEEDED(hr), "Failed to set fog start, hr %#x.\n", hr);
15708 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGEND, conv.d);
15709 ok(SUCCEEDED(hr), "Failed to set fog end, hr %#x.\n", hr);
15711 for (i = 0; i < sizeof(tests) / sizeof(*tests); i++)
15713 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff0000ff, 1.0f, 0);
15714 ok(SUCCEEDED(hr), "Failed to clear render target, hr %#x.\n", hr);
15716 if (!tests[i].vs)
15718 hr = IDirect3DDevice9_SetVertexShader(device, NULL);
15719 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
15721 else if (vs)
15723 hr = IDirect3DDevice9_SetVertexShader(device, vs);
15724 ok(SUCCEEDED(hr), "Failed to set vertex shader, hr %#x.\n", hr);
15726 else
15728 continue;
15731 if (!tests[i].ps)
15733 hr = IDirect3DDevice9_SetPixelShader(device, NULL);
15734 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
15736 else if (ps)
15738 hr = IDirect3DDevice9_SetPixelShader(device, ps);
15739 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
15741 else
15743 continue;
15746 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGVERTEXMODE, tests[i].vertexmode);
15747 ok(SUCCEEDED(hr), "Failed to set fogvertexmode, hr %#x.\n", hr);
15748 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_FOGTABLEMODE, tests[i].tablemode);
15749 ok(SUCCEEDED(hr), "Failed to set fogtablemode, hr %#x.\n", hr);
15751 hr = IDirect3DDevice9_BeginScene(device);
15752 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
15753 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
15754 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
15755 hr = IDirect3DDevice9_EndScene(device);
15756 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
15758 color = getPixelColor(device, 310, 240);
15759 ok(color_match(color, tests[i].color_left, 1),
15760 "Expected left color 0x%08x, got 0x%08x, case %u.\n", tests[i].color_left, color, i);
15761 color = getPixelColor(device, 330, 240);
15762 ok(color_match(color, tests[i].color_right, 1),
15763 "Expected right color 0x%08x, got 0x%08x, case %u.\n", tests[i].color_right, color, i);
15765 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
15766 ok(SUCCEEDED(hr), "Failed to present backbuffer, hr %#x.\n", hr);
15769 if (vs)
15770 IDirect3DVertexShader9_Release(vs);
15771 if (ps)
15772 IDirect3DPixelShader9_Release(ps);
15773 refcount = IDirect3DDevice9_Release(device);
15774 ok(!refcount, "Device has %u references left.\n", refcount);
15775 done:
15776 IDirect3D9_Release(d3d);
15777 DestroyWindow(window);
15780 static void volume_srgb_test(void)
15782 HRESULT hr;
15783 unsigned int i, j;
15784 IDirect3DVolumeTexture9 *tex1, *tex2;
15785 D3DPOOL pool;
15786 D3DLOCKED_BOX locked_box;
15787 IDirect3DDevice9 *device;
15788 IDirect3D9 *d3d;
15789 D3DCOLOR color;
15790 ULONG refcount;
15791 HWND window;
15793 static const struct
15795 BOOL srgb;
15796 DWORD color;
15798 tests[] =
15800 /* Try toggling on and off */
15801 { FALSE, 0x007f7f7f },
15802 { TRUE, 0x00363636 },
15803 { FALSE, 0x007f7f7f },
15805 static const struct
15807 struct vec3 pos;
15808 struct vec3 texcrd;
15810 quad[] =
15812 {{-1.0f, -1.0f, 0.0f}, {0.0f, 0.0f, 0.0f}},
15813 {{-1.0f, 1.0f, 0.0f}, {0.0f, 0.0f, 0.0f}},
15814 {{ 1.0f, -1.0f, 0.0f}, {0.0f, 0.0f, 0.0f}},
15815 {{ 1.0f, 1.0f, 0.0f}, {0.0f, 0.0f, 0.0f}},
15818 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
15819 0, 0, 640, 480, NULL, NULL, NULL, NULL);
15820 d3d = Direct3DCreate9(D3D_SDK_VERSION);
15821 ok(!!d3d, "Failed to create a D3D object.\n");
15822 if (IDirect3D9_CheckDeviceFormat(d3d, 0, D3DDEVTYPE_HAL, D3DFMT_X8R8G8B8,
15823 D3DUSAGE_QUERY_SRGBREAD, D3DRTYPE_VOLUMETEXTURE, D3DFMT_A8R8G8B8) != D3D_OK)
15825 skip("D3DFMT_A8R8G8B8 volume textures with SRGBREAD not supported.\n");
15826 goto done;
15828 if (!(device = create_device(d3d, window, window, TRUE)))
15830 skip("Failed to create a D3D device, skipping tests.\n");
15831 goto done;
15834 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
15835 ok(SUCCEEDED(hr), "Failed to set color op 0, hr %#x.\n", hr);
15836 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
15837 ok(SUCCEEDED(hr), "Failed to set color arg, hr %#x.\n", hr);
15838 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_COLOROP, D3DTOP_DISABLE);
15839 ok(SUCCEEDED(hr), "Failed to set color op 0, hr %#x.\n", hr);
15840 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1 | D3DFVF_TEXCOORDSIZE3(0));
15841 ok(SUCCEEDED(hr), "Failed to set fvf, hr %#x.\n", hr);
15843 for (i = 0; i < 2; i++)
15845 if (!i)
15846 pool = D3DPOOL_SYSTEMMEM;
15847 else
15848 pool = D3DPOOL_MANAGED;
15850 hr = IDirect3DDevice9_CreateVolumeTexture(device, 1, 1, 1, 1, 0, D3DFMT_A8R8G8B8, pool, &tex1, NULL);
15851 ok(SUCCEEDED(hr), "Failed to create volume texture, hr %#x.\n", hr);
15852 hr = IDirect3DVolumeTexture9_LockBox(tex1, 0, &locked_box, NULL, 0);
15853 ok(SUCCEEDED(hr), "Failed to lock volume texture, hr %#x.\n", hr);
15854 *((DWORD *)locked_box.pBits) = 0x7f7f7f7f;
15855 hr = IDirect3DVolumeTexture9_UnlockBox(tex1, 0);
15856 ok(SUCCEEDED(hr), "Failed to lock volume texture, hr %#x.\n", hr);
15858 if (!i)
15860 hr = IDirect3DDevice9_CreateVolumeTexture(device, 1, 1, 1, 1, 0,
15861 D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &tex2, NULL);
15862 ok(SUCCEEDED(hr), "Failed to create volume texture, hr %#x.\n", hr);
15863 hr = IDirect3DDevice9_UpdateTexture(device, (IDirect3DBaseTexture9 *)tex1, (IDirect3DBaseTexture9 *)tex2);
15864 ok(SUCCEEDED(hr), "Failed to update texture, hr %#x.\n", hr);
15865 IDirect3DVolumeTexture9_Release(tex1);
15867 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)tex2);
15868 ok(SUCCEEDED(hr), "Failed to set texture, hr %#x.\n", hr);
15869 IDirect3DVolumeTexture9_Release(tex2);
15871 else
15873 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)tex1);
15874 ok(SUCCEEDED(hr), "Failed to set texture, hr %#x.\n", hr);
15875 IDirect3DVolumeTexture9_Release(tex1);
15878 for (j = 0; j < sizeof(tests) / sizeof(*tests); j++)
15880 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_SRGBTEXTURE, tests[j].srgb);
15881 ok(SUCCEEDED(hr), "Failed to set srgb state, hr %#x.\n", hr);
15883 hr = IDirect3DDevice9_BeginScene(device);
15884 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
15885 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
15886 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
15887 hr = IDirect3DDevice9_EndScene(device);
15888 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
15890 color = getPixelColor(device, 320, 240);
15891 ok(color_match(color, tests[j].color, 2),
15892 "Expected color 0x%08x, got 0x%08x, i = %u, j = %u.\n", tests[j].color, color, i, j);
15894 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
15895 ok(SUCCEEDED(hr), "Failed to present backbuffer, hr %#x.\n", hr);
15899 refcount = IDirect3DDevice9_Release(device);
15900 ok(!refcount, "Device has %u references left.\n", refcount);
15901 done:
15902 IDirect3D9_Release(d3d);
15903 DestroyWindow(window);
15906 static void volume_dxt5_test(void)
15908 IDirect3DVolumeTexture9 *texture;
15909 IDirect3DDevice9 *device;
15910 D3DLOCKED_BOX box;
15911 IDirect3D9 *d3d;
15912 unsigned int i;
15913 ULONG refcount;
15914 DWORD color;
15915 HWND window;
15916 HRESULT hr;
15918 static const char texture_data[] =
15920 /* A 8x4x2 texture consisting of 4 4x4 blocks. The colors of the blocks are red, green, blue and white. */
15921 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xf8, 0x00, 0xf8, 0x00, 0x00, 0x00, 0x00,
15922 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xe0, 0x07, 0xe0, 0x07, 0x00, 0x00, 0x00, 0x00,
15923 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1f, 0x00, 0x1f, 0x00, 0x00, 0x00, 0x00, 0x00,
15924 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00
15926 static const struct
15928 struct vec3 position;
15929 struct vec3 texcrd;
15931 quads[] =
15933 {{ -1.0f, -1.0f, 0.0f}, { 0.0f, 0.0f, 0.25f}},
15934 {{ -1.0f, 1.0f, 0.0f}, { 0.0f, 1.0f, 0.25f}},
15935 {{ 0.0f, -1.0f, 1.0f}, { 1.0f, 0.0f, 0.25f}},
15936 {{ 0.0f, 1.0f, 1.0f}, { 1.0f, 1.0f, 0.25f}},
15938 {{ 0.0f, -1.0f, 0.0f}, { 0.0f, 0.0f, 0.75f}},
15939 {{ 0.0f, 1.0f, 0.0f}, { 0.0f, 1.0f, 0.75f}},
15940 {{ 1.0f, -1.0f, 1.0f}, { 1.0f, 0.0f, 0.75f}},
15941 {{ 1.0f, 1.0f, 1.0f}, { 1.0f, 1.0f, 0.75f}},
15943 static const DWORD expected_colors[] = {0x00ff0000, 0x0000ff00, 0x000000ff, 0x00ffffff};
15945 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
15946 0, 0, 640, 480, NULL, NULL, NULL, NULL);
15947 d3d = Direct3DCreate9(D3D_SDK_VERSION);
15948 ok(!!d3d, "Failed to create a D3D object.\n");
15949 if (FAILED(IDirect3D9_CheckDeviceFormat(d3d, D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL,
15950 D3DFMT_X8R8G8B8, 0, D3DRTYPE_VOLUMETEXTURE, D3DFMT_DXT5)))
15952 skip("DXT5 volume textures are not supported, skipping test.\n");
15953 goto done;
15955 if (!(device = create_device(d3d, window, window, TRUE)))
15957 skip("Failed to create a D3D device, skipping tests.\n");
15958 goto done;
15961 hr = IDirect3DDevice9_CreateVolumeTexture(device, 8, 4, 2, 1, 0, D3DFMT_DXT5,
15962 D3DPOOL_MANAGED, &texture, NULL);
15963 ok(SUCCEEDED(hr), "Failed to create volume texture, hr %#x.\n", hr);
15965 hr = IDirect3DVolumeTexture9_LockBox(texture, 0, &box, NULL, 0);
15966 ok(SUCCEEDED(hr), "Failed to lock volume texture, hr %#x.\n", hr);
15967 memcpy(box.pBits, texture_data, sizeof(texture_data));
15968 hr = IDirect3DVolumeTexture9_UnlockBox(texture, 0);
15969 ok(SUCCEEDED(hr), "Failed to unlock volume texture, hr %#x.\n", hr);
15971 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1 | D3DFVF_TEXCOORDSIZE3(0));
15972 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
15973 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)texture);
15974 ok(SUCCEEDED(hr), "Failed to set texture, hr %#x.\n", hr);
15975 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
15976 ok(SUCCEEDED(hr), "Failed to set color op, hr %#x.\n", hr);
15977 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
15978 ok(SUCCEEDED(hr), "Failed to set color arg, hr %#x.\n", hr);
15979 hr = IDirect3DDevice9_SetTextureStageState(device, 1, D3DTSS_COLOROP, D3DTOP_DISABLE);
15980 ok(SUCCEEDED(hr), "Failed to set color op, hr %#x.\n", hr);
15981 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAGFILTER, D3DTEXF_POINT);
15982 ok(SUCCEEDED(hr), "Failed to set mag filter, hr %#x.\n", hr);
15984 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x00ff00ff, 1.0f, 0);
15985 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
15986 hr = IDirect3DDevice9_BeginScene(device);
15987 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
15988 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quads[0], sizeof(*quads));
15989 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
15990 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quads[4], sizeof(*quads));
15991 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
15992 hr = IDirect3DDevice9_EndScene(device);
15993 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
15995 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
15996 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
15997 for (i = 0; i < 4; i++)
15999 color = getPixelColor(device, 80 + 160 * i, 240);
16000 ok (color_match(color, expected_colors[i], 1),
16001 "Expected color 0x%08x, got 0x%08x, case %u.\n", expected_colors[i], color, i);
16004 IDirect3DVolumeTexture9_Release(texture);
16005 refcount = IDirect3DDevice9_Release(device);
16006 ok(!refcount, "Device has %u references left.\n", refcount);
16007 done:
16008 IDirect3D9_Release(d3d);
16009 DestroyWindow(window);
16012 static void volume_v16u16_test(void)
16014 IDirect3DVolumeTexture9 *texture;
16015 IDirect3DPixelShader9 *shader;
16016 IDirect3DDevice9 *device;
16017 D3DLOCKED_BOX box;
16018 IDirect3D9 *d3d;
16019 unsigned int i;
16020 ULONG refcount;
16021 D3DCAPS9 caps;
16022 SHORT *texel;
16023 DWORD color;
16024 HWND window;
16025 HRESULT hr;
16027 static const struct
16029 struct vec3 position;
16030 struct vec3 texcrd;
16032 quads[] =
16034 {{ -1.0f, -1.0f, 0.0f}, { 0.0f, 0.0f, 0.25f}},
16035 {{ -1.0f, 1.0f, 0.0f}, { 0.0f, 1.0f, 0.25f}},
16036 {{ 0.0f, -1.0f, 1.0f}, { 1.0f, 0.0f, 0.25f}},
16037 {{ 0.0f, 1.0f, 1.0f}, { 1.0f, 1.0f, 0.25f}},
16039 {{ 0.0f, -1.0f, 0.0f}, { 0.0f, 0.0f, 0.75f}},
16040 {{ 0.0f, 1.0f, 0.0f}, { 0.0f, 1.0f, 0.75f}},
16041 {{ 1.0f, -1.0f, 1.0f}, { 1.0f, 0.0f, 0.75f}},
16042 {{ 1.0f, 1.0f, 1.0f}, { 1.0f, 1.0f, 0.75f}},
16044 static const DWORD shader_code[] =
16046 0xffff0101, /* ps_1_1 */
16047 0x00000051, 0xa00f0000, 0x3f000000, 0x3f000000, /* def c0, 0.5, 0.5, */
16048 0x3f000000, 0x3f000000, /* 0.5, 0.5 */
16049 0x00000042, 0xb00f0000, /* tex t0 */
16050 0x00000004, 0x800f0000, 0xb0e40000, 0xa0e40000, 0xa0e40000, /* mad r0, t0, c0, c0 */
16051 0x0000ffff /* end */
16054 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
16055 0, 0, 640, 480, NULL, NULL, NULL, NULL);
16056 d3d = Direct3DCreate9(D3D_SDK_VERSION);
16057 ok(!!d3d, "Failed to create a D3D object.\n");
16058 if (!(device = create_device(d3d, window, window, TRUE)))
16060 skip("Failed to create a D3D device, skipping tests.\n");
16061 goto done;
16064 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
16065 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
16066 if (caps.PixelShaderVersion < D3DPS_VERSION(1, 1))
16068 skip("No ps_1_1 support, skipping tests.\n");
16069 IDirect3DDevice9_Release(device);
16070 goto done;
16072 if (FAILED(IDirect3D9_CheckDeviceFormat(d3d, D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL,
16073 D3DFMT_X8R8G8B8, 0, D3DRTYPE_VOLUMETEXTURE, D3DFMT_V16U16)))
16075 skip("Volume V16U16 textures are not supported, skipping test.\n");
16076 IDirect3DDevice9_Release(device);
16077 goto done;
16080 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1 | D3DFVF_TEXCOORDSIZE3(0));
16081 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
16082 hr = IDirect3DDevice9_CreatePixelShader(device, shader_code, &shader);
16083 ok(SUCCEEDED(hr), "Failed to create pixel shader, hr %#x.\n", hr);
16084 hr = IDirect3DDevice9_SetPixelShader(device, shader);
16085 ok(SUCCEEDED(hr), "Failed to set pixel shader, hr %#x.\n", hr);
16086 hr = IDirect3DDevice9_SetSamplerState(device, 0, D3DSAMP_MAGFILTER, D3DTEXF_POINT);
16087 ok(SUCCEEDED(hr), "Failed to set filter, hr %#x.\n", hr);
16089 for (i = 0; i < 2; i++)
16091 D3DPOOL pool;
16093 if (i)
16094 pool = D3DPOOL_SYSTEMMEM;
16095 else
16096 pool = D3DPOOL_MANAGED;
16098 hr = IDirect3DDevice9_CreateVolumeTexture(device, 1, 2, 2, 1, 0, D3DFMT_V16U16,
16099 pool, &texture, NULL);
16100 ok(SUCCEEDED(hr), "Failed to create volume texture, hr %#x.\n", hr);
16102 hr = IDirect3DVolumeTexture9_LockBox(texture, 0, &box, NULL, 0);
16103 ok(SUCCEEDED(hr), "Failed to lock volume texture, hr %#x.\n", hr);
16105 texel = (SHORT *)((BYTE *)box.pBits + 0 * box.RowPitch + 0 * box.SlicePitch);
16106 texel[0] = 32767;
16107 texel[1] = 32767;
16108 texel = (SHORT *)((BYTE *)box.pBits + 1 * box.RowPitch + 0 * box.SlicePitch);
16109 texel[0] = -32768;
16110 texel[1] = 0;
16111 texel = (SHORT *)((BYTE *)box.pBits + 0 * box.RowPitch + 1 * box.SlicePitch);
16112 texel[0] = -16384;
16113 texel[1] = 16384;
16114 texel = (SHORT *)((BYTE *)box.pBits + 1 * box.RowPitch + 1 * box.SlicePitch);
16115 texel[0] = 0;
16116 texel[1] = 0;
16118 hr = IDirect3DVolumeTexture9_UnlockBox(texture, 0);
16119 ok(SUCCEEDED(hr), "Failed to unlock volume texture, hr %#x.\n", hr);
16121 if (i)
16123 IDirect3DVolumeTexture9 *texture2;
16125 hr = IDirect3DDevice9_CreateVolumeTexture(device, 1, 2, 2, 1, 0, D3DFMT_V16U16,
16126 D3DPOOL_DEFAULT, &texture2, NULL);
16127 ok(SUCCEEDED(hr), "Failed to create volume texture, hr %#x.\n", hr);
16129 hr = IDirect3DDevice9_UpdateTexture(device, (IDirect3DBaseTexture9 *)texture,
16130 (IDirect3DBaseTexture9 *)texture2);
16131 ok(SUCCEEDED(hr), "Failed to update texture, hr %#x.\n", hr);
16133 IDirect3DVolumeTexture9_Release(texture);
16134 texture = texture2;
16137 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *) texture);
16138 ok(SUCCEEDED(hr), "Failed to set texture, hr %#x.\n", hr);
16140 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x00ff00ff, 1.0f, 0);
16141 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
16142 hr = IDirect3DDevice9_BeginScene(device);
16143 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
16144 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quads[0], sizeof(*quads));
16145 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
16146 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quads[4], sizeof(*quads));
16147 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
16148 hr = IDirect3DDevice9_EndScene(device);
16149 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
16151 color = getPixelColor(device, 120, 160);
16152 ok (color_match(color, 0x000080ff, 2),
16153 "Expected color 0x000080ff, got 0x%08x, V16U16 input -32768, 0.\n", color);
16154 color = getPixelColor(device, 120, 400);
16155 ok (color_match(color, 0x00ffffff, 2),
16156 "Expected color 0x00ffffff, got 0x%08x, V16U16 input 32767, 32767.\n", color);
16157 color = getPixelColor(device, 360, 160);
16158 ok (color_match(color, 0x007f7fff, 2),
16159 "Expected color 0x007f7fff, got 0x%08x, V16U16 input 0, 0.\n", color);
16160 color = getPixelColor(device, 360, 400);
16161 ok (color_match(color, 0x0040c0ff, 2),
16162 "Expected color 0x0040c0ff, got 0x%08x, V16U16 input -16384, 16384.\n", color);
16164 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16165 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16167 IDirect3DVolumeTexture9_Release(texture);
16170 IDirect3DPixelShader9_Release(shader);
16171 refcount = IDirect3DDevice9_Release(device);
16172 ok(!refcount, "Device has %u references left.\n", refcount);
16173 done:
16174 IDirect3D9_Release(d3d);
16175 DestroyWindow(window);
16178 static void add_dirty_rect_test_draw(IDirect3DDevice9 *device)
16180 HRESULT hr;
16181 static const struct
16183 struct vec3 position;
16184 struct vec2 texcoord;
16186 quad[] =
16188 {{-1.0, -1.0, 0.0}, {0.0, 0.0}},
16189 {{-1.0, 1.0, 0.0}, {0.0, 1.0}},
16190 {{ 1.0, -1.0, 0.0}, {1.0, 0.0}},
16191 {{ 1.0, 1.0, 0.0}, {1.0, 1.0}},
16194 hr = IDirect3DDevice9_BeginScene(device);
16195 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
16196 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, &quad, sizeof(*quad));
16197 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
16198 hr = IDirect3DDevice9_EndScene(device);
16199 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
16202 static void add_dirty_rect_test(void)
16204 HRESULT hr;
16205 IDirect3DTexture9 *tex_dst1, *tex_dst2, *tex_src_red, *tex_src_green, *tex_managed;
16206 IDirect3DSurface9 *surface_dst2, *surface_src_green, *surface_src_red, *surface_managed;
16207 IDirect3DDevice9 *device;
16208 IDirect3D9 *d3d;
16209 unsigned int i;
16210 ULONG refcount;
16211 DWORD *texel;
16212 HWND window;
16213 D3DLOCKED_RECT locked_rect;
16214 static const RECT part_rect = {96, 96, 160, 160};
16215 DWORD color;
16217 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
16218 0, 0, 640, 480, NULL, NULL, NULL, NULL);
16219 d3d = Direct3DCreate9(D3D_SDK_VERSION);
16220 ok(!!d3d, "Failed to create a D3D object.\n");
16221 if (!(device = create_device(d3d, window, window, TRUE)))
16223 skip("Failed to create a D3D device, skipping tests.\n");
16224 IDirect3D9_Release(d3d);
16225 DestroyWindow(window);
16226 return;
16229 hr = IDirect3DDevice9_CreateTexture(device, 256, 256, 1, 0, D3DFMT_X8R8G8B8,
16230 D3DPOOL_DEFAULT, &tex_dst1, NULL);
16231 ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);
16232 hr = IDirect3DDevice9_CreateTexture(device, 256, 256, 1, 0, D3DFMT_X8R8G8B8,
16233 D3DPOOL_DEFAULT, &tex_dst2, NULL);
16234 ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);
16235 hr = IDirect3DDevice9_CreateTexture(device, 256, 256, 1, 0, D3DFMT_X8R8G8B8,
16236 D3DPOOL_SYSTEMMEM, &tex_src_red, NULL);
16237 ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);
16238 hr = IDirect3DDevice9_CreateTexture(device, 256, 256, 1, 0, D3DFMT_X8R8G8B8,
16239 D3DPOOL_SYSTEMMEM, &tex_src_green, NULL);
16240 ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);
16241 hr = IDirect3DDevice9_CreateTexture(device, 256, 256, 1, 0, D3DFMT_X8R8G8B8,
16242 D3DPOOL_MANAGED, &tex_managed, NULL);
16243 ok(SUCCEEDED(hr), "Failed to create texture, hr %#x.\n", hr);
16245 hr = IDirect3DTexture9_GetSurfaceLevel(tex_dst2, 0, &surface_dst2);
16246 ok(SUCCEEDED(hr), "Failed to get surface level, hr %#x.\n", hr);
16247 hr = IDirect3DTexture9_GetSurfaceLevel(tex_src_green, 0, &surface_src_green);
16248 ok(SUCCEEDED(hr), "Failed to get surface level, hr %#x.\n", hr);
16249 hr = IDirect3DTexture9_GetSurfaceLevel(tex_src_red, 0, &surface_src_red);
16250 ok(SUCCEEDED(hr), "Failed to get surface level, hr %#x.\n", hr);
16251 hr = IDirect3DTexture9_GetSurfaceLevel(tex_managed, 0, &surface_managed);
16252 ok(SUCCEEDED(hr), "Failed to get surface level, hr %#x.\n", hr);
16254 fill_surface(surface_src_red, 0x00ff0000, 0);
16255 fill_surface(surface_src_green, 0x0000ff00, 0);
16257 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_TEX1);
16258 ok(SUCCEEDED(hr), "Failed to set fvf, hr %#x.\n", hr);
16259 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
16260 ok(SUCCEEDED(hr), "Failed to set color op, hr %#x.\n", hr);
16261 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
16262 ok(SUCCEEDED(hr), "Failed to set color arg, hr %#x.\n", hr);
16264 hr = IDirect3DDevice9_UpdateTexture(device, (IDirect3DBaseTexture9 *)tex_src_green,
16265 (IDirect3DBaseTexture9 *)tex_dst1);
16266 ok(SUCCEEDED(hr), "Failed to update texture, hr %#x.\n", hr);
16268 /* The second UpdateTexture call writing to tex_dst2 is ignored because tex_src_green is not dirty. */
16269 hr = IDirect3DDevice9_UpdateTexture(device, (IDirect3DBaseTexture9 *)tex_src_red,
16270 (IDirect3DBaseTexture9 *)tex_dst2);
16271 ok(SUCCEEDED(hr), "Failed to update texture, hr %#x.\n", hr);
16272 hr = IDirect3DDevice9_UpdateTexture(device, (IDirect3DBaseTexture9 *)tex_src_green,
16273 (IDirect3DBaseTexture9 *)tex_dst2);
16274 ok(SUCCEEDED(hr), "Failed to update texture, hr %#x.\n", hr);
16276 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)tex_dst1);
16277 ok(SUCCEEDED(hr), "Failed to set texture, hr %#x.\n", hr);
16278 add_dirty_rect_test_draw(device);
16279 color = getPixelColor(device, 320, 240);
16280 ok(color_match(color, 0x0000ff00, 1),
16281 "Expected color 0x0000ff00, got 0x%08x.\n", color);
16282 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16283 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16285 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)tex_dst2);
16286 ok(SUCCEEDED(hr), "Failed to set texture, hr %#x.\n", hr);
16287 add_dirty_rect_test_draw(device);
16288 color = getPixelColor(device, 320, 240);
16289 todo_wine ok(color_match(color, 0x00ff0000, 1),
16290 "Expected color 0x00ff0000, got 0x%08x.\n", color);
16291 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16292 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16294 /* AddDirtyRect on the destination is ignored. */
16295 hr = IDirect3DTexture9_AddDirtyRect(tex_dst2, &part_rect);
16296 ok(SUCCEEDED(hr), "Failed to add dirty rect, hr %#x.\n", hr);
16297 hr = IDirect3DDevice9_UpdateTexture(device, (IDirect3DBaseTexture9 *)tex_src_green,
16298 (IDirect3DBaseTexture9 *)tex_dst2);
16299 ok(SUCCEEDED(hr), "Failed to update texture, hr %#x.\n", hr);
16300 add_dirty_rect_test_draw(device);
16301 color = getPixelColor(device, 320, 240);
16302 todo_wine ok(color_match(color, 0x00ff0000, 1),
16303 "Expected color 0x00ff0000, got 0x%08x.\n", color);
16304 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16305 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16307 hr = IDirect3DTexture9_AddDirtyRect(tex_dst2, NULL);
16308 ok(SUCCEEDED(hr), "Failed to add dirty rect, hr %#x.\n", hr);
16309 hr = IDirect3DDevice9_UpdateTexture(device, (IDirect3DBaseTexture9 *)tex_src_green,
16310 (IDirect3DBaseTexture9 *)tex_dst2);
16311 ok(SUCCEEDED(hr), "Failed to update texture, hr %#x.\n", hr);
16312 add_dirty_rect_test_draw(device);
16313 color = getPixelColor(device, 320, 240);
16314 todo_wine ok(color_match(color, 0x00ff0000, 1),
16315 "Expected color 0x00ff0000, got 0x%08x.\n", color);
16316 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16317 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16319 /* AddDirtyRect on the source makes UpdateTexture work. Partial rectangle
16320 * tracking is supported. */
16321 hr = IDirect3DTexture9_AddDirtyRect(tex_src_green, &part_rect);
16322 ok(SUCCEEDED(hr), "Failed to add dirty rect, hr %#x.\n", hr);
16323 hr = IDirect3DDevice9_UpdateTexture(device, (IDirect3DBaseTexture9 *)tex_src_green,
16324 (IDirect3DBaseTexture9 *)tex_dst2);
16325 ok(SUCCEEDED(hr), "Failed to update texture, hr %#x.\n", hr);
16326 add_dirty_rect_test_draw(device);
16327 color = getPixelColor(device, 320, 240);
16328 ok(color_match(color, 0x0000ff00, 1),
16329 "Expected color 0x0000ff00, got 0x%08x.\n", color);
16330 color = getPixelColor(device, 1, 1);
16331 todo_wine ok(color_match(color, 0x00ff0000, 1),
16332 "Expected color 0x00ff0000, got 0x%08x.\n", color);
16333 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16334 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16336 hr = IDirect3DTexture9_AddDirtyRect(tex_src_green, NULL);
16337 ok(SUCCEEDED(hr), "Failed to add dirty rect, hr %#x.\n", hr);
16338 hr = IDirect3DDevice9_UpdateTexture(device, (IDirect3DBaseTexture9 *)tex_src_green,
16339 (IDirect3DBaseTexture9 *)tex_dst2);
16340 ok(SUCCEEDED(hr), "Failed to update texture, hr %#x.\n", hr);
16341 add_dirty_rect_test_draw(device);
16342 color = getPixelColor(device, 1, 1);
16343 ok(color_match(color, 0x0000ff00, 1),
16344 "Expected color 0x0000ff00, got 0x%08x.\n", color);
16346 /* Locks with NO_DIRTY_UPDATE are ignored. */
16347 fill_surface(surface_src_green, 0x00000080, D3DLOCK_NO_DIRTY_UPDATE);
16348 hr = IDirect3DDevice9_UpdateTexture(device, (IDirect3DBaseTexture9 *)tex_src_green,
16349 (IDirect3DBaseTexture9 *)tex_dst2);
16350 ok(SUCCEEDED(hr), "Failed to update texture, hr %#x.\n", hr);
16351 add_dirty_rect_test_draw(device);
16352 color = getPixelColor(device, 320, 240);
16353 todo_wine ok(color_match(color, 0x0000ff00, 1),
16354 "Expected color 0x0000ff00, got 0x%08x.\n", color);
16355 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16356 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16358 /* Readonly maps write to D3DPOOL_SYSTEMMEM, but don't record a dirty rectangle. */
16359 fill_surface(surface_src_green, 0x000000ff, D3DLOCK_READONLY);
16360 hr = IDirect3DDevice9_UpdateTexture(device, (IDirect3DBaseTexture9 *)tex_src_green,
16361 (IDirect3DBaseTexture9 *)tex_dst2);
16362 ok(SUCCEEDED(hr), "Failed to update texture, hr %#x.\n", hr);
16363 add_dirty_rect_test_draw(device);
16364 color = getPixelColor(device, 320, 240);
16365 todo_wine ok(color_match(color, 0x0000ff00, 1),
16366 "Expected color 0x0000ff00, got 0x%08x.\n", color);
16367 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16368 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16370 hr = IDirect3DTexture9_AddDirtyRect(tex_src_green, NULL);
16371 hr = IDirect3DDevice9_UpdateTexture(device, (IDirect3DBaseTexture9 *)tex_src_green,
16372 (IDirect3DBaseTexture9 *)tex_dst2);
16373 ok(SUCCEEDED(hr), "Failed to update texture, hr %#x.\n", hr);
16374 add_dirty_rect_test_draw(device);
16375 color = getPixelColor(device, 320, 240);
16376 ok(color_match(color, 0x000000ff, 1),
16377 "Expected color 0x000000ff, got 0x%08x.\n", color);
16378 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16379 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16381 /* Maps without either of these flags record a dirty rectangle. */
16382 fill_surface(surface_src_green, 0x00ffffff, 0);
16383 hr = IDirect3DDevice9_UpdateTexture(device, (IDirect3DBaseTexture9 *)tex_src_green,
16384 (IDirect3DBaseTexture9 *)tex_dst2);
16385 ok(SUCCEEDED(hr), "Failed to update texture, hr %#x.\n", hr);
16386 add_dirty_rect_test_draw(device);
16387 color = getPixelColor(device, 320, 240);
16388 ok(color_match(color, 0x00ffffff, 1),
16389 "Expected color 0x00ffffff, got 0x%08x.\n", color);
16390 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16391 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16393 /* Partial LockRect works just like a partial AddDirtyRect call. */
16394 hr = IDirect3DTexture9_LockRect(tex_src_green, 0, &locked_rect, &part_rect, 0);
16395 ok(SUCCEEDED(hr), "Failed to lock texture, hr %#x.\n", hr);
16396 texel = locked_rect.pBits;
16397 for (i = 0; i < 64; i++)
16398 texel[i] = 0x00ff00ff;
16399 for (i = 1; i < 64; i++)
16400 memcpy((BYTE *)locked_rect.pBits + i * locked_rect.Pitch, locked_rect.pBits, locked_rect.Pitch);
16401 hr = IDirect3DTexture9_UnlockRect(tex_src_green, 0);
16402 ok(SUCCEEDED(hr), "Failed to unlock texture, hr %#x.\n", hr);
16403 hr = IDirect3DDevice9_UpdateTexture(device, (IDirect3DBaseTexture9 *)tex_src_green,
16404 (IDirect3DBaseTexture9 *)tex_dst2);
16405 ok(SUCCEEDED(hr), "Failed to update texture, hr %#x.\n", hr);
16406 add_dirty_rect_test_draw(device);
16407 color = getPixelColor(device, 320, 240);
16408 ok(color_match(color, 0x00ff00ff, 1),
16409 "Expected color 0x00ff00ff, got 0x%08x.\n", color);
16410 color = getPixelColor(device, 1, 1);
16411 ok(color_match(color, 0x00ffffff, 1),
16412 "Expected color 0x00ffffff, got 0x%08x.\n", color);
16413 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16414 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16416 fill_surface(surface_src_red, 0x00ff0000, 0);
16417 fill_surface(surface_src_green, 0x0000ff00, 0);
16419 hr = IDirect3DDevice9_UpdateTexture(device, (IDirect3DBaseTexture9 *)tex_src_green,
16420 (IDirect3DBaseTexture9 *)tex_dst1);
16421 ok(SUCCEEDED(hr), "Failed to update texture, hr %#x.\n", hr);
16422 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)tex_dst1);
16423 ok(SUCCEEDED(hr), "Failed to set texture, hr %#x.\n", hr);
16424 add_dirty_rect_test_draw(device);
16425 color = getPixelColor(device, 320, 240);
16426 ok(color_match(color, 0x0000ff00, 1),
16427 "Expected color 0x0000ff00, got 0x%08x.\n", color);
16428 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16429 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16431 /* UpdateSurface ignores the missing dirty marker. */
16432 hr = IDirect3DDevice9_UpdateTexture(device, (IDirect3DBaseTexture9 *)tex_src_red,
16433 (IDirect3DBaseTexture9 *)tex_dst2);
16434 hr = IDirect3DDevice9_UpdateSurface(device, surface_src_green, NULL, surface_dst2, NULL);
16435 ok(SUCCEEDED(hr), "Failed to update surface, hr %#x.\n", hr);
16436 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)tex_dst2);
16437 ok(SUCCEEDED(hr), "Failed to set texture, hr %#x.\n", hr);
16438 add_dirty_rect_test_draw(device);
16439 color = getPixelColor(device, 320, 240);
16440 ok(color_match(color, 0x0000ff00, 1),
16441 "Expected color 0x0000ff00, got 0x%08x.\n", color);
16442 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16443 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16445 fill_surface(surface_managed, 0x00ff0000, 0);
16446 hr = IDirect3DDevice9_SetTexture(device, 0, (IDirect3DBaseTexture9 *)tex_managed);
16447 ok(SUCCEEDED(hr), "Failed to set texture, hr %#x.\n", hr);
16448 add_dirty_rect_test_draw(device);
16449 color = getPixelColor(device, 320, 240);
16450 ok(color_match(color, 0x00ff0000, 1),
16451 "Expected color 0x00ff0000, got 0x%08x.\n", color);
16452 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16453 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16455 /* Managed textures also honor D3DLOCK_NO_DIRTY_UPDATE. */
16456 fill_surface(surface_managed, 0x0000ff00, D3DLOCK_NO_DIRTY_UPDATE);
16457 add_dirty_rect_test_draw(device);
16458 color = getPixelColor(device, 320, 240);
16459 ok(color_match(color, 0x00ff0000, 1),
16460 "Expected color 0x00ff0000, got 0x%08x.\n", color);
16461 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16462 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16464 /* AddDirtyRect uploads the new contents.
16465 * Side note, not tested in the test: Partial surface updates work, and two separate
16466 * dirty rectangles are tracked individually. Tested on Nvidia Kepler, other drivers
16467 * untested. */
16468 hr = IDirect3DTexture9_AddDirtyRect(tex_managed, NULL);
16469 ok(SUCCEEDED(hr), "Failed to add dirty rect, hr %#x.\n", hr);
16470 add_dirty_rect_test_draw(device);
16471 color = getPixelColor(device, 320, 240);
16472 ok(color_match(color, 0x0000ff00, 1),
16473 "Expected color 0x0000ff00, got 0x%08x.\n", color);
16474 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16475 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16477 /* So does EvictManagedResources. */
16478 fill_surface(surface_managed, 0x000000ff, D3DLOCK_NO_DIRTY_UPDATE);
16479 ok(SUCCEEDED(hr), "Failed to unlock texture, hr %#x.\n", hr);
16480 hr = IDirect3DDevice9_EvictManagedResources(device);
16481 ok(SUCCEEDED(hr), "Failed to evict managed resources, hr %#x.\n", hr);
16482 add_dirty_rect_test_draw(device);
16483 color = getPixelColor(device, 320, 240);
16484 ok(color_match(color, 0x000000ff, 1),
16485 "Expected color 0x000000ff, got 0x%08x.\n", color);
16486 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16487 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16489 /* AddDirtyRect on a locked texture is allowed. */
16490 hr = IDirect3DTexture9_LockRect(tex_src_red, 0, &locked_rect, NULL, 0);
16491 ok(SUCCEEDED(hr), "Failed to lock texture, hr %#x.\n", hr);
16492 hr = IDirect3DTexture9_AddDirtyRect(tex_src_red, NULL);
16493 ok(SUCCEEDED(hr), "Failed to add dirty rect, hr %#x.\n", hr);
16494 hr = IDirect3DTexture9_UnlockRect(tex_src_red, 0);
16495 ok(SUCCEEDED(hr), "Failed to unlock texture, hr %#x.\n", hr);
16497 /* Redundant AddDirtyRect calls are ok. */
16498 hr = IDirect3DTexture9_AddDirtyRect(tex_managed, NULL);
16499 ok(SUCCEEDED(hr), "Failed to add dirty rect, hr %#x.\n", hr);
16500 hr = IDirect3DTexture9_AddDirtyRect(tex_managed, NULL);
16501 ok(SUCCEEDED(hr), "Failed to add dirty rect, hr %#x.\n", hr);
16503 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_DISABLE);
16504 ok(SUCCEEDED(hr), "Failed to set color op, hr %#x.\n", hr);
16505 hr = IDirect3DDevice9_SetTexture(device, 0, NULL);
16506 ok(SUCCEEDED(hr), "Failed to set texture, hr %#x.\n", hr);
16507 IDirect3DSurface9_Release(surface_dst2);
16508 IDirect3DSurface9_Release(surface_managed);
16509 IDirect3DSurface9_Release(surface_src_red);
16510 IDirect3DSurface9_Release(surface_src_green);
16511 IDirect3DTexture9_Release(tex_src_red);
16512 IDirect3DTexture9_Release(tex_src_green);
16513 IDirect3DTexture9_Release(tex_dst1);
16514 IDirect3DTexture9_Release(tex_dst2);
16515 IDirect3DTexture9_Release(tex_managed);
16516 refcount = IDirect3DDevice9_Release(device);
16517 ok(!refcount, "Device has %u references left.\n", refcount);
16518 IDirect3D9_Release(d3d);
16519 DestroyWindow(window);
16522 static void test_per_stage_constant(void)
16524 IDirect3DDevice9 *device;
16525 IDirect3D9 *d3d;
16526 D3DCOLOR color;
16527 ULONG refcount;
16528 D3DCAPS9 caps;
16529 HWND window;
16530 HRESULT hr;
16532 static const struct
16534 struct vec3 position;
16535 D3DCOLOR diffuse;
16537 quad[] =
16539 {{-1.0f, -1.0f, 0.1f}, 0xffff0000},
16540 {{-1.0f, 1.0f, 0.1f}, 0xffff0000},
16541 {{ 1.0f, -1.0f, 0.1f}, 0xffff0000},
16542 {{ 1.0f, 1.0f, 0.1f}, 0xffff0000},
16545 window = CreateWindowA("static", "d3d9_test", WS_OVERLAPPEDWINDOW | WS_VISIBLE,
16546 0, 0, 640, 480, NULL, NULL, NULL, NULL);
16547 d3d = Direct3DCreate9(D3D_SDK_VERSION);
16548 ok(!!d3d, "Failed to create a D3D object.\n");
16549 if (!(device = create_device(d3d, window, window, TRUE)))
16551 skip("Failed to create a D3D device, skipping tests.\n");
16552 goto done;
16555 hr = IDirect3DDevice9_GetDeviceCaps(device, &caps);
16556 ok(SUCCEEDED(hr), "Failed to get device caps, hr %#x.\n", hr);
16557 if (!(caps.PrimitiveMiscCaps & D3DPMISCCAPS_PERSTAGECONSTANT))
16559 skip("Per-stage constants not supported, skipping tests.\n");
16560 IDirect3DDevice9_Release(device);
16561 goto done;
16564 hr = IDirect3DDevice9_SetFVF(device, D3DFVF_XYZ | D3DFVF_DIFFUSE);
16565 ok(SUCCEEDED(hr), "Failed to set FVF, hr %#x.\n", hr);
16566 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_ALPHABLENDENABLE, TRUE);
16567 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
16568 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_SRCBLEND, D3DBLEND_SRCALPHA);
16569 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
16570 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA);
16571 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
16572 hr = IDirect3DDevice9_SetRenderState(device, D3DRS_LIGHTING, FALSE);
16573 ok(SUCCEEDED(hr), "Failed to set render state, hr %#x.\n", hr);
16575 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_CONSTANT, 0x80a1b2c3);
16576 ok(SUCCEEDED(hr), "Failed to set texture stage state, hr %#x.\n", hr);
16577 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_CONSTANT);
16578 ok(SUCCEEDED(hr), "Failed to set texture stage state, hr %#x.\n", hr);
16579 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
16580 ok(SUCCEEDED(hr), "Failed to set texture stage state, hr %#x.\n", hr);
16582 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x000000ff, 1.0f, 0);
16583 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
16585 hr = IDirect3DDevice9_BeginScene(device);
16586 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
16587 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
16588 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
16589 hr = IDirect3DDevice9_EndScene(device);
16590 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
16592 color = getPixelColor(device, 320, 240);
16593 ok(color_match(color, 0x00a1b2c3, 1), "Got unexpected color 0x%08x.\n", color);
16594 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16595 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16597 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_CONSTANT | D3DTA_COMPLEMENT);
16598 ok(SUCCEEDED(hr), "Failed to set texture stage state, hr %#x.\n", hr);
16600 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x000000ff, 1.0f, 0);
16601 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
16603 hr = IDirect3DDevice9_BeginScene(device);
16604 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
16605 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
16606 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
16607 hr = IDirect3DDevice9_EndScene(device);
16608 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
16610 color = getPixelColor(device, 320, 240);
16611 ok(color_match(color, 0x005e4d3c, 1), "Got unexpected color 0x%08x.\n", color);
16612 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16613 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16615 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_CONSTANT | D3DTA_ALPHAREPLICATE);
16616 ok(SUCCEEDED(hr), "Failed to set texture stage state, hr %#x.\n", hr);
16618 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x000000ff, 1.0f, 0);
16619 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
16621 hr = IDirect3DDevice9_BeginScene(device);
16622 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
16623 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
16624 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
16625 hr = IDirect3DDevice9_EndScene(device);
16626 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
16628 color = getPixelColor(device, 320, 240);
16629 ok(color_match(color, 0x00808080, 1), "Got unexpected color 0x%08x.\n", color);
16630 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16631 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16633 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_ALPHAARG1, D3DTA_CONSTANT);
16634 ok(SUCCEEDED(hr), "Failed to set texture stage state, hr %#x.\n", hr);
16635 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_ALPHAOP, D3DTOP_SELECTARG1);
16636 ok(SUCCEEDED(hr), "Failed to set texture stage state, hr %#x.\n", hr);
16637 hr = IDirect3DDevice9_SetTextureStageState(device, 0, D3DTSS_COLORARG1, D3DTA_CURRENT);
16638 ok(SUCCEEDED(hr), "Failed to set texture stage state, hr %#x.\n", hr);
16640 hr = IDirect3DDevice9_Clear(device, 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0x000000ff, 1.0f, 0);
16641 ok(SUCCEEDED(hr), "Failed to clear, hr %#x.\n", hr);
16643 hr = IDirect3DDevice9_BeginScene(device);
16644 ok(SUCCEEDED(hr), "Failed to begin scene, hr %#x.\n", hr);
16645 hr = IDirect3DDevice9_DrawPrimitiveUP(device, D3DPT_TRIANGLESTRIP, 2, quad, sizeof(*quad));
16646 ok(SUCCEEDED(hr), "Failed to draw, hr %#x.\n", hr);
16647 hr = IDirect3DDevice9_EndScene(device);
16648 ok(SUCCEEDED(hr), "Failed to end scene, hr %#x.\n", hr);
16650 color = getPixelColor(device, 320, 240);
16651 ok(color_match(color, 0x0080007f, 1), "Got unexpected color 0x%08x.\n", color);
16652 hr = IDirect3DDevice9_Present(device, NULL, NULL, NULL, NULL);
16653 ok(SUCCEEDED(hr), "Failed to present, hr %#x.\n", hr);
16655 refcount = IDirect3DDevice9_Release(device);
16656 ok(!refcount, "Device has %u references left.\n", refcount);
16657 done:
16658 IDirect3D9_Release(d3d);
16659 DestroyWindow(window);
16662 START_TEST(visual)
16664 D3DADAPTER_IDENTIFIER9 identifier;
16665 IDirect3D9 *d3d;
16666 HRESULT hr;
16668 if (!(d3d = Direct3DCreate9(D3D_SDK_VERSION)))
16670 skip("could not create D3D9 object\n");
16671 return;
16674 memset(&identifier, 0, sizeof(identifier));
16675 hr = IDirect3D9_GetAdapterIdentifier(d3d, 0, 0, &identifier);
16676 ok(SUCCEEDED(hr), "Failed to get adapter identifier, hr %#x.\n", hr);
16677 trace("Driver string: \"%s\"\n", identifier.Driver);
16678 trace("Description string: \"%s\"\n", identifier.Description);
16679 /* Only Windows XP's default VGA driver should have an empty description */
16680 ok(identifier.Description[0] || broken(!strcmp(identifier.Driver, "vga.dll")), "Empty driver description.\n");
16681 trace("Device name string: \"%s\"\n", identifier.DeviceName);
16682 ok(identifier.DeviceName[0], "Empty device name.\n");
16683 trace("Driver version %d.%d.%d.%d\n",
16684 HIWORD(U(identifier.DriverVersion).HighPart), LOWORD(U(identifier.DriverVersion).HighPart),
16685 HIWORD(U(identifier.DriverVersion).LowPart), LOWORD(U(identifier.DriverVersion).LowPart));
16687 IDirect3D9_Release(d3d);
16689 test_sanity();
16690 depth_clamp_test();
16691 stretchrect_test();
16692 lighting_test();
16693 clear_test();
16694 color_fill_test();
16695 fog_test();
16696 test_cube_wrap();
16697 z_range_test();
16698 maxmip_test();
16699 offscreen_test();
16700 ds_size_test();
16701 alpha_test();
16702 shademode_test();
16703 srgbtexture_test();
16704 release_buffer_test();
16705 float_texture_test();
16706 g16r16_texture_test();
16707 pixelshader_blending_test();
16708 texture_transform_flags_test();
16709 autogen_mipmap_test();
16710 fixed_function_decl_test();
16711 conditional_np2_repeat_test();
16712 fixed_function_bumpmap_test();
16713 pointsize_test();
16714 tssargtemp_test();
16715 np2_stretch_rect_test();
16716 yuv_color_test();
16717 yuv_layout_test();
16718 zwriteenable_test();
16719 alphatest_test();
16720 viewport_test();
16721 test_constant_clamp_vs();
16722 test_compare_instructions();
16723 test_mova();
16724 loop_index_test();
16725 sincos_test();
16726 sgn_test();
16727 clip_planes_test();
16728 test_vshader_input();
16729 test_vshader_float16();
16730 stream_test();
16731 fog_with_shader_test();
16732 texbem_test();
16733 texdepth_test();
16734 texkill_test();
16735 x8l8v8u8_test();
16736 volume_v16u16_test();
16737 constant_clamp_ps_test();
16738 cnd_test();
16739 dp2add_ps_test();
16740 unbound_sampler_test();
16741 nested_loop_test();
16742 pretransformed_varying_test();
16743 vface_register_test();
16744 vpos_register_test();
16745 multiple_rendertargets_test();
16746 texop_test();
16747 texop_range_test();
16748 alphareplicate_test();
16749 dp3_alpha_test();
16750 depth_buffer_test();
16751 depth_buffer2_test();
16752 depth_blit_test();
16753 intz_test();
16754 shadow_test();
16755 fp_special_test();
16756 depth_bounds_test();
16757 srgbwrite_format_test();
16758 update_surface_test();
16759 multisample_get_rtdata_test();
16760 zenable_test();
16761 fog_special_test();
16762 volume_srgb_test();
16763 volume_dxt5_test();
16764 add_dirty_rect_test();
16765 multisampled_depth_buffer_test();
16766 resz_test();
16767 stencil_cull_test();
16768 test_per_stage_constant();