comparison src/video/win32/SDL_d3drender.c @ 1907:06c27a737b7a

Streamlined the API a bit and optimized the software renderer.
author Sam Lantinga <slouken@libsdl.org>
date Sat, 15 Jul 2006 09:46:36 +0000
parents 36d52b1f0504
children 83420da906a5
comparison
equal deleted inserted replaced
1906:0c49855a7a3e 1907:06c27a737b7a
48 static void SDL_D3D_UnlockTexture(SDL_Renderer * renderer, 48 static void SDL_D3D_UnlockTexture(SDL_Renderer * renderer,
49 SDL_Texture * texture); 49 SDL_Texture * texture);
50 static void SDL_D3D_DirtyTexture(SDL_Renderer * renderer, 50 static void SDL_D3D_DirtyTexture(SDL_Renderer * renderer,
51 SDL_Texture * texture, int numrects, 51 SDL_Texture * texture, int numrects,
52 const SDL_Rect * rects); 52 const SDL_Rect * rects);
53 static void SDL_D3D_SelectRenderTexture(SDL_Renderer * renderer,
54 SDL_Texture * texture);
55 static int SDL_D3D_RenderFill(SDL_Renderer * renderer, const SDL_Rect * rect, 53 static int SDL_D3D_RenderFill(SDL_Renderer * renderer, const SDL_Rect * rect,
56 Uint32 color); 54 Uint32 color);
57 static int SDL_D3D_RenderCopy(SDL_Renderer * renderer, SDL_Texture * texture, 55 static int SDL_D3D_RenderCopy(SDL_Renderer * renderer, SDL_Texture * texture,
58 const SDL_Rect * srcrect, 56 const SDL_Rect * srcrect,
59 const SDL_Rect * dstrect, int blendMode, 57 const SDL_Rect * dstrect, int blendMode,
60 int scaleMode); 58 int scaleMode);
61 static int SDL_D3D_RenderReadPixels(SDL_Renderer * renderer,
62 const SDL_Rect * rect, void *pixels,
63 int pitch);
64 static int SDL_D3D_RenderWritePixels(SDL_Renderer * renderer,
65 const SDL_Rect * rect,
66 const void *pixels, int pitch);
67 static void SDL_D3D_RenderPresent(SDL_Renderer * renderer); 59 static void SDL_D3D_RenderPresent(SDL_Renderer * renderer);
68 static void SDL_D3D_DestroyTexture(SDL_Renderer * renderer, 60 static void SDL_D3D_DestroyTexture(SDL_Renderer * renderer,
69 SDL_Texture * texture); 61 SDL_Texture * texture);
70 static void SDL_D3D_DestroyRenderer(SDL_Renderer * renderer); 62 static void SDL_D3D_DestroyRenderer(SDL_Renderer * renderer);
71 63
74 SDL_D3D_CreateRenderer, 66 SDL_D3D_CreateRenderer,
75 { 67 {
76 "d3d", 68 "d3d",
77 (SDL_Renderer_SingleBuffer | SDL_Renderer_PresentCopy | 69 (SDL_Renderer_SingleBuffer | SDL_Renderer_PresentCopy |
78 SDL_Renderer_PresentFlip2 | SDL_Renderer_PresentFlip3 | 70 SDL_Renderer_PresentFlip2 | SDL_Renderer_PresentFlip3 |
79 SDL_Renderer_PresentDiscard | SDL_Renderer_RenderTarget), 71 SDL_Renderer_PresentDiscard | SDL_Renderer_PresentVSync),
80 (SDL_TextureBlendMode_None | 72 (SDL_TextureBlendMode_None | SDL_TextureBlendMode_Mask | SDL_TextureBlendMode_Blend), /* FIXME */
81 SDL_TextureBlendMode_Mask | SDL_TextureBlendMode_Blend), 73 (SDL_TextureScaleMode_None | SDL_TextureScaleMode_Fast), /* FIXME */
82 (SDL_TextureScaleMode_None | SDL_TextureScaleMode_Fast),
83 12, 74 12,
84 { 75 {
85 SDL_PixelFormat_Index8, 76 SDL_PixelFormat_Index8,
86 SDL_PixelFormat_RGB332, 77 SDL_PixelFormat_RGB332,
87 SDL_PixelFormat_RGB444, 78 SDL_PixelFormat_RGB444,
99 }; 90 };
100 91
101 typedef struct 92 typedef struct
102 { 93 {
103 IDirect3DDevice9 *device; 94 IDirect3DDevice9 *device;
104 IDirect3DSurface9 *surface;
105 IDirect3DSurface9 *offscreen;
106 SDL_bool beginScene; 95 SDL_bool beginScene;
107 } SDL_D3D_RenderData; 96 } SDL_D3D_RenderData;
108 97
109 typedef struct 98 typedef struct
110 { 99 {
248 SDL_WindowData *windowdata = (SDL_WindowData *) window->driverdata; 237 SDL_WindowData *windowdata = (SDL_WindowData *) window->driverdata;
249 SDL_Renderer *renderer; 238 SDL_Renderer *renderer;
250 SDL_D3D_RenderData *data; 239 SDL_D3D_RenderData *data;
251 HRESULT result; 240 HRESULT result;
252 D3DPRESENT_PARAMETERS pparams; 241 D3DPRESENT_PARAMETERS pparams;
242 IDirect3DSwapChain9 *chain;
253 243
254 renderer = (SDL_Renderer *) SDL_malloc(sizeof(*renderer)); 244 renderer = (SDL_Renderer *) SDL_malloc(sizeof(*renderer));
255 if (!renderer) { 245 if (!renderer) {
256 SDL_OutOfMemory(); 246 SDL_OutOfMemory();
257 return NULL; 247 return NULL;
271 renderer->GetTexturePalette = SDL_D3D_GetTexturePalette; 261 renderer->GetTexturePalette = SDL_D3D_GetTexturePalette;
272 renderer->UpdateTexture = SDL_D3D_UpdateTexture; 262 renderer->UpdateTexture = SDL_D3D_UpdateTexture;
273 renderer->LockTexture = SDL_D3D_LockTexture; 263 renderer->LockTexture = SDL_D3D_LockTexture;
274 renderer->UnlockTexture = SDL_D3D_UnlockTexture; 264 renderer->UnlockTexture = SDL_D3D_UnlockTexture;
275 renderer->DirtyTexture = SDL_D3D_DirtyTexture; 265 renderer->DirtyTexture = SDL_D3D_DirtyTexture;
276 renderer->SelectRenderTexture = SDL_D3D_SelectRenderTexture;
277 renderer->RenderFill = SDL_D3D_RenderFill; 266 renderer->RenderFill = SDL_D3D_RenderFill;
278 renderer->RenderCopy = SDL_D3D_RenderCopy; 267 renderer->RenderCopy = SDL_D3D_RenderCopy;
279 renderer->RenderReadPixels = SDL_D3D_RenderReadPixels;
280 renderer->RenderWritePixels = SDL_D3D_RenderWritePixels;
281 renderer->RenderPresent = SDL_D3D_RenderPresent; 268 renderer->RenderPresent = SDL_D3D_RenderPresent;
282 renderer->DestroyTexture = SDL_D3D_DestroyTexture; 269 renderer->DestroyTexture = SDL_D3D_DestroyTexture;
283 renderer->DestroyRenderer = SDL_D3D_DestroyRenderer; 270 renderer->DestroyRenderer = SDL_D3D_DestroyRenderer;
284 renderer->info = SDL_D3D_RenderDriver.info; 271 renderer->info = SDL_D3D_RenderDriver.info;
285 renderer->window = window->id; 272 renderer->window = window->id;
286 renderer->driverdata = data; 273 renderer->driverdata = data;
287 274
288 renderer->info.flags = SDL_Renderer_RenderTarget; 275 renderer->info.flags = SDL_Renderer_Accelerated;
289 276
290 SDL_zero(pparams); 277 SDL_zero(pparams);
291 pparams.BackBufferWidth = window->w; 278 pparams.BackBufferWidth = window->w;
292 pparams.BackBufferHeight = window->h; 279 pparams.BackBufferHeight = window->h;
293 if (window->flags & SDL_WINDOW_FULLSCREEN) { 280 if (window->flags & SDL_WINDOW_FULLSCREEN) {
315 display->fullscreen_mode->refresh_rate; 302 display->fullscreen_mode->refresh_rate;
316 } else { 303 } else {
317 pparams.Windowed = TRUE; 304 pparams.Windowed = TRUE;
318 pparams.FullScreen_RefreshRateInHz = 0; 305 pparams.FullScreen_RefreshRateInHz = 0;
319 } 306 }
320 pparams.PresentationInterval = D3DPRESENT_INTERVAL_IMMEDIATE; 307 if (flags & SDL_Renderer_PresentVSync) {
308 pparams.PresentationInterval = D3DPRESENT_INTERVAL_ONE;
309 } else {
310 pparams.PresentationInterval = D3DPRESENT_INTERVAL_IMMEDIATE;
311 }
321 312
322 result = IDirect3D9_CreateDevice(videodata->d3d, D3DADAPTER_DEFAULT, /* FIXME */ 313 result = IDirect3D9_CreateDevice(videodata->d3d, D3DADAPTER_DEFAULT, /* FIXME */
323 D3DDEVTYPE_HAL, 314 D3DDEVTYPE_HAL,
324 windowdata->hwnd, 315 windowdata->hwnd,
325 D3DCREATE_SOFTWARE_VERTEXPROCESSING, 316 D3DCREATE_SOFTWARE_VERTEXPROCESSING,
328 SDL_D3D_DestroyRenderer(renderer); 319 SDL_D3D_DestroyRenderer(renderer);
329 D3D_SetError("CreateDevice()", result); 320 D3D_SetError("CreateDevice()", result);
330 return NULL; 321 return NULL;
331 } 322 }
332 data->beginScene = SDL_TRUE; 323 data->beginScene = SDL_TRUE;
324
325 /* Get presentation parameters to fill info */
326 result = IDirect3DDevice9_GetSwapChain(data->device, 0, &chain);
327 if (FAILED(result)) {
328 SDL_D3D_DestroyRenderer(renderer);
329 D3D_SetError("GetSwapChain()", result);
330 return NULL;
331 }
332 result = IDirect3DSwapChain9_GetPresentParameters(chain, &pparams);
333 if (FAILED(result)) {
334 IDirect3DSwapChain9_Release(chain);
335 SDL_D3D_DestroyRenderer(renderer);
336 D3D_SetError("GetPresentParameters()", result);
337 return NULL;
338 }
339 IDirect3DSwapChain9_Release(chain);
340 switch (pparams.SwapEffect) {
341 case D3DSWAPEFFECT_COPY:
342 renderer->info.flags |= SDL_Renderer_PresentCopy;
343 break;
344 case D3DSWAPEFFECT_FLIP:
345 switch (pparams.BackBufferCount) {
346 case 2:
347 renderer->info.flags |= SDL_Renderer_PresentFlip2;
348 break;
349 case 3:
350 renderer->info.flags |= SDL_Renderer_PresentFlip3;
351 break;
352 }
353 break;
354 case D3DSWAPEFFECT_DISCARD:
355 renderer->info.flags |= SDL_Renderer_PresentDiscard;
356 break;
357 }
358 if (pparams.PresentationInterval == D3DPRESENT_INTERVAL_ONE) {
359 renderer->info.flags |= SDL_Renderer_PresentVSync;
360 }
333 361
334 /* Set up parameters for rendering */ 362 /* Set up parameters for rendering */
335 IDirect3DDevice9_SetVertexShader(data->device, NULL); 363 IDirect3DDevice9_SetVertexShader(data->device, NULL);
336 IDirect3DDevice9_SetFVF(data->device, D3DFVF_XYZRHW | D3DFVF_TEX1); 364 IDirect3DDevice9_SetFVF(data->device, D3DFVF_XYZRHW | D3DFVF_TEX1);
337 IDirect3DDevice9_SetRenderState(data->device, D3DRS_CULLMODE, 365 IDirect3DDevice9_SetRenderState(data->device, D3DRS_CULLMODE,
525 553
526 IDirect3DTexture9_AddDirtyRect(data->texture, &d3drect); 554 IDirect3DTexture9_AddDirtyRect(data->texture, &d3drect);
527 } 555 }
528 } 556 }
529 557
530 static void
531 SDL_D3D_SelectRenderTexture(SDL_Renderer * renderer, SDL_Texture * texture)
532 {
533 SDL_D3D_RenderData *data = (SDL_D3D_RenderData *) renderer->driverdata;
534
535 /* FIXME */
536 }
537
538 static int 558 static int
539 SDL_D3D_RenderFill(SDL_Renderer * renderer, const SDL_Rect * rect, 559 SDL_D3D_RenderFill(SDL_Renderer * renderer, const SDL_Rect * rect,
540 Uint32 color) 560 Uint32 color)
541 { 561 {
542 SDL_D3D_RenderData *data = (SDL_D3D_RenderData *) renderer->driverdata; 562 SDL_D3D_RenderData *data = (SDL_D3D_RenderData *) renderer->driverdata;
635 return -1; 655 return -1;
636 } 656 }
637 return 0; 657 return 0;
638 } 658 }
639 659
640 static int
641 SDL_D3D_RenderReadPixels(SDL_Renderer * renderer, const SDL_Rect * rect,
642 void *pixels, int pitch)
643 {
644 SDL_D3D_RenderData *data = (SDL_D3D_RenderData *) renderer->driverdata;
645
646 /* FIXME */
647 return 0;
648 }
649
650 static int
651 SDL_D3D_RenderWritePixels(SDL_Renderer * renderer, const SDL_Rect * rect,
652 const void *pixels, int pitch)
653 {
654 SDL_Window *window = SDL_GetWindowFromID(renderer->window);
655 SDL_VideoDisplay *display = SDL_GetDisplayFromWindow(window);
656 SDL_D3D_RenderData *data = (SDL_D3D_RenderData *) renderer->driverdata;
657 RECT d3drect;
658 POINT point;
659 D3DLOCKED_RECT locked;
660 const Uint8 *src;
661 Uint8 *dst;
662 int row, length;
663 HRESULT result;
664
665 if (!data->surface) {
666 result =
667 IDirect3DDevice9_GetBackBuffer(data->device, 0, 0,
668 D3DBACKBUFFER_TYPE_MONO,
669 &data->surface);
670 if (FAILED(result)) {
671 D3D_SetError("GetBackBuffer()", result);
672 return -1;
673 }
674 }
675 if (!data->offscreen) {
676 result =
677 IDirect3DDevice9_CreateOffscreenPlainSurface(data->device,
678 window->w, window->h,
679 PixelFormatToD3DFMT
680 (display->
681 current_mode.
682 format),
683 D3DPOOL_SYSTEMMEM,
684 &data->offscreen,
685 NULL);
686 if (FAILED(result)) {
687 D3D_SetError("CreateOffscreenPlainSurface()", result);
688 return -1;
689 }
690 }
691
692 d3drect.left = rect->x;
693 d3drect.right = rect->x + rect->w;
694 d3drect.top = rect->y;
695 d3drect.bottom = rect->y + rect->h;
696
697 result =
698 IDirect3DSurface9_LockRect(data->offscreen, &locked, &d3drect, 0);
699 if (FAILED(result)) {
700 D3D_SetError("LockRect()", result);
701 return -1;
702 }
703
704 src = pixels;
705 dst = locked.pBits;
706 length = rect->w * SDL_BYTESPERPIXEL(display->current_mode.format);
707 for (row = 0; row < rect->h; ++row) {
708 SDL_memcpy(dst, src, length);
709 src += pitch;
710 dst += locked.Pitch;
711 }
712 IDirect3DSurface9_UnlockRect(data->offscreen);
713
714 point.x = rect->x;
715 point.y = rect->y;
716 result =
717 IDirect3DDevice9_UpdateSurface(data->device, data->offscreen,
718 &d3drect, data->surface, &point);
719 if (FAILED(result)) {
720 D3D_SetError("UpdateSurface()", result);
721 return -1;
722 }
723
724 return 0;
725 }
726
727 static void 660 static void
728 SDL_D3D_RenderPresent(SDL_Renderer * renderer) 661 SDL_D3D_RenderPresent(SDL_Renderer * renderer)
729 { 662 {
730 SDL_D3D_RenderData *data = (SDL_D3D_RenderData *) renderer->driverdata; 663 SDL_D3D_RenderData *data = (SDL_D3D_RenderData *) renderer->driverdata;
731 HRESULT result; 664 HRESULT result;
763 696
764 if (data) { 697 if (data) {
765 if (data->device) { 698 if (data->device) {
766 IDirect3DDevice9_Release(data->device); 699 IDirect3DDevice9_Release(data->device);
767 } 700 }
768 if (data->surface) {
769 IDirect3DSurface9_Release(data->surface);
770 }
771 if (data->offscreen) {
772 IDirect3DSurface9_Release(data->offscreen);
773 }
774 SDL_free(data); 701 SDL_free(data);
775 } 702 }
776 SDL_free(renderer); 703 SDL_free(renderer);
777 } 704 }
778 705