1 /* DirectDraw using DGA or Xlib(XSHM)
3 * Copyright 1997,1998 Marcus Meissner
4 * Copyright 1998 Lionel Ulmer (most of Direct3D stuff)
7 * When DirectVideo mode is enabled you can no longer use 'normal' X
8 * applications nor can you switch to a virtual console. Also, enabling
9 * only works, if you have switched to the screen where the application
11 * Some ways to debug this stuff are:
12 * - A terminal connected to the serial port. Can be bought used for cheap.
13 * (This is the method I am using.)
14 * - Another machine connected over some kind of network.
23 #include <sys/types.h>
27 #endif /* defined(HAVE_LIBXXSHM) */
29 #ifdef HAVE_LIBXXF86DGA
30 #include "ts_xf86dga.h"
31 #endif /* defined(HAVE_LIBXXF86DGA) */
33 #ifdef HAVE_LIBXXF86VM
34 /* X is retarted and insists on declaring INT32, INT16 etc in Xmd.h,
35 this is a crude hack to get around it */
38 #include "ts_xf86vmode.h"
39 #endif /* defined(HAVE_LIBXXF86VM) */
45 #include <sys/signal.h>
67 /* This for all the enumeration and creation of D3D-related objects */
68 #include "d3d_private.h"
70 /* define this if you want to play Diablo using XF86DGA. (bug workaround) */
73 /* Restore signal handlers overwritten by XF86DGA
75 #define RESTORE_SIGNALS
76 BOOL32 (*SIGNAL_Reinit)(void); /* didn't find any obvious place to put this */
78 /* Where do these GUIDs come from? mkuuid.
79 * They exist solely to distinguish between the targets Wine support,
80 * and should be different than any other GUIDs in existence.
82 static GUID DGA_DirectDraw_GUID = { /* e2dcb020-dc60-11d1-8407-9714f5d50802 */
86 {0x84, 0x07, 0x97, 0x14, 0xf5, 0xd5, 0x08, 0x02}
89 static GUID XLIB_DirectDraw_GUID = { /* 1574a740-dc61-11d1-8407-f7875a7d1879 */
93 {0x84, 0x07, 0xf7, 0x87, 0x5a, 0x7d, 0x18, 0x79}
96 static struct IDirectDrawSurface4_VTable dga_dds4vt, xlib_dds4vt;
97 static struct IDirectDraw_VTable dga_ddvt, xlib_ddvt;
98 static struct IDirectDraw2_VTable dga_dd2vt, xlib_dd2vt;
99 static struct IDirectDraw4_VTable dga_dd4vt, xlib_dd4vt;
100 static struct IDirectDrawClipper_VTable ddclipvt;
101 static struct IDirectDrawPalette_VTable dga_ddpalvt, xlib_ddpalvt;
102 static struct IDirect3D_VTable d3dvt;
103 static struct IDirect3D2_VTable d3d2vt;
105 #ifdef HAVE_LIBXXF86VM
106 static XF86VidModeModeInfo *orig_mode = NULL;
110 DDRAW_DGA_Available(void)
112 #ifdef HAVE_LIBXXF86DGA
113 int evbase, evret, fd;
118 /* You don't have to be root to use DGA extensions. Simply having access to /dev/mem will do the trick */
119 /* This can be achieved by adding the user to the "kmem" group on Debian 2.x systems, don't know about */
120 /* others. --stephenc */
121 if ((fd = open("/dev/mem", O_RDWR)) != -1)
124 return (fd != -1) && TSXF86DGAQueryExtension(display,&evbase,&evret);
125 #else /* defined(HAVE_LIBXXF86DGA) */
127 #endif /* defined(HAVE_LIBXXF86DGA) */
131 DirectDrawEnumerate32A(LPDDENUMCALLBACK32A ddenumproc,LPVOID data) {
132 if (DDRAW_DGA_Available()) {
133 TRACE(ddraw, "Enumerating DGA interface\n");
134 ddenumproc(&DGA_DirectDraw_GUID,"WINE with XFree86 DGA","display",data);
136 TRACE(ddraw, "Enumerating Xlib interface\n");
137 ddenumproc(&XLIB_DirectDraw_GUID,"WINE with Xlib","display",data);
138 TRACE(ddraw, "Enumerating Default interface\n");
139 ddenumproc(NULL,"WINE (default)","display",data);
143 /* What is this doing here? */
145 DSoundHelp(DWORD x,DWORD y,DWORD z) {
146 FIXME(ddraw,"(0x%08lx,0x%08lx,0x%08lx),stub!\n",x,y,z);
151 /******************************************************************************
152 * internal helper functions
154 static void _dump_DDBLTFX(DWORD flagmask) {
160 #define FE(x) { x, #x},
161 FE(DDBLTFX_ARITHSTRETCHY)
162 FE(DDBLTFX_MIRRORLEFTRIGHT)
163 FE(DDBLTFX_MIRRORUPDOWN)
164 FE(DDBLTFX_NOTEARING)
165 FE(DDBLTFX_ROTATE180)
166 FE(DDBLTFX_ROTATE270)
168 FE(DDBLTFX_ZBUFFERRANGE)
169 FE(DDBLTFX_ZBUFFERBASEDEST)
171 for (i=0;i<sizeof(flags)/sizeof(flags[0]);i++)
172 if (flags[i].mask & flagmask) {
173 DUMP("%s ",flags[i].name);
180 static void _dump_DDBLTFAST(DWORD flagmask) {
186 #define FE(x) { x, #x},
187 FE(DDBLTFAST_NOCOLORKEY)
188 FE(DDBLTFAST_SRCCOLORKEY)
189 FE(DDBLTFAST_DESTCOLORKEY)
192 for (i=0;i<sizeof(flags)/sizeof(flags[0]);i++)
193 if (flags[i].mask & flagmask)
194 DUMP("%s ",flags[i].name);
198 static void _dump_DDBLT(DWORD flagmask) {
204 #define FE(x) { x, #x},
206 FE(DDBLT_ALPHADESTCONSTOVERRIDE)
207 FE(DDBLT_ALPHADESTNEG)
208 FE(DDBLT_ALPHADESTSURFACEOVERRIDE)
209 FE(DDBLT_ALPHAEDGEBLEND)
211 FE(DDBLT_ALPHASRCCONSTOVERRIDE)
212 FE(DDBLT_ALPHASRCNEG)
213 FE(DDBLT_ALPHASRCSURFACEOVERRIDE)
219 FE(DDBLT_KEYDESTOVERRIDE)
221 FE(DDBLT_KEYSRCOVERRIDE)
223 FE(DDBLT_ROTATIONANGLE)
225 FE(DDBLT_ZBUFFERDESTCONSTOVERRIDE)
226 FE(DDBLT_ZBUFFERDESTOVERRIDE)
227 FE(DDBLT_ZBUFFERSRCCONSTOVERRIDE)
228 FE(DDBLT_ZBUFFERSRCOVERRIDE)
232 for (i=0;i<sizeof(flags)/sizeof(flags[0]);i++)
233 if (flags[i].mask & flagmask)
234 DUMP("%s ",flags[i].name);
238 static void _dump_DDSCAPS(DWORD flagmask) {
244 #define FE(x) { x, #x},
245 FE(DDSCAPS_RESERVED1)
247 FE(DDSCAPS_BACKBUFFER)
250 FE(DDSCAPS_FRONTBUFFER)
251 FE(DDSCAPS_OFFSCREENPLAIN)
254 FE(DDSCAPS_PRIMARYSURFACE)
255 FE(DDSCAPS_PRIMARYSURFACELEFT)
256 FE(DDSCAPS_SYSTEMMEMORY)
259 FE(DDSCAPS_VIDEOMEMORY)
261 FE(DDSCAPS_WRITEONLY)
264 FE(DDSCAPS_LIVEVIDEO)
268 FE(DDSCAPS_RESERVED2)
269 FE(DDSCAPS_ALLOCONLOAD)
270 FE(DDSCAPS_VIDEOPORT)
271 FE(DDSCAPS_LOCALVIDMEM)
272 FE(DDSCAPS_NONLOCALVIDMEM)
273 FE(DDSCAPS_STANDARDVGAMODE)
274 FE(DDSCAPS_OPTIMIZED)
276 for (i=0;i<sizeof(flags)/sizeof(flags[0]);i++)
277 if (flags[i].mask & flagmask)
278 DUMP("%s ",flags[i].name);
282 static void _dump_DDSD(DWORD flagmask) {
292 FE(DDSD_BACKBUFFERCOUNT)
293 FE(DDSD_ZBUFFERBITDEPTH)
294 FE(DDSD_ALPHABITDEPTH)
296 FE(DDSD_CKDESTOVERLAY)
298 FE(DDSD_CKSRCOVERLAY)
305 for (i=0;i<sizeof(flags)/sizeof(flags[0]);i++)
306 if (flags[i].mask & flagmask)
307 DUMP("%s ",flags[i].name);
311 static void _dump_DDCOLORKEY(DWORD flagmask) {
317 #define FE(x) { x, #x},
321 FE(DDPF_PALETTEINDEXED4)
322 FE(DDPF_PALETTEINDEXEDTO8)
323 FE(DDPF_PALETTEINDEXED8)
329 FE(DDPF_PALETTEINDEXED1)
330 FE(DDPF_PALETTEINDEXED2)
333 for (i=0;i<sizeof(flags)/sizeof(flags[0]);i++)
334 if (flags[i].mask & flagmask)
335 DUMP("%s ",flags[i].name);
339 static void _dump_paletteformat(DWORD dwFlags) {
345 #define FE(x) { x, #x},
347 FE(DDPCAPS_8BITENTRIES)
349 FE(DDPCAPS_INITIALIZE)
350 FE(DDPCAPS_PRIMARYSURFACE)
351 FE(DDPCAPS_PRIMARYSURFACELEFT)
358 for (i=0;i<sizeof(flags)/sizeof(flags[0]);i++)
359 if (flags[i].mask & dwFlags)
360 DUMP("%s ",flags[i].name);
364 static void _dump_pixelformat(LPDDPIXELFORMAT pf) {
365 DUMP("Size : %ld\n", pf->dwSize);
367 _dump_DDCOLORKEY(pf->dwFlags);
368 DUMP("dwFourCC : %ld\n", pf->dwFourCC);
369 DUMP("RGB bit count : %ld\n", pf->x.dwRGBBitCount);
370 DUMP("Masks : R %08lx G %08lx B %08lx A %08lx\n",
371 pf->y.dwRBitMask, pf->z.dwGBitMask, pf->xx.dwBBitMask, pf->xy.dwRGBAlphaBitMask);
374 static int _getpixelformat(LPDIRECTDRAW2 ddraw,LPDDPIXELFORMAT pf) {
375 static XVisualInfo *vi;
380 vi = TSXGetVisualInfo(display,VisualNoMask,&vt,&nitems);
383 pf->dwSize = sizeof(DDPIXELFORMAT);
384 if (ddraw->d.depth==8) {
385 pf->dwFlags = DDPF_RGB|DDPF_PALETTEINDEXED8;
386 pf->x.dwRGBBitCount = 8;
387 pf->y.dwRBitMask = 0;
388 pf->z.dwGBitMask = 0;
389 pf->xx.dwBBitMask = 0;
390 pf->xy.dwRGBAlphaBitMask= 0;
393 if (ddraw->d.depth==16) {
394 pf->dwFlags = DDPF_RGB;
395 pf->x.dwRGBBitCount = 16;
396 pf->y.dwRBitMask = vi[0].red_mask;
397 pf->z.dwGBitMask = vi[0].green_mask;
398 pf->xx.dwBBitMask = vi[0].blue_mask;
399 pf->xy.dwRGBAlphaBitMask= 0;
402 FIXME(ddraw,"_getpixelformat:unknown depth %ld?\n",ddraw->d.depth);
403 return DDERR_GENERIC;
406 /******************************************************************************
407 * IDirectDrawSurface methods
409 * Since DDS3 and DDS2 are supersets of DDS, we implement DDS3 and let
410 * DDS and DDS2 use those functions. (Function calls did not change (except
411 * using different DirectDrawSurfaceX version), just added flags and functions)
413 static HRESULT WINAPI IDirectDrawSurface4_Lock(
414 LPDIRECTDRAWSURFACE4 this,LPRECT32 lprect,LPDDSURFACEDESC lpddsd,DWORD flags, HANDLE32 hnd
416 TRACE(ddraw, "(%p)->Lock(%p,%p,%08lx,%08lx)\n",
417 this,lprect,lpddsd,flags,(DWORD)hnd);
418 if (flags & ~(DDLOCK_WAIT|DDLOCK_READONLY|DDLOCK_WRITEONLY))
419 WARN(ddraw, "(%p)->Lock(%p,%p,%08lx,%08lx)\n",
420 this,lprect,lpddsd,flags,(DWORD)hnd);
422 /* First, copy the Surface description */
423 *lpddsd = this->s.surface_desc;
424 TRACE(ddraw,"locked surface: height=%ld, width=%ld, pitch=%ld\n",
425 lpddsd->dwHeight,lpddsd->dwWidth,lpddsd->lPitch);
427 /* If asked only for a part, change the surface pointer */
429 FIXME(ddraw," lprect: %dx%d-%dx%d\n",
430 lprect->top,lprect->left,lprect->bottom,lprect->right
432 lpddsd->y.lpSurface = this->s.surface_desc.y.lpSurface +
433 (lprect->top*this->s.surface_desc.lPitch) +
434 (lprect->left*(this->s.surface_desc.ddpfPixelFormat.x.dwRGBBitCount / 8));
436 assert(this->s.surface_desc.y.lpSurface);
441 static HRESULT WINAPI DGA_IDirectDrawSurface4_Unlock(
442 LPDIRECTDRAWSURFACE4 this,LPVOID surface
444 TRACE(ddraw,"(%p)->Unlock(%p)\n",this,surface);
448 static void Xlib_copy_surface_on_screen(LPDIRECTDRAWSURFACE4 this) {
449 if (this->s.ddraw->d.depth != this->s.ddraw->d.screen_depth) {
450 /* Pixel convertion ! */
451 if ((this->s.ddraw->d.depth == 8) && (this->s.ddraw->d.screen_depth == 16)) {
452 unsigned char *src = (unsigned char *) this->s.surface_desc.y.lpSurface;
453 unsigned short *dst = (unsigned short *) this->t.xlib.image->data;
457 if (this->s.palette != NULL) {
458 pal = (unsigned short *) this->s.palette->screen_palents;
459 for (y = 0; y < this->s.surface_desc.dwHeight; y++) {
460 for (x = 0; x < this->s.surface_desc.dwWidth; x++) {
461 dst[x + y * this->s.surface_desc.lPitch] = pal[src[x + y * this->s.surface_desc.lPitch]];
465 WARN(ddraw, "No palette set...\n");
466 memset(dst, 0, this->s.surface_desc.lPitch * this->s.surface_desc.dwHeight * 2);
469 ERR(ddraw, "Unsupported pixel convertion...\n");
474 if (this->s.ddraw->e.xlib.xshm_active)
475 TSXShmPutImage(display,
476 this->s.ddraw->d.drawable,
477 DefaultGCOfScreen(X11DRV_GetXScreen()),
480 this->t.xlib.image->width,
481 this->t.xlib.image->height,
485 TSXPutImage( display,
486 this->s.ddraw->d.drawable,
487 DefaultGCOfScreen(X11DRV_GetXScreen()),
490 this->t.xlib.image->width,
491 this->t.xlib.image->height);
494 static HRESULT WINAPI Xlib_IDirectDrawSurface4_Unlock(
495 LPDIRECTDRAWSURFACE4 this,LPVOID surface)
497 TRACE(ddraw,"(%p)->Unlock(%p)\n",this,surface);
499 if (!this->s.ddraw->d.paintable)
502 /* Only redraw the screen when unlocking the buffer that is on screen */
503 if ((this->t.xlib.image != NULL) &&
504 (this->s.surface_desc.ddsCaps.dwCaps & DDSCAPS_VISIBLE)) {
505 Xlib_copy_surface_on_screen(this);
507 if (this->s.palette && this->s.palette->cm)
508 TSXSetWindowColormap(display,this->s.ddraw->d.drawable,this->s.palette->cm);
514 static HRESULT WINAPI DGA_IDirectDrawSurface4_Flip(
515 LPDIRECTDRAWSURFACE4 this,LPDIRECTDRAWSURFACE4 flipto,DWORD dwFlags
517 #ifdef HAVE_LIBXXF86DGA
518 TRACE(ddraw,"(%p)->Flip(%p,%08lx)\n",this,flipto,dwFlags);
520 if (this->s.backbuffer)
521 flipto = this->s.backbuffer;
525 TSXF86DGASetViewPort(display,DefaultScreen(display),0,flipto->t.dga.fb_height);
527 if (flipto->s.palette && flipto->s.palette->cm) {
528 TSXF86DGAInstallColormap(display,DefaultScreen(display),flipto->s.palette->cm);
530 while (!TSXF86DGAViewPortChanged(display,DefaultScreen(display),2)) {
536 tmp = this->t.dga.fb_height;
537 this->t.dga.fb_height = flipto->t.dga.fb_height;
538 flipto->t.dga.fb_height = tmp;
540 ptmp = this->s.surface_desc.y.lpSurface;
541 this->s.surface_desc.y.lpSurface = flipto->s.surface_desc.y.lpSurface;
542 flipto->s.surface_desc.y.lpSurface = ptmp;
545 #else /* defined(HAVE_LIBXXF86DGA) */
547 #endif /* defined(HAVE_LIBXXF86DGA) */
550 static HRESULT WINAPI Xlib_IDirectDrawSurface4_Flip(
551 LPDIRECTDRAWSURFACE4 this,LPDIRECTDRAWSURFACE4 flipto,DWORD dwFlags
553 TRACE(ddraw,"(%p)->Flip(%p,%08lx)\n",this,flipto,dwFlags);
554 if (!this->s.ddraw->d.paintable)
558 if (this->s.backbuffer)
559 flipto = this->s.backbuffer;
564 Xlib_copy_surface_on_screen(this);
566 if (flipto->s.palette && flipto->s.palette->cm) {
567 TSXSetWindowColormap(display,this->s.ddraw->d.drawable,flipto->s.palette->cm);
572 tmp = this->t.xlib.image;
573 this->t.xlib.image = flipto->t.xlib.image;
574 flipto->t.xlib.image = tmp;
575 surf = this->s.surface_desc.y.lpSurface;
576 this->s.surface_desc.y.lpSurface = flipto->s.surface_desc.y.lpSurface;
577 flipto->s.surface_desc.y.lpSurface = surf;
583 /* The IDirectDrawSurface4::SetPalette method attaches the specified
584 * DirectDrawPalette object to a surface. The surface uses this palette for all
585 * subsequent operations. The palette change takes place immediately.
587 static HRESULT WINAPI Xlib_IDirectDrawSurface4_SetPalette(
588 LPDIRECTDRAWSURFACE4 this,LPDIRECTDRAWPALETTE pal
591 TRACE(ddraw,"(%p)->(%p)\n",this,pal);
594 if( this->s.palette != NULL )
595 this->s.palette->lpvtbl->fnRelease( this->s.palette );
596 this->s.palette = pal;
601 if( !(pal->cm) && (this->s.ddraw->d.screen_depth<=8))
603 pal->cm = TSXCreateColormap(display,this->s.ddraw->d.drawable,
604 DefaultVisualOfScreen(X11DRV_GetXScreen()),AllocAll);
606 if (!Options.managed)
607 TSXInstallColormap(display,pal->cm);
609 for (i=0;i<256;i++) {
612 xc.red = pal->palents[i].peRed<<8;
613 xc.blue = pal->palents[i].peBlue<<8;
614 xc.green = pal->palents[i].peGreen<<8;
615 xc.flags = DoRed|DoBlue|DoGreen;
617 TSXStoreColor(display,pal->cm,&xc);
619 TSXInstallColormap(display,pal->cm);
622 /* According to spec, we are only supposed to
623 * AddRef if this is not the same palette.
625 if( this->s.palette != pal )
628 pal->lpvtbl->fnAddRef( pal );
629 if( this->s.palette != NULL )
630 this->s.palette->lpvtbl->fnRelease( this->s.palette );
631 this->s.palette = pal;
633 /* I think that we need to attach it to all backbuffers...*/
634 if( this->s.backbuffer ) {
635 if( this->s.backbuffer->s.palette )
636 this->s.backbuffer->s.palette->lpvtbl->fnRelease(
637 this->s.backbuffer->s.palette );
638 this->s.backbuffer->s.palette = pal;
640 pal->lpvtbl->fnAddRef( pal );
642 /* Perform the refresh */
643 TSXSetWindowColormap(display,this->s.ddraw->d.drawable,this->s.palette->cm);
648 static HRESULT WINAPI DGA_IDirectDrawSurface4_SetPalette(
649 LPDIRECTDRAWSURFACE4 this,LPDIRECTDRAWPALETTE pal
651 TRACE(ddraw,"(%p)->(%p)\n",this,pal);
652 #ifdef HAVE_LIBXXF86DGA
653 /* According to spec, we are only supposed to
654 * AddRef if this is not the same palette.
656 if( this->s.palette != pal )
659 pal->lpvtbl->fnAddRef( pal );
660 if( this->s.palette != NULL )
661 this->s.palette->lpvtbl->fnRelease( this->s.palette );
662 this->s.palette = pal;
664 /* I think that we need to attach it to all backbuffers...*/
665 if( this->s.backbuffer ) {
666 if( this->s.backbuffer->s.palette )
667 this->s.backbuffer->s.palette->lpvtbl->fnRelease(this->s.backbuffer->s.palette );
668 this->s.backbuffer->s.palette = pal;
669 if( pal ) pal->lpvtbl->fnAddRef( pal );
671 TSXF86DGAInstallColormap(display,DefaultScreen(display),this->s.palette->cm);
674 #else /* defined(HAVE_LIBXXF86DGA) */
676 #endif /* defined(HAVE_LIBXXF86DGA) */
681 static HRESULT WINAPI IDirectDrawSurface4_Blt(
682 LPDIRECTDRAWSURFACE4 this,LPRECT32 rdst,LPDIRECTDRAWSURFACE4 src,LPRECT32 rsrc,DWORD dwFlags,LPDDBLTFX lpbltfx
685 DDSURFACEDESC ddesc,sdesc;
688 TRACE(ddraw,"(%p)->(%p,%p,%p,%08lx,%p)\n",
689 this,rdst,src,rsrc,dwFlags,lpbltfx);
692 src ->lpvtbl->fnLock(src, NULL,&sdesc,0,0);
693 this->lpvtbl->fnLock(this,NULL,&ddesc,0,0);
695 if (TRACE_ON(ddraw)) {
696 if (rdst) TRACE(ddraw," destrect :%dx%d-%dx%d\n",rdst->left,rdst->top,rdst->right,rdst->bottom);
697 if (rsrc) TRACE(ddraw," srcrect :%dx%d-%dx%d\n",rsrc->left,rsrc->top,rsrc->right,rsrc->bottom);
698 TRACE(ddraw,"\tflags: ");_dump_DDBLT(dwFlags);fprintf(stderr,"\n");
699 if (dwFlags & DDBLT_DDFX) {
700 TRACE(ddraw," blitfx: \n");_dump_DDBLTFX(lpbltfx->dwDDFX);
705 memcpy(&xdst,rdst,sizeof(xdst));
708 xdst.bottom = ddesc.dwHeight;
710 xdst.right = ddesc.dwWidth;
714 memcpy(&xsrc,rsrc,sizeof(xsrc));
718 xsrc.bottom = sdesc.dwHeight;
720 xsrc.right = sdesc.dwWidth;
722 memset(&xsrc,0,sizeof(xsrc));
726 dwFlags &= ~(DDBLT_WAIT|DDBLT_ASYNC);/* FIXME: can't handle right now */
728 /* First, all the 'source-less' blits */
729 if (dwFlags & DDBLT_COLORFILL) {
730 int bpp = ddesc.ddpfPixelFormat.x.dwRGBBitCount / 8;
733 xline = (LPBYTE) ddesc.y.lpSurface + xdst.top * ddesc.lPitch;
734 for (i=xdst.top;i<xdst.bottom;i++) {
735 xpixel = xline+bpp*xdst.left;
737 for (j=xdst.left;j<xdst.right;j++) {
738 /* FIXME: this only works on little endian
739 * architectures, where DWORD starts with low
742 memcpy(xpixel,&(lpbltfx->b.dwFillColor),bpp);
745 xline += ddesc.lPitch;
747 dwFlags &= ~(DDBLT_COLORFILL);
750 if (dwFlags & DDBLT_DEPTHFILL) {
754 /* Clears the screen */
755 TRACE(ddraw, " Filling depth buffer with %ld\n", lpbltfx->b.dwFillDepth);
756 glClearDepth(lpbltfx->b.dwFillDepth / 65535.0); /* We suppose a 16 bit Z Buffer */
757 glGetBooleanv(GL_DEPTH_TEST, &ztest);
758 glDepthMask(GL_TRUE); /* Enables Z writing to be sure to delete also the Z buffer */
759 glClear(GL_DEPTH_BUFFER_BIT);
762 dwFlags &= ~(DDBLT_DEPTHFILL);
768 TRACE(ddraw,"\t(src=NULL):Unsupported flags: ");_dump_DDBLT(dwFlags);fprintf(stderr,"\n");
770 this->lpvtbl->fnUnlock(this,ddesc.y.lpSurface);
774 /* Now the 'with source' blits */
776 /* Standard 'full-surface' blit without special effects */
777 if ( (xsrc.top ==0) && (xsrc.bottom ==ddesc.dwHeight) &&
778 (xsrc.left==0) && (xsrc.right ==ddesc.dwWidth) &&
779 (xdst.top ==0) && (xdst.bottom ==ddesc.dwHeight) &&
780 (xdst.left==0) && (xdst.right ==ddesc.dwWidth) &&
783 memcpy(ddesc.y.lpSurface,
785 ddesc.dwHeight * ddesc.lPitch);
787 int bpp = ddesc.ddpfPixelFormat.x.dwRGBBitCount / 8;
788 int srcheight = xsrc.bottom - xsrc.top;
789 int srcwidth = xsrc.right - xsrc.left;
790 int dstheight = xdst.bottom - xdst.top;
791 int dstwidth = xdst.right - xdst.left;
792 int width = (xsrc.right - xsrc.left) * bpp;
795 /* Sanity check for rectangle sizes */
796 if ((srcheight != dstheight) || (srcwidth != dstwidth)) {
799 /* I think we should do a Blit with 'stretching' here....
800 Tomb Raider II uses this to display the background during the menu selection
801 when the screen resolution is != than 640x480 */
802 TRACE(ddraw, "Blt with stretching\n");
804 /* This is a basic stretch implementation. It is painfully slow and quite ugly. */
806 /* In this case, we cannot do any anti-aliasing */
807 if(dwFlags & DDBLT_KEYSRC) {
808 for (y = xdst.top; y < xdst.bottom; y++) {
809 for (x = xdst.left; x < xdst.right; x++) {
812 unsigned char *dbuf = (unsigned char *) ddesc.y.lpSurface;
813 unsigned char *sbuf = (unsigned char *) sdesc.y.lpSurface;
815 sx = (((double) (x - xdst.left) / dstwidth) * srcwidth) + xsrc.left;
816 sy = (((double) (y - xdst.top) / dstheight) * srcheight) + xsrc.top;
818 tmp = sbuf[(((int) sy) * sdesc.lPitch) + ((int) sx)];
820 if ((tmp < src->s.surface_desc.ddckCKSrcBlt.dwColorSpaceLowValue) ||
821 (tmp > src->s.surface_desc.ddckCKSrcBlt.dwColorSpaceHighValue))
822 dbuf[(y * ddesc.lPitch) + x] = tmp;
826 for (y = xdst.top; y < xdst.bottom; y++) {
827 for (x = xdst.left; x < xdst.right; x++) {
829 unsigned char *dbuf = (unsigned char *) ddesc.y.lpSurface;
830 unsigned char *sbuf = (unsigned char *) sdesc.y.lpSurface;
832 sx = (((double) (x - xdst.left) / dstwidth) * srcwidth) + xsrc.left;
833 sy = (((double) (y - xdst.top) / dstheight) * srcheight) + xsrc.top;
835 dbuf[(y * ddesc.lPitch) + x] = sbuf[(((int) sy) * sdesc.lPitch) + ((int) sx)];
840 FIXME(ddraw, "Not done yet for depth != 8\n");
843 /* Same size => fast blit */
844 if (dwFlags & DDBLT_KEYSRC) {
847 unsigned char tmp,*psrc,*pdst;
850 for (h = 0; h < srcheight; h++) {
851 psrc=sdesc.y.lpSurface +
852 ((h + xsrc.top) * sdesc.lPitch) + xsrc.left;
853 pdst=ddesc.y.lpSurface +
854 ((h + xdst.top) * ddesc.lPitch) + xdst.left;
855 for(i=0;i<srcwidth;i++) {
857 if ((tmp < src->s.surface_desc.ddckCKSrcBlt.dwColorSpaceLowValue) ||
858 (tmp > src->s.surface_desc.ddckCKSrcBlt.dwColorSpaceHighValue))
862 dwFlags&=~(DDBLT_KEYSRC);
866 unsigned short tmp,*psrc,*pdst;
869 for (h = 0; h < srcheight; h++) {
870 psrc=sdesc.y.lpSurface +
871 ((h + xsrc.top) * sdesc.lPitch) + xsrc.left;
872 pdst=ddesc.y.lpSurface +
873 ((h + xdst.top) * ddesc.lPitch) + xdst.left;
874 for(i=0;i<srcwidth;i++) {
876 if ((tmp < src->s.surface_desc.ddckCKSrcBlt.dwColorSpaceLowValue) ||
877 (tmp > src->s.surface_desc.ddckCKSrcBlt.dwColorSpaceHighValue))
881 dwFlags&=~(DDBLT_KEYSRC);
885 FIXME(ddraw, "Bitblt, KEYSRC: Not done yet for depth > 16\n");
888 /* Non-stretching Blt without color keying */
889 for (h = 0; h < srcheight; h++) {
890 memcpy(ddesc.y.lpSurface + ((h + xdst.top) * ddesc.lPitch) + xdst.left * bpp,
891 sdesc.y.lpSurface + ((h + xsrc.top) * sdesc.lPitch) + xsrc.left * bpp,
898 if (dwFlags && FIXME_ON(ddraw)) {
899 FIXME(ddraw,"\tUnsupported flags: ");_dump_DDBLT(dwFlags);
902 this->lpvtbl->fnUnlock(this,ddesc.y.lpSurface);
903 src ->lpvtbl->fnUnlock(src,sdesc.y.lpSurface);
908 static HRESULT WINAPI IDirectDrawSurface4_BltFast(
909 LPDIRECTDRAWSURFACE4 this,DWORD dstx,DWORD dsty,LPDIRECTDRAWSURFACE4 src,LPRECT32 rsrc,DWORD trans
912 DDSURFACEDESC ddesc,sdesc;
914 if (1 || TRACE_ON(ddraw)) {
915 FIXME(ddraw,"(%p)->(%ld,%ld,%p,%p,%08lx)\n",
916 this,dstx,dsty,src,rsrc,trans
918 FIXME(ddraw," trans:");_dump_DDBLTFAST(trans);fprintf(stderr,"\n");
919 FIXME(ddraw," srcrect: %dx%d-%dx%d\n",rsrc->left,rsrc->top,rsrc->right,rsrc->bottom);
921 /* We need to lock the surfaces, or we won't get refreshes when done. */
922 src ->lpvtbl->fnLock(src, NULL,&sdesc,DDLOCK_READONLY, 0);
923 this->lpvtbl->fnLock(this,NULL,&ddesc,DDLOCK_WRITEONLY,0);
924 bpp = this->s.surface_desc.ddpfPixelFormat.x.dwRGBBitCount / 8;
925 h=rsrc->bottom-rsrc->top;
926 if (h>ddesc.dwHeight-dsty) h=ddesc.dwHeight-dsty;
927 if (h>sdesc.dwHeight-rsrc->top) h=sdesc.dwHeight-rsrc->top;
929 w=rsrc->right-rsrc->left;
930 if (w>ddesc.dwWidth-dstx) w=ddesc.dwWidth-dstx;
931 if (w>sdesc.dwWidth-rsrc->left) w=sdesc.dwWidth-rsrc->left;
935 memcpy( ddesc.y.lpSurface+(dsty +i)*ddesc.lPitch+dstx*bpp,
936 sdesc.y.lpSurface+(rsrc->top+i)*sdesc.lPitch+rsrc->left*bpp,
940 this->lpvtbl->fnUnlock(this,ddesc.y.lpSurface);
941 src ->lpvtbl->fnUnlock(src,sdesc.y.lpSurface);
945 static HRESULT WINAPI IDirectDrawSurface4_BltBatch(
946 LPDIRECTDRAWSURFACE4 this,LPDDBLTBATCH ddbltbatch,DWORD x,DWORD y
948 FIXME(ddraw,"(%p)->BltBatch(%p,%08lx,%08lx),stub!\n",
954 static HRESULT WINAPI IDirectDrawSurface4_GetCaps(
955 LPDIRECTDRAWSURFACE4 this,LPDDSCAPS caps
957 TRACE(ddraw,"(%p)->GetCaps(%p)\n",this,caps);
958 caps->dwCaps = DDSCAPS_PALETTE; /* probably more */
962 static HRESULT WINAPI IDirectDrawSurface4_GetSurfaceDesc(
963 LPDIRECTDRAWSURFACE4 this,LPDDSURFACEDESC ddsd
965 TRACE(ddraw, "(%p)->GetSurfaceDesc(%p)\n",
968 /* Simply copy the surface description stored in the object */
969 *ddsd = this->s.surface_desc;
971 if (TRACE_ON(ddraw)) {
972 fprintf(stderr," flags: ");
973 _dump_DDSD(ddsd->dwFlags);
974 if (ddsd->dwFlags & DDSD_CAPS) {
975 fprintf(stderr, " caps: ");
976 _dump_DDSCAPS(ddsd->ddsCaps.dwCaps);
978 fprintf(stderr,"\n");
984 static ULONG WINAPI IDirectDrawSurface4_AddRef(LPDIRECTDRAWSURFACE4 this) {
985 TRACE( ddraw, "(%p)->() incrementing from %lu.\n", this, this->ref );
987 return ++(this->ref);
990 static ULONG WINAPI DGA_IDirectDrawSurface4_Release(LPDIRECTDRAWSURFACE4 this) {
991 TRACE( ddraw, "(%p)->() decrementing from %lu.\n", this, this->ref );
993 #ifdef HAVE_LIBXXF86DGA
994 if (!--(this->ref)) {
995 this->s.ddraw->lpvtbl->fnRelease(this->s.ddraw);
996 /* clear out of surface list */
997 if (this->t.dga.fb_height == -1) {
998 HeapFree(GetProcessHeap(),0,this->s.surface_desc.y.lpSurface);
1000 this->s.ddraw->e.dga.vpmask &= ~(1<<(this->t.dga.fb_height/this->s.ddraw->e.dga.fb_height));
1003 /* Free the backbuffer */
1004 if (this->s.backbuffer)
1005 this->s.backbuffer->lpvtbl->fnRelease(this->s.backbuffer);
1007 HeapFree(GetProcessHeap(),0,this);
1010 #endif /* defined(HAVE_LIBXXF86DGA) */
1014 static ULONG WINAPI Xlib_IDirectDrawSurface4_Release(LPDIRECTDRAWSURFACE4 this) {
1015 TRACE( ddraw, "(%p)->() decrementing from %lu.\n", this, this->ref );
1017 if (!--(this->ref)) {
1018 this->s.ddraw->lpvtbl->fnRelease(this->s.ddraw);
1020 if( this->s.backbuffer )
1021 this->s.backbuffer->lpvtbl->fnRelease(this->s.backbuffer);
1023 if (this->t.xlib.image != NULL) {
1024 if (this->s.ddraw->d.depth != this->s.ddraw->d.screen_depth) {
1025 /* In pixel conversion mode, there are two buffers to release... */
1026 HeapFree(GetProcessHeap(),0,this->s.surface_desc.y.lpSurface);
1028 #ifdef HAVE_LIBXXSHM
1029 if (this->s.ddraw->e.xlib.xshm_active) {
1030 TSXShmDetach(display, &(this->t.xlib.shminfo));
1031 TSXDestroyImage(this->t.xlib.image);
1032 shmdt(this->t.xlib.shminfo.shmaddr);
1035 HeapFree(GetProcessHeap(),0,this->t.xlib.image->data);
1036 this->t.xlib.image->data = NULL;
1037 TSXDestroyImage(this->t.xlib.image);
1038 #ifdef HAVE_LIBXXSHM
1043 this->t.xlib.image->data = NULL;
1045 #ifdef HAVE_LIBXXSHM
1046 if (this->s.ddraw->e.xlib.xshm_active) {
1047 TSXShmDetach(display, &(this->t.xlib.shminfo));
1048 TSXDestroyImage(this->t.xlib.image);
1049 shmdt(this->t.xlib.shminfo.shmaddr);
1052 HeapFree(GetProcessHeap(),0,this->s.surface_desc.y.lpSurface);
1053 TSXDestroyImage(this->t.xlib.image);
1054 #ifdef HAVE_LIBXXSHM
1059 this->t.xlib.image = 0;
1061 HeapFree(GetProcessHeap(),0,this->s.surface_desc.y.lpSurface);
1064 if (this->s.palette)
1065 this->s.palette->lpvtbl->fnRelease(this->s.palette);
1067 HeapFree(GetProcessHeap(),0,this);
1074 static HRESULT WINAPI IDirectDrawSurface4_GetAttachedSurface(
1075 LPDIRECTDRAWSURFACE4 this,LPDDSCAPS lpddsd,LPDIRECTDRAWSURFACE4 *lpdsf
1077 TRACE(ddraw, "(%p)->GetAttachedSurface(%p,%p)\n",
1078 this, lpddsd, lpdsf);
1080 if (TRACE_ON(ddraw)) {
1081 TRACE(ddraw," caps ");
1082 _dump_DDSCAPS(lpddsd->dwCaps);
1085 if (!(lpddsd->dwCaps & DDSCAPS_BACKBUFFER)) {
1086 FIXME(ddraw,"whoops, can only handle backbuffers for now\n");
1090 /* FIXME: should handle more than one backbuffer */
1091 *lpdsf = this->s.backbuffer;
1093 if( this->s.backbuffer )
1094 this->s.backbuffer->lpvtbl->fnAddRef( this->s.backbuffer );
1099 static HRESULT WINAPI IDirectDrawSurface4_Initialize(
1100 LPDIRECTDRAWSURFACE4 this,LPDIRECTDRAW ddraw,LPDDSURFACEDESC lpdsfd
1102 TRACE(ddraw,"(%p)->(%p, %p)\n",this,ddraw,lpdsfd);
1104 return DDERR_ALREADYINITIALIZED;
1107 static HRESULT WINAPI IDirectDrawSurface4_GetPixelFormat(
1108 LPDIRECTDRAWSURFACE4 this,LPDDPIXELFORMAT pf
1110 TRACE(ddraw,"(%p)->(%p)\n",this,pf);
1112 *pf = this->s.surface_desc.ddpfPixelFormat;
1117 static HRESULT WINAPI IDirectDrawSurface4_GetBltStatus(LPDIRECTDRAWSURFACE4 this,DWORD dwFlags) {
1118 FIXME(ddraw,"(%p)->(0x%08lx),stub!\n",this,dwFlags);
1122 static HRESULT WINAPI IDirectDrawSurface4_GetOverlayPosition(
1123 LPDIRECTDRAWSURFACE4 this,LPLONG x1,LPLONG x2
1125 FIXME(ddraw,"(%p)->(%p,%p),stub!\n",this,x1,x2);
1129 static HRESULT WINAPI IDirectDrawSurface4_SetClipper(
1130 LPDIRECTDRAWSURFACE4 this,LPDIRECTDRAWCLIPPER clipper
1132 FIXME(ddraw,"(%p)->(%p),stub!\n",this,clipper);
1136 static HRESULT WINAPI IDirectDrawSurface4_AddAttachedSurface(
1137 LPDIRECTDRAWSURFACE4 this,LPDIRECTDRAWSURFACE4 surf
1139 FIXME(ddraw,"(%p)->(%p),stub!\n",this,surf);
1141 this->lpvtbl->fnAddRef(this);
1143 /* This hack will be enough for the moment */
1144 if (this->s.backbuffer == NULL)
1145 this->s.backbuffer = surf;
1149 static HRESULT WINAPI IDirectDrawSurface4_GetDC(LPDIRECTDRAWSURFACE4 this,HDC32* lphdc) {
1150 FIXME(ddraw,"(%p)->GetDC(%p)\n",this,lphdc);
1151 *lphdc = BeginPaint32(this->s.ddraw->d.window,&this->s.ddraw->d.ps);
1155 static HRESULT WINAPI IDirectDrawSurface4_ReleaseDC(LPDIRECTDRAWSURFACE4 this,HDC32 hdc) {
1159 FIXME(ddraw,"(%p)->(0x%08lx),stub!\n",this,(long)hdc);
1160 EndPaint32(this->s.ddraw->d.window,&this->s.ddraw->d.ps);
1162 /* Well, as what the application did paint in this DC is NOT saved in the surface,
1163 I fill it with 'dummy' values to have something on the screen */
1164 this->lpvtbl->fnLock(this,NULL,&desc,0,0);
1165 for (y = 0; y < desc.dwHeight; y++) {
1166 for (x = 0; x < desc.dwWidth; x++) {
1167 ((unsigned char *) desc.y.lpSurface)[x + y * desc.dwWidth] = (unsigned int) this + x + y;
1170 this->lpvtbl->fnUnlock(this,NULL);
1176 static HRESULT WINAPI IDirectDrawSurface4_QueryInterface(LPDIRECTDRAWSURFACE4 this,REFIID refiid,LPVOID *obj) {
1179 WINE_StringFromCLSID((LPCLSID)refiid,xrefiid);
1180 TRACE(ddraw,"(%p)->(%s,%p)\n",this,xrefiid,obj);
1182 /* All DirectDrawSurface versions (1, 2, 3 and 4) use
1183 * the same interface. And IUnknown does that too of course.
1185 if ( !memcmp(&IID_IDirectDrawSurface4,refiid,sizeof(IID)) ||
1186 !memcmp(&IID_IDirectDrawSurface3,refiid,sizeof(IID)) ||
1187 !memcmp(&IID_IDirectDrawSurface2,refiid,sizeof(IID)) ||
1188 !memcmp(&IID_IDirectDrawSurface,refiid,sizeof(IID)) ||
1189 !memcmp(&IID_IUnknown,refiid,sizeof(IID))
1192 this->lpvtbl->fnAddRef(this);
1194 TRACE(ddraw, " Creating IDirectDrawSurface interface (%p)\n", *obj);
1198 else if (!memcmp(&IID_IDirect3DTexture2,refiid,sizeof(IID)))
1200 /* Texture interface */
1201 *obj = d3dtexture2_create(this);
1202 this->lpvtbl->fnAddRef(this);
1204 TRACE(ddraw, " Creating IDirect3DTexture2 interface (%p)\n", *obj);
1208 else if (!memcmp(&IID_IDirect3DTexture,refiid,sizeof(IID)))
1210 /* Texture interface */
1211 *obj = d3dtexture_create(this);
1212 this->lpvtbl->fnAddRef(this);
1214 TRACE(ddraw, " Creating IDirect3DTexture interface (%p)\n", *obj);
1218 else if (is_OpenGL_dx3(refiid, (LPDIRECTDRAWSURFACE) this, (LPDIRECT3DDEVICE *) obj))
1220 /* It is the OpenGL Direct3D Device */
1221 this->lpvtbl->fnAddRef(this);
1223 TRACE(ddraw, " Creating IDirect3DDevice interface (%p)\n", *obj);
1228 FIXME(ddraw,"(%p):interface for IID %s NOT found!\n",this,xrefiid);
1229 return OLE_E_ENUM_NOMORE;
1232 static HRESULT WINAPI IDirectDrawSurface4_IsLost(LPDIRECTDRAWSURFACE4 this) {
1233 TRACE(ddraw,"(%p)->(), stub!\n",this);
1234 return DD_OK; /* hmm */
1237 static HRESULT WINAPI IDirectDrawSurface4_EnumAttachedSurfaces(LPDIRECTDRAWSURFACE4 this,LPVOID context,LPDDENUMSURFACESCALLBACK esfcb) {
1238 FIXME(ddraw,"(%p)->(%p,%p),stub!\n",this,context,esfcb);
1242 static HRESULT WINAPI IDirectDrawSurface4_Restore(LPDIRECTDRAWSURFACE4 this) {
1243 FIXME(ddraw,"(%p)->(),stub!\n",this);
1247 static HRESULT WINAPI IDirectDrawSurface4_SetColorKey(
1248 LPDIRECTDRAWSURFACE4 this, DWORD dwFlags, LPDDCOLORKEY ckey )
1250 TRACE(ddraw,"(%p)->(0x%08lx,%p)\n",this,dwFlags,ckey);
1252 if( dwFlags & DDCKEY_SRCBLT )
1254 dwFlags &= ~DDCKEY_SRCBLT;
1255 this->s.surface_desc.dwFlags |= DDSD_CKSRCBLT;
1256 memcpy( &(this->s.surface_desc.ddckCKSrcBlt), ckey, sizeof( *ckey ) );
1259 if( dwFlags & DDCKEY_DESTBLT )
1261 dwFlags &= ~DDCKEY_DESTBLT;
1262 this->s.surface_desc.dwFlags |= DDSD_CKDESTBLT;
1263 memcpy( &(this->s.surface_desc.ddckCKDestBlt), ckey, sizeof( *ckey ) );
1266 if( dwFlags & DDCKEY_SRCOVERLAY )
1268 dwFlags &= ~DDCKEY_SRCOVERLAY;
1269 this->s.surface_desc.dwFlags |= DDSD_CKSRCOVERLAY;
1270 memcpy( &(this->s.surface_desc.ddckCKSrcOverlay), ckey, sizeof( *ckey ) );
1273 if( dwFlags & DDCKEY_DESTOVERLAY )
1275 dwFlags &= ~DDCKEY_DESTOVERLAY;
1276 this->s.surface_desc.dwFlags |= DDSD_CKDESTOVERLAY;
1277 memcpy( &(this->s.surface_desc.ddckCKDestOverlay), ckey, sizeof( *ckey ) );
1282 FIXME( ddraw, "unhandled dwFlags: 0x%08lx\n", dwFlags );
1289 static HRESULT WINAPI IDirectDrawSurface4_AddOverlayDirtyRect(
1290 LPDIRECTDRAWSURFACE4 this,
1293 FIXME(ddraw,"(%p)->(%p),stub!\n",this,lpRect);
1298 static HRESULT WINAPI IDirectDrawSurface4_DeleteAttachedSurface(
1299 LPDIRECTDRAWSURFACE4 this,
1301 LPDIRECTDRAWSURFACE4 lpDDSAttachedSurface )
1303 FIXME(ddraw,"(%p)->(0x%08lx,%p),stub!\n",this,dwFlags,lpDDSAttachedSurface);
1308 static HRESULT WINAPI IDirectDrawSurface4_EnumOverlayZOrders(
1309 LPDIRECTDRAWSURFACE4 this,
1312 LPDDENUMSURFACESCALLBACK lpfnCallback )
1314 FIXME(ddraw,"(%p)->(0x%08lx,%p,%p),stub!\n", this,dwFlags,
1315 lpContext, lpfnCallback );
1320 static HRESULT WINAPI IDirectDrawSurface4_GetClipper(
1321 LPDIRECTDRAWSURFACE4 this,
1322 LPDIRECTDRAWCLIPPER* lplpDDClipper )
1324 FIXME(ddraw,"(%p)->(%p),stub!\n", this, lplpDDClipper);
1329 static HRESULT WINAPI IDirectDrawSurface4_GetColorKey(
1330 LPDIRECTDRAWSURFACE4 this,
1332 LPDDCOLORKEY lpDDColorKey )
1334 TRACE(ddraw,"(%p)->(0x%08lx,%p)\n", this, dwFlags, lpDDColorKey);
1336 if( dwFlags & DDCKEY_SRCBLT ) {
1337 dwFlags &= ~DDCKEY_SRCBLT;
1338 memcpy( lpDDColorKey, &(this->s.surface_desc.ddckCKSrcBlt), sizeof( *lpDDColorKey ) );
1341 if( dwFlags & DDCKEY_DESTBLT )
1343 dwFlags &= ~DDCKEY_DESTBLT;
1344 memcpy( lpDDColorKey, &(this->s.surface_desc.ddckCKDestBlt), sizeof( *lpDDColorKey ) );
1347 if( dwFlags & DDCKEY_SRCOVERLAY )
1349 dwFlags &= ~DDCKEY_SRCOVERLAY;
1350 memcpy( lpDDColorKey, &(this->s.surface_desc.ddckCKSrcOverlay), sizeof( *lpDDColorKey ) );
1353 if( dwFlags & DDCKEY_DESTOVERLAY )
1355 dwFlags &= ~DDCKEY_DESTOVERLAY;
1356 memcpy( lpDDColorKey, &(this->s.surface_desc.ddckCKDestOverlay), sizeof( *lpDDColorKey ) );
1361 FIXME( ddraw, "unhandled dwFlags: 0x%08lx\n", dwFlags );
1367 static HRESULT WINAPI IDirectDrawSurface4_GetFlipStatus(
1368 LPDIRECTDRAWSURFACE4 this,
1371 FIXME(ddraw,"(%p)->(0x%08lx),stub!\n", this, dwFlags);
1376 static HRESULT WINAPI IDirectDrawSurface4_GetPalette(
1377 LPDIRECTDRAWSURFACE4 this,
1378 LPDIRECTDRAWPALETTE* lplpDDPalette )
1380 FIXME(ddraw,"(%p)->(%p),stub!\n", this, lplpDDPalette);
1385 static HRESULT WINAPI IDirectDrawSurface4_SetOverlayPosition(
1386 LPDIRECTDRAWSURFACE4 this,
1390 FIXME(ddraw,"(%p)->(%ld,%ld),stub!\n", this, lX, lY);
1395 static HRESULT WINAPI IDirectDrawSurface4_UpdateOverlay(
1396 LPDIRECTDRAWSURFACE4 this,
1398 LPDIRECTDRAWSURFACE4 lpDDDestSurface,
1399 LPRECT32 lpDestRect,
1401 LPDDOVERLAYFX lpDDOverlayFx )
1403 FIXME(ddraw,"(%p)->(%p,%p,%p,0x%08lx,%p),stub!\n", this,
1404 lpSrcRect, lpDDDestSurface, lpDestRect, dwFlags, lpDDOverlayFx );
1409 static HRESULT WINAPI IDirectDrawSurface4_UpdateOverlayDisplay(
1410 LPDIRECTDRAWSURFACE4 this,
1413 FIXME(ddraw,"(%p)->(0x%08lx),stub!\n", this, dwFlags);
1418 static HRESULT WINAPI IDirectDrawSurface4_UpdateOverlayZOrder(
1419 LPDIRECTDRAWSURFACE4 this,
1421 LPDIRECTDRAWSURFACE4 lpDDSReference )
1423 FIXME(ddraw,"(%p)->(0x%08lx,%p),stub!\n", this, dwFlags, lpDDSReference);
1428 static HRESULT WINAPI IDirectDrawSurface4_GetDDInterface(
1429 LPDIRECTDRAWSURFACE4 this,
1432 FIXME(ddraw,"(%p)->(%p),stub!\n", this, lplpDD);
1434 /* Not sure about that... */
1435 *lplpDD = (void *) this->s.ddraw;
1440 static HRESULT WINAPI IDirectDrawSurface4_PageLock(
1441 LPDIRECTDRAWSURFACE4 this,
1444 FIXME(ddraw,"(%p)->(0x%08lx),stub!\n", this, dwFlags);
1449 static HRESULT WINAPI IDirectDrawSurface4_PageUnlock(
1450 LPDIRECTDRAWSURFACE4 this,
1453 FIXME(ddraw,"(%p)->(0x%08lx),stub!\n", this, dwFlags);
1458 static HRESULT WINAPI IDirectDrawSurface4_SetSurfaceDesc(
1459 LPDIRECTDRAWSURFACE4 this,
1460 LPDDSURFACEDESC lpDDSD,
1463 FIXME(ddraw,"(%p)->(%p,0x%08lx),stub!\n", this, lpDDSD, dwFlags);
1468 static HRESULT WINAPI IDirectDrawSurface4_SetPrivateData(LPDIRECTDRAWSURFACE4 this,
1473 FIXME(ddraw, "(%p)->(%p,%p,%ld,%08lx\n", this, guidTag, lpData, cbSize, dwFlags);
1478 static HRESULT WINAPI IDirectDrawSurface4_GetPrivateData(LPDIRECTDRAWSURFACE4 this,
1481 LPDWORD lpcbBufferSize) {
1482 FIXME(ddraw, "(%p)->(%p,%p,%p)\n", this, guidTag, lpBuffer, lpcbBufferSize);
1487 static HRESULT WINAPI IDirectDrawSurface4_FreePrivateData(LPDIRECTDRAWSURFACE4 this,
1489 FIXME(ddraw, "(%p)->(%p)\n", this, guidTag);
1494 static HRESULT WINAPI IDirectDrawSurface4_GetUniquenessValue(LPDIRECTDRAWSURFACE4 this,
1496 FIXME(ddraw, "(%p)->(%p)\n", this, lpValue);
1501 static HRESULT WINAPI IDirectDrawSurface4_ChangeUniquenessValue(LPDIRECTDRAWSURFACE4 this) {
1502 FIXME(ddraw, "(%p)\n", this);
1507 static struct IDirectDrawSurface4_VTable dga_dds4vt = {
1508 IDirectDrawSurface4_QueryInterface,
1509 IDirectDrawSurface4_AddRef,
1510 DGA_IDirectDrawSurface4_Release,
1511 IDirectDrawSurface4_AddAttachedSurface,
1512 IDirectDrawSurface4_AddOverlayDirtyRect,
1513 IDirectDrawSurface4_Blt,
1514 IDirectDrawSurface4_BltBatch,
1515 IDirectDrawSurface4_BltFast,
1516 IDirectDrawSurface4_DeleteAttachedSurface,
1517 IDirectDrawSurface4_EnumAttachedSurfaces,
1518 IDirectDrawSurface4_EnumOverlayZOrders,
1519 DGA_IDirectDrawSurface4_Flip,
1520 IDirectDrawSurface4_GetAttachedSurface,
1521 IDirectDrawSurface4_GetBltStatus,
1522 IDirectDrawSurface4_GetCaps,
1523 IDirectDrawSurface4_GetClipper,
1524 IDirectDrawSurface4_GetColorKey,
1525 IDirectDrawSurface4_GetDC,
1526 IDirectDrawSurface4_GetFlipStatus,
1527 IDirectDrawSurface4_GetOverlayPosition,
1528 IDirectDrawSurface4_GetPalette,
1529 IDirectDrawSurface4_GetPixelFormat,
1530 IDirectDrawSurface4_GetSurfaceDesc,
1531 IDirectDrawSurface4_Initialize,
1532 IDirectDrawSurface4_IsLost,
1533 IDirectDrawSurface4_Lock,
1534 IDirectDrawSurface4_ReleaseDC,
1535 IDirectDrawSurface4_Restore,
1536 IDirectDrawSurface4_SetClipper,
1537 IDirectDrawSurface4_SetColorKey,
1538 IDirectDrawSurface4_SetOverlayPosition,
1539 DGA_IDirectDrawSurface4_SetPalette,
1540 DGA_IDirectDrawSurface4_Unlock,
1541 IDirectDrawSurface4_UpdateOverlay,
1542 IDirectDrawSurface4_UpdateOverlayDisplay,
1543 IDirectDrawSurface4_UpdateOverlayZOrder,
1544 IDirectDrawSurface4_GetDDInterface,
1545 IDirectDrawSurface4_PageLock,
1546 IDirectDrawSurface4_PageUnlock,
1547 IDirectDrawSurface4_SetSurfaceDesc,
1548 IDirectDrawSurface4_SetPrivateData,
1549 IDirectDrawSurface4_GetPrivateData,
1550 IDirectDrawSurface4_FreePrivateData,
1551 IDirectDrawSurface4_GetUniquenessValue,
1552 IDirectDrawSurface4_ChangeUniquenessValue
1555 static struct IDirectDrawSurface4_VTable xlib_dds4vt = {
1556 IDirectDrawSurface4_QueryInterface,
1557 IDirectDrawSurface4_AddRef,
1558 Xlib_IDirectDrawSurface4_Release,
1559 IDirectDrawSurface4_AddAttachedSurface,
1560 IDirectDrawSurface4_AddOverlayDirtyRect,
1561 IDirectDrawSurface4_Blt,
1562 IDirectDrawSurface4_BltBatch,
1563 IDirectDrawSurface4_BltFast,
1564 IDirectDrawSurface4_DeleteAttachedSurface,
1565 IDirectDrawSurface4_EnumAttachedSurfaces,
1566 IDirectDrawSurface4_EnumOverlayZOrders,
1567 Xlib_IDirectDrawSurface4_Flip,
1568 IDirectDrawSurface4_GetAttachedSurface,
1569 IDirectDrawSurface4_GetBltStatus,
1570 IDirectDrawSurface4_GetCaps,
1571 IDirectDrawSurface4_GetClipper,
1572 IDirectDrawSurface4_GetColorKey,
1573 IDirectDrawSurface4_GetDC,
1574 IDirectDrawSurface4_GetFlipStatus,
1575 IDirectDrawSurface4_GetOverlayPosition,
1576 IDirectDrawSurface4_GetPalette,
1577 IDirectDrawSurface4_GetPixelFormat,
1578 IDirectDrawSurface4_GetSurfaceDesc,
1579 IDirectDrawSurface4_Initialize,
1580 IDirectDrawSurface4_IsLost,
1581 IDirectDrawSurface4_Lock,
1582 IDirectDrawSurface4_ReleaseDC,
1583 IDirectDrawSurface4_Restore,
1584 IDirectDrawSurface4_SetClipper,
1585 IDirectDrawSurface4_SetColorKey,
1586 IDirectDrawSurface4_SetOverlayPosition,
1587 Xlib_IDirectDrawSurface4_SetPalette,
1588 Xlib_IDirectDrawSurface4_Unlock,
1589 IDirectDrawSurface4_UpdateOverlay,
1590 IDirectDrawSurface4_UpdateOverlayDisplay,
1591 IDirectDrawSurface4_UpdateOverlayZOrder,
1592 IDirectDrawSurface4_GetDDInterface,
1593 IDirectDrawSurface4_PageLock,
1594 IDirectDrawSurface4_PageUnlock,
1595 IDirectDrawSurface4_SetSurfaceDesc,
1596 IDirectDrawSurface4_SetPrivateData,
1597 IDirectDrawSurface4_GetPrivateData,
1598 IDirectDrawSurface4_FreePrivateData,
1599 IDirectDrawSurface4_GetUniquenessValue,
1600 IDirectDrawSurface4_ChangeUniquenessValue
1603 /******************************************************************************
1604 * DirectDrawCreateClipper (DDRAW.7)
1606 HRESULT WINAPI DirectDrawCreateClipper( DWORD dwFlags,
1607 LPDIRECTDRAWCLIPPER *lplpDDClipper,
1608 LPUNKNOWN pUnkOuter)
1610 TRACE(ddraw, "(%08lx,%p,%p)\n", dwFlags, lplpDDClipper, pUnkOuter);
1612 *lplpDDClipper = (LPDIRECTDRAWCLIPPER)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,sizeof(IDirectDrawClipper));
1613 (*lplpDDClipper)->lpvtbl = &ddclipvt;
1614 (*lplpDDClipper)->ref = 1;
1619 /******************************************************************************
1620 * IDirectDrawClipper
1622 static HRESULT WINAPI IDirectDrawClipper_SetHwnd(
1623 LPDIRECTDRAWCLIPPER this,DWORD x,HWND32 hwnd
1625 FIXME(ddraw,"(%p)->SetHwnd(0x%08lx,0x%08lx),stub!\n",this,x,(DWORD)hwnd);
1629 static ULONG WINAPI IDirectDrawClipper_Release(LPDIRECTDRAWCLIPPER this) {
1630 TRACE( ddraw, "(%p)->() decrementing from %lu.\n", this, this->ref );
1635 HeapFree(GetProcessHeap(),0,this);
1639 static HRESULT WINAPI IDirectDrawClipper_GetClipList(
1640 LPDIRECTDRAWCLIPPER this,LPRECT32 rects,LPRGNDATA lprgn,LPDWORD hmm
1642 FIXME(ddraw,"(%p,%p,%p,%p),stub!\n",this,rects,lprgn,hmm);
1647 static HRESULT WINAPI IDirectDrawClipper_SetClipList(
1648 LPDIRECTDRAWCLIPPER this,LPRGNDATA lprgn,DWORD hmm
1650 FIXME(ddraw,"(%p,%p,%ld),stub!\n",this,lprgn,hmm);
1654 static HRESULT WINAPI IDirectDrawClipper_QueryInterface(
1655 LPDIRECTDRAWCLIPPER this,
1659 FIXME(ddraw,"(%p)->(%p,%p),stub!\n",this,riid,ppvObj);
1660 return OLE_E_ENUM_NOMORE;
1663 static ULONG WINAPI IDirectDrawClipper_AddRef( LPDIRECTDRAWCLIPPER this )
1665 TRACE( ddraw, "(%p)->() incrementing from %lu.\n", this, this->ref );
1666 return ++(this->ref);
1669 static HRESULT WINAPI IDirectDrawClipper_GetHWnd(
1670 LPDIRECTDRAWCLIPPER this,
1673 FIXME(ddraw,"(%p)->(%p),stub!\n",this,HWndPtr);
1677 static HRESULT WINAPI IDirectDrawClipper_Initialize(
1678 LPDIRECTDRAWCLIPPER this,
1682 FIXME(ddraw,"(%p)->(%p,0x%08lx),stub!\n",this,lpDD,dwFlags);
1686 static HRESULT WINAPI IDirectDrawClipper_IsClipListChanged(
1687 LPDIRECTDRAWCLIPPER this,
1688 BOOL32* lpbChanged )
1690 FIXME(ddraw,"(%p)->(%p),stub!\n",this,lpbChanged);
1694 static struct IDirectDrawClipper_VTable ddclipvt = {
1695 IDirectDrawClipper_QueryInterface,
1696 IDirectDrawClipper_AddRef,
1697 IDirectDrawClipper_Release,
1698 IDirectDrawClipper_GetClipList,
1699 IDirectDrawClipper_GetHWnd,
1700 IDirectDrawClipper_Initialize,
1701 IDirectDrawClipper_IsClipListChanged,
1702 IDirectDrawClipper_SetClipList,
1703 IDirectDrawClipper_SetHwnd
1707 /******************************************************************************
1708 * IDirectDrawPalette
1710 static HRESULT WINAPI IDirectDrawPalette_GetEntries(
1711 LPDIRECTDRAWPALETTE this,DWORD x,DWORD start,DWORD count,LPPALETTEENTRY palent
1715 TRACE(ddraw,"(%p)->GetEntries(%08lx,%ld,%ld,%p)\n",
1716 this,x,start,count,palent);
1718 if (!this->cm) /* should not happen */ {
1719 FIXME(ddraw,"app tried to read colormap for non-palettized mode\n");
1720 return DDERR_GENERIC;
1722 for (i=0;i<count;i++) {
1723 palent[i].peRed = this->palents[start+i].peRed;
1724 palent[i].peBlue = this->palents[start+i].peBlue;
1725 palent[i].peGreen = this->palents[start+i].peGreen;
1726 palent[i].peFlags = this->palents[start+i].peFlags;
1732 static HRESULT WINAPI Xlib_IDirectDrawPalette_SetEntries(
1733 LPDIRECTDRAWPALETTE this,DWORD x,DWORD start,DWORD count,LPPALETTEENTRY palent
1738 TRACE(ddraw,"(%p)->SetEntries(%08lx,%ld,%ld,%p)\n",
1739 this,x,start,count,palent
1741 for (i=0;i<count;i++) {
1742 xc.red = palent[i].peRed<<8;
1743 xc.blue = palent[i].peBlue<<8;
1744 xc.green = palent[i].peGreen<<8;
1745 xc.flags = DoRed|DoBlue|DoGreen;
1749 TSXStoreColor(display,this->cm,&xc);
1751 this->palents[start+i].peRed = palent[i].peRed;
1752 this->palents[start+i].peBlue = palent[i].peBlue;
1753 this->palents[start+i].peGreen = palent[i].peGreen;
1754 this->palents[start+i].peFlags = palent[i].peFlags;
1757 /* Now, if we are in 'depth conversion mode', update the screen palette */
1758 if (this->ddraw->d.depth != this->ddraw->d.screen_depth) {
1761 switch (this->ddraw->d.screen_depth) {
1763 unsigned short *screen_palette = (unsigned short *) this->screen_palents;
1765 for (i = 0; i < count; i++) {
1766 screen_palette[start + i] = (((((unsigned short) palent[i].peRed) & 0xF8) << 8) |
1767 ((((unsigned short) palent[i].peBlue) & 0xF8) >> 3) |
1768 ((((unsigned short) palent[i].peGreen) & 0xFC) << 3));
1773 ERR(ddraw, "Memory corruption !\n");
1778 if (!this->cm) /* should not happen */ {
1783 static HRESULT WINAPI DGA_IDirectDrawPalette_SetEntries(
1784 LPDIRECTDRAWPALETTE this,DWORD x,DWORD start,DWORD count,LPPALETTEENTRY palent
1786 #ifdef HAVE_LIBXXF86DGA
1791 TRACE(ddraw,"(%p)->SetEntries(%08lx,%ld,%ld,%p)\n",
1792 this,x,start,count,palent
1794 if (!this->cm) /* should not happen */ {
1795 FIXME(ddraw,"app tried to set colormap in non-palettized mode\n");
1796 return DDERR_GENERIC;
1798 /* FIXME: free colorcells instead of freeing whole map */
1800 this->cm = TSXCopyColormapAndFree(display,this->cm);
1801 TSXFreeColormap(display,cm);
1803 for (i=0;i<count;i++) {
1804 xc.red = palent[i].peRed<<8;
1805 xc.blue = palent[i].peBlue<<8;
1806 xc.green = palent[i].peGreen<<8;
1807 xc.flags = DoRed|DoBlue|DoGreen;
1810 TSXStoreColor(display,this->cm,&xc);
1812 this->palents[start+i].peRed = palent[i].peRed;
1813 this->palents[start+i].peBlue = palent[i].peBlue;
1814 this->palents[start+i].peGreen = palent[i].peGreen;
1815 this->palents[start+i].peFlags = palent[i].peFlags;
1817 TSXF86DGAInstallColormap(display,DefaultScreen(display),this->cm);
1819 #else /* defined(HAVE_LIBXXF86DGA) */
1820 return E_UNEXPECTED;
1821 #endif /* defined(HAVE_LIBXXF86DGA) */
1824 static ULONG WINAPI IDirectDrawPalette_Release(LPDIRECTDRAWPALETTE this) {
1825 TRACE( ddraw, "(%p)->() decrementing from %lu.\n", this, this->ref );
1826 if (!--(this->ref)) {
1828 TSXFreeColormap(display,this->cm);
1831 HeapFree(GetProcessHeap(),0,this);
1837 static ULONG WINAPI IDirectDrawPalette_AddRef(LPDIRECTDRAWPALETTE this) {
1839 TRACE( ddraw, "(%p)->() incrementing from %lu.\n", this, this->ref );
1840 return ++(this->ref);
1843 static HRESULT WINAPI IDirectDrawPalette_Initialize(
1844 LPDIRECTDRAWPALETTE this,LPDIRECTDRAW ddraw,DWORD x,LPPALETTEENTRY palent
1846 TRACE(ddraw,"(%p)->(%p,%ld,%p)\n", this, ddraw, x, palent);
1848 return DDERR_ALREADYINITIALIZED;
1851 static HRESULT WINAPI IDirectDrawPalette_GetCaps(
1852 LPDIRECTDRAWPALETTE this, LPDWORD lpdwCaps )
1854 FIXME( ddraw, "(%p)->(%p) stub.\n", this, lpdwCaps );
1858 static HRESULT WINAPI IDirectDrawPalette_QueryInterface(
1859 LPDIRECTDRAWPALETTE this,REFIID refiid,LPVOID *obj )
1863 WINE_StringFromCLSID((LPCLSID)refiid,xrefiid);
1864 FIXME(ddraw,"(%p)->(%s,%p) stub.\n",this,xrefiid,obj);
1869 static struct IDirectDrawPalette_VTable dga_ddpalvt = {
1870 IDirectDrawPalette_QueryInterface,
1871 IDirectDrawPalette_AddRef,
1872 IDirectDrawPalette_Release,
1873 IDirectDrawPalette_GetCaps,
1874 IDirectDrawPalette_GetEntries,
1875 IDirectDrawPalette_Initialize,
1876 DGA_IDirectDrawPalette_SetEntries
1879 static struct IDirectDrawPalette_VTable xlib_ddpalvt = {
1880 IDirectDrawPalette_QueryInterface,
1881 IDirectDrawPalette_AddRef,
1882 IDirectDrawPalette_Release,
1883 IDirectDrawPalette_GetCaps,
1884 IDirectDrawPalette_GetEntries,
1885 IDirectDrawPalette_Initialize,
1886 Xlib_IDirectDrawPalette_SetEntries
1889 /*******************************************************************************
1892 static HRESULT WINAPI IDirect3D_QueryInterface(
1893 LPDIRECT3D this,REFIID refiid,LPVOID *obj
1895 /* FIXME: Not sure if this is correct */
1898 WINE_StringFromCLSID((LPCLSID)refiid,xrefiid);
1899 TRACE(ddraw,"(%p)->(%s,%p)\n",this,xrefiid,obj);
1900 if (!memcmp(&IID_IUnknown,refiid,sizeof(IID_IUnknown))) {
1902 this->lpvtbl->fnAddRef(this);
1904 TRACE(ddraw, " Creating IUnknown interface (%p)\n", *obj);
1908 if (!memcmp(&IID_IDirect3D,refiid,sizeof(IID_IDirect3D))) {
1911 d3d = HeapAlloc(GetProcessHeap(),0,sizeof(*d3d));
1913 d3d->ddraw = (LPDIRECTDRAW)this;
1914 this->lpvtbl->fnAddRef(this);
1915 d3d->lpvtbl = &d3dvt;
1918 TRACE(ddraw, " Creating IDirect3D interface (%p)\n", *obj);
1922 if (!memcmp(&IID_IDirect3D2,refiid,sizeof(IID_IDirect3D2))) {
1925 d3d = HeapAlloc(GetProcessHeap(),0,sizeof(*d3d));
1927 d3d->ddraw = (LPDIRECTDRAW)this;
1928 this->lpvtbl->fnAddRef(this);
1929 d3d->lpvtbl = &d3d2vt;
1932 TRACE(ddraw, " Creating IDirect3D2 interface (%p)\n", *obj);
1936 FIXME(ddraw,"(%p):interface for IID %s NOT found!\n",this,xrefiid);
1937 return OLE_E_ENUM_NOMORE;
1940 static ULONG WINAPI IDirect3D_AddRef(LPDIRECT3D this) {
1941 TRACE( ddraw, "(%p)->() incrementing from %lu.\n", this, this->ref );
1943 return ++(this->ref);
1946 static ULONG WINAPI IDirect3D_Release(LPDIRECT3D this)
1948 TRACE( ddraw, "(%p)->() decrementing from %lu.\n", this, this->ref );
1950 if (!--(this->ref)) {
1951 this->ddraw->lpvtbl->fnRelease(this->ddraw);
1952 HeapFree(GetProcessHeap(),0,this);
1958 static HRESULT WINAPI IDirect3D_Initialize(
1959 LPDIRECT3D this, REFIID refiid )
1961 /* FIXME: Not sure if this is correct */
1964 WINE_StringFromCLSID((LPCLSID)refiid,xrefiid);
1965 FIXME(ddraw,"(%p)->(%s):stub.\n",this,xrefiid);
1967 return DDERR_ALREADYINITIALIZED;
1970 static HRESULT WINAPI IDirect3D_EnumDevices(LPDIRECT3D this,
1971 LPD3DENUMDEVICESCALLBACK cb,
1973 FIXME(ddraw,"(%p)->(%p,%p),stub!\n",this,cb,context);
1975 /* Call functions defined in d3ddevices.c */
1976 if (d3d_OpenGL_dx3(cb, context))
1982 static HRESULT WINAPI IDirect3D_CreateLight(LPDIRECT3D this,
1983 LPDIRECT3DLIGHT *lplight,
1986 TRACE(ddraw, "(%p)->(%p,%p): stub\n", this, lplight, lpunk);
1988 /* Call the creation function that is located in d3dlight.c */
1989 *lplight = d3dlight_create_dx3(this);
1994 static HRESULT WINAPI IDirect3D_CreateMaterial(LPDIRECT3D this,
1995 LPDIRECT3DMATERIAL *lpmaterial,
1998 TRACE(ddraw, "(%p)->(%p,%p): stub\n", this, lpmaterial, lpunk);
2000 /* Call the creation function that is located in d3dviewport.c */
2001 *lpmaterial = d3dmaterial_create(this);
2006 static HRESULT WINAPI IDirect3D_CreateViewport(LPDIRECT3D this,
2007 LPDIRECT3DVIEWPORT *lpviewport,
2010 TRACE(ddraw, "(%p)->(%p,%p): stub\n", this, lpviewport, lpunk);
2012 /* Call the creation function that is located in d3dviewport.c */
2013 *lpviewport = d3dviewport_create(this);
2018 static HRESULT WINAPI IDirect3D_FindDevice(LPDIRECT3D this,
2019 LPD3DFINDDEVICESEARCH lpfinddevsrc,
2020 LPD3DFINDDEVICERESULT lpfinddevrst)
2022 TRACE(ddraw, "(%p)->(%p,%p): stub\n", this, lpfinddevsrc, lpfinddevrst);
2027 static struct IDirect3D_VTable d3dvt = {
2028 IDirect3D_QueryInterface,
2031 IDirect3D_Initialize,
2032 IDirect3D_EnumDevices,
2033 IDirect3D_CreateLight,
2034 IDirect3D_CreateMaterial,
2035 IDirect3D_CreateViewport,
2036 IDirect3D_FindDevice
2039 /*******************************************************************************
2042 static HRESULT WINAPI IDirect3D2_QueryInterface(
2043 LPDIRECT3D2 this,REFIID refiid,LPVOID *obj) {
2044 /* For the moment, we use the same function as in IDirect3D */
2045 TRACE(ddraw, "Calling IDirect3D enumerating function.\n");
2047 return IDirect3D_QueryInterface((LPDIRECT3D) this, refiid, obj);
2050 static ULONG WINAPI IDirect3D2_AddRef(LPDIRECT3D2 this) {
2051 TRACE( ddraw, "(%p)->() incrementing from %lu.\n", this, this->ref );
2053 return ++(this->ref);
2056 static ULONG WINAPI IDirect3D2_Release(LPDIRECT3D2 this) {
2057 TRACE( ddraw, "(%p)->() decrementing from %lu.\n", this, this->ref );
2059 if (!--(this->ref)) {
2060 this->ddraw->lpvtbl->fnRelease(this->ddraw);
2061 HeapFree(GetProcessHeap(),0,this);
2067 static HRESULT WINAPI IDirect3D2_EnumDevices(
2068 LPDIRECT3D2 this,LPD3DENUMDEVICESCALLBACK cb, LPVOID context
2070 FIXME(ddraw,"(%p)->(%p,%p),stub!\n",this,cb,context);
2072 /* Call functions defined in d3ddevices.c */
2073 if (d3d_OpenGL(cb, context))
2079 static HRESULT WINAPI IDirect3D2_CreateLight(LPDIRECT3D2 this,
2080 LPDIRECT3DLIGHT *lplight,
2083 TRACE(ddraw, "(%p)->(%p,%p): stub\n", this, lplight, lpunk);
2085 /* Call the creation function that is located in d3dlight.c */
2086 *lplight = d3dlight_create(this);
2091 static HRESULT WINAPI IDirect3D2_CreateMaterial(LPDIRECT3D2 this,
2092 LPDIRECT3DMATERIAL2 *lpmaterial,
2095 TRACE(ddraw, "(%p)->(%p,%p): stub\n", this, lpmaterial, lpunk);
2097 /* Call the creation function that is located in d3dviewport.c */
2098 *lpmaterial = d3dmaterial2_create(this);
2103 static HRESULT WINAPI IDirect3D2_CreateViewport(LPDIRECT3D2 this,
2104 LPDIRECT3DVIEWPORT2 *lpviewport,
2107 TRACE(ddraw, "(%p)->(%p,%p): stub\n", this, lpviewport, lpunk);
2109 /* Call the creation function that is located in d3dviewport.c */
2110 *lpviewport = d3dviewport2_create(this);
2115 static HRESULT WINAPI IDirect3D2_FindDevice(LPDIRECT3D2 this,
2116 LPD3DFINDDEVICESEARCH lpfinddevsrc,
2117 LPD3DFINDDEVICERESULT lpfinddevrst)
2119 TRACE(ddraw, "(%p)->(%p,%p): stub\n", this, lpfinddevsrc, lpfinddevrst);
2124 static HRESULT WINAPI IDirect3D2_CreateDevice(LPDIRECT3D2 this,
2126 LPDIRECTDRAWSURFACE surface,
2127 LPDIRECT3DDEVICE2 *device)
2131 WINE_StringFromCLSID(rguid,xbuf);
2132 FIXME(ddraw,"(%p)->(%s,%p,%p): stub\n",this,xbuf,surface,device);
2134 if (is_OpenGL(rguid, surface, device, this)) {
2135 this->lpvtbl->fnAddRef(this);
2139 return DDERR_INVALIDPARAMS;
2142 static struct IDirect3D2_VTable d3d2vt = {
2143 IDirect3D2_QueryInterface,
2146 IDirect3D2_EnumDevices,
2147 IDirect3D2_CreateLight,
2148 IDirect3D2_CreateMaterial,
2149 IDirect3D2_CreateViewport,
2150 IDirect3D2_FindDevice,
2151 IDirect3D2_CreateDevice
2154 /*******************************************************************************
2158 /* Used in conjunction with cbWndExtra for storage of the this ptr for the window.
2159 * Please adjust allocation in Xlib_DirectDrawCreate if you store more data here.
2161 static INT32 ddrawXlibThisOffset = 0;
2163 static HRESULT common_off_screen_CreateSurface(LPDIRECTDRAW2 this,
2164 LPDDSURFACEDESC lpddsd,
2165 LPDIRECTDRAWSURFACE lpdsf)
2169 /* The surface was already allocated when entering in this function */
2170 TRACE(ddraw,"using system memory for a surface (%p)\n", lpdsf);
2172 if (lpddsd->dwFlags & DDSD_ZBUFFERBITDEPTH) {
2173 /* This is a Z Buffer */
2174 TRACE(ddraw, "Creating Z-Buffer of %ld bit depth\n", lpddsd->x.dwZBufferBitDepth);
2175 bpp = lpddsd->x.dwZBufferBitDepth / 8;
2177 /* This is a standard image */
2178 if (!(lpddsd->dwFlags & DDSD_PIXELFORMAT)) {
2179 /* No pixel format => use DirectDraw's format */
2180 _getpixelformat(this,&(lpddsd->ddpfPixelFormat));
2181 lpddsd->dwFlags |= DDSD_PIXELFORMAT;
2183 /* To check what the program wants */
2184 if (TRACE_ON(ddraw)) {
2185 _dump_pixelformat(&(lpddsd->ddpfPixelFormat));
2189 if (lpddsd->ddpfPixelFormat.dwFlags & DDPF_PALETTEINDEXED8) {
2192 bpp = lpddsd->ddpfPixelFormat.x.dwRGBBitCount / 8;
2196 /* Copy the surface description */
2197 lpdsf->s.surface_desc = *lpddsd;
2199 lpdsf->s.surface_desc.dwFlags |= DDSD_WIDTH|DDSD_HEIGHT|DDSD_PITCH|DDSD_LPSURFACE;
2200 lpdsf->s.surface_desc.y.lpSurface = (LPBYTE)HeapAlloc(GetProcessHeap(),0,lpddsd->dwWidth * lpddsd->dwHeight * bpp);
2201 lpdsf->s.surface_desc.lPitch = lpddsd->dwWidth * bpp;
2206 static HRESULT WINAPI DGA_IDirectDraw2_CreateSurface(
2207 LPDIRECTDRAW2 this,LPDDSURFACEDESC lpddsd,LPDIRECTDRAWSURFACE *lpdsf,IUnknown *lpunk
2209 #ifdef HAVE_LIBXXF86DGA
2212 TRACE(ddraw, "(%p)->(%p,%p,%p)\n",this,lpddsd,lpdsf,lpunk);
2213 if (TRACE_ON(ddraw)) {
2214 DUMP("[w=%ld,h=%ld,flags ",lpddsd->dwWidth,lpddsd->dwHeight);
2215 _dump_DDSD(lpddsd->dwFlags);
2216 fprintf(stderr,"caps ");
2217 _dump_DDSCAPS(lpddsd->ddsCaps.dwCaps);
2218 fprintf(stderr,"]\n");
2221 *lpdsf = (LPDIRECTDRAWSURFACE)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,sizeof(IDirectDrawSurface));
2222 this->lpvtbl->fnAddRef(this);
2225 (*lpdsf)->lpvtbl = (LPDIRECTDRAWSURFACE_VTABLE)&dga_dds4vt;
2226 (*lpdsf)->s.ddraw = this;
2227 (*lpdsf)->s.palette = NULL;
2228 (*lpdsf)->t.dga.fb_height = -1; /* This is to have non-on screen surfaces freed */
2230 if (!(lpddsd->dwFlags & DDSD_WIDTH))
2231 lpddsd->dwWidth = this->d.width;
2232 if (!(lpddsd->dwFlags & DDSD_HEIGHT))
2233 lpddsd->dwHeight = this->d.height;
2235 /* Check if this a 'primary surface' or not */
2236 if ((lpddsd->dwFlags & DDSD_CAPS) &&
2237 (lpddsd->ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE)) {
2239 /* This is THE primary surface => there is DGA-specific code */
2240 /* First, store the surface description */
2241 (*lpdsf)->s.surface_desc = *lpddsd;
2243 /* Find a viewport */
2245 if (!(this->e.dga.vpmask & (1<<i)))
2247 TRACE(ddraw,"using viewport %d for a primary surface\n",i);
2248 /* if i == 32 or maximum ... return error */
2249 this->e.dga.vpmask|=(1<<i);
2250 (*lpdsf)->s.surface_desc.y.lpSurface =
2251 this->e.dga.fb_addr+((i*this->e.dga.fb_height)*this->e.dga.fb_width*this->d.depth/8);
2252 (*lpdsf)->t.dga.fb_height = i*this->e.dga.fb_height;
2253 (*lpdsf)->s.surface_desc.lPitch = this->e.dga.fb_width*this->d.depth/8;
2254 lpddsd->lPitch = (*lpdsf)->s.surface_desc.lPitch;
2256 /* Add flags if there were not present */
2257 (*lpdsf)->s.surface_desc.dwFlags |= DDSD_WIDTH|DDSD_HEIGHT|DDSD_PITCH|DDSD_LPSURFACE;
2258 (*lpdsf)->s.surface_desc.dwWidth = this->d.width;
2259 (*lpdsf)->s.surface_desc.dwHeight = this->d.height;
2260 TRACE(ddraw,"primary surface: dwWidth=%ld, dwHeight=%ld, lPitch=%ld\n",this->d.width,this->d.height,lpddsd->lPitch);
2261 /* We put our surface always in video memory */
2262 (*lpdsf)->s.surface_desc.ddsCaps.dwCaps |= DDSCAPS_VISIBLE|DDSCAPS_VIDEOMEMORY;
2263 _getpixelformat(this,&((*lpdsf)->s.surface_desc.ddpfPixelFormat));
2264 (*lpdsf)->s.backbuffer = NULL;
2266 if (lpddsd->dwFlags & DDSD_BACKBUFFERCOUNT) {
2267 LPDIRECTDRAWSURFACE4 back;
2269 if (lpddsd->dwBackBufferCount>1)
2270 FIXME(ddraw,"urks, wants to have more than one backbuffer (%ld)!\n",lpddsd->dwBackBufferCount);
2272 (*lpdsf)->s.backbuffer = back =
2273 (LPDIRECTDRAWSURFACE4)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,sizeof(IDirectDrawSurface4));
2274 this->lpvtbl->fnAddRef(this);
2276 back->lpvtbl = (LPDIRECTDRAWSURFACE4_VTABLE)&dga_dds4vt;
2278 if (!(this->e.dga.vpmask & (1<<i)))
2280 TRACE(ddraw,"using viewport %d for backbuffer\n",i);
2281 /* if i == 32 or maximum ... return error */
2282 this->e.dga.vpmask|=(1<<i);
2283 back->t.dga.fb_height = i*this->e.dga.fb_height;
2285 /* Copy the surface description from the front buffer */
2286 back->s.surface_desc = (*lpdsf)->s.surface_desc;
2287 /* Change the parameters that are not the same */
2288 back->s.surface_desc.y.lpSurface = this->e.dga.fb_addr+
2289 ((i*this->e.dga.fb_height)*this->e.dga.fb_width*this->d.depth/8);
2290 back->s.ddraw = this;
2291 back->s.backbuffer = NULL; /* does not have a backbuffer, it is
2294 /* Add relevant info to front and back buffers */
2295 (*lpdsf)->s.surface_desc.ddsCaps.dwCaps |= DDSCAPS_FRONTBUFFER;
2296 back->s.surface_desc.ddsCaps.dwCaps |= DDSCAPS_BACKBUFFER;
2297 back->s.surface_desc.dwFlags &= ~DDSD_BACKBUFFERCOUNT;
2298 back->s.surface_desc.ddsCaps.dwCaps &= ~DDSCAPS_VISIBLE;
2299 back->s.surface_desc.ddsCaps.dwCaps |= DDSCAPS_VIDEOMEMORY;
2302 /* There is no DGA-specific code here...
2303 Go to the common surface creation function */
2304 return common_off_screen_CreateSurface(this, lpddsd, *lpdsf);
2308 #else /* defined(HAVE_LIBXXF86DGA) */
2309 return E_UNEXPECTED;
2310 #endif /* defined(HAVE_LIBXXF86DGA) */
2313 static XImage *create_ximage(LPDIRECTDRAW2 this, LPDIRECTDRAWSURFACE4 lpdsf) {
2317 #ifdef HAVE_LIBXXSHM
2318 if (this->e.xlib.xshm_active) {
2319 img = TSXShmCreateImage(display,
2320 DefaultVisualOfScreen(X11DRV_GetXScreen()),
2321 this->d.screen_depth,
2324 &(lpdsf->t.xlib.shminfo),
2325 lpdsf->s.surface_desc.dwWidth,
2326 lpdsf->s.surface_desc.dwHeight);
2331 lpdsf->t.xlib.shminfo.shmid = shmget( IPC_PRIVATE, img->bytes_per_line * img->height, IPC_CREAT|0777 );
2332 if (lpdsf->t.xlib.shminfo.shmid < 0) {
2333 TSXDestroyImage(img);
2337 lpdsf->t.xlib.shminfo.shmaddr = img->data = (char*)shmat(lpdsf->t.xlib.shminfo.shmid, 0, 0);
2339 if (img->data == (char *) -1) {
2340 TSXDestroyImage(img);
2341 shmctl(lpdsf->t.xlib.shminfo.shmid, IPC_RMID, 0);
2344 lpdsf->t.xlib.shminfo.readOnly = False;
2346 TSXShmAttach(display, &(lpdsf->t.xlib.shminfo));
2347 TSXSync(display, False);
2349 shmctl(lpdsf->t.xlib.shminfo.shmid, IPC_RMID, 0);
2351 if (this->d.depth != this->d.screen_depth) {
2352 lpdsf->s.surface_desc.y.lpSurface = HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,
2353 lpdsf->s.surface_desc.dwWidth *
2354 lpdsf->s.surface_desc.dwHeight *
2355 (this->d.depth / 8));
2357 lpdsf->s.surface_desc.y.lpSurface = img->data;
2361 /* Allocate surface memory */
2362 lpdsf->s.surface_desc.y.lpSurface = HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,
2363 lpdsf->s.surface_desc.dwWidth *
2364 lpdsf->s.surface_desc.dwHeight *
2365 (this->d.depth / 8));
2367 if (this->d.depth != this->d.screen_depth) {
2368 img_data = HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,
2369 lpdsf->s.surface_desc.dwWidth *
2370 lpdsf->s.surface_desc.dwHeight *
2371 (this->d.screen_depth / 8));
2373 img_data = lpdsf->s.surface_desc.y.lpSurface;
2376 /* In this case, create an XImage */
2378 TSXCreateImage(display,
2379 DefaultVisualOfScreen(X11DRV_GetXScreen()),
2380 this->d.screen_depth,
2384 lpdsf->s.surface_desc.dwWidth,
2385 lpdsf->s.surface_desc.dwHeight,
2387 lpdsf->s.surface_desc.dwWidth * (this->d.screen_depth / 8)
2390 #ifdef HAVE_LIBXXSHM
2393 if (this->d.depth != this->d.screen_depth) {
2394 lpdsf->s.surface_desc.lPitch = (this->d.depth / 8) * lpdsf->s.surface_desc.dwWidth;
2396 lpdsf->s.surface_desc.lPitch = img->bytes_per_line;
2402 static HRESULT WINAPI Xlib_IDirectDraw2_CreateSurface(
2403 LPDIRECTDRAW2 this,LPDDSURFACEDESC lpddsd,LPDIRECTDRAWSURFACE *lpdsf,IUnknown *lpunk
2405 TRACE(ddraw, "(%p)->CreateSurface(%p,%p,%p)\n",
2406 this,lpddsd,lpdsf,lpunk);
2408 if (TRACE_ON(ddraw)) {
2409 fprintf(stderr,"[w=%ld,h=%ld,flags ",lpddsd->dwWidth,lpddsd->dwHeight);
2410 _dump_DDSD(lpddsd->dwFlags);
2411 fprintf(stderr,"caps ");
2412 _dump_DDSCAPS(lpddsd->ddsCaps.dwCaps);
2413 fprintf(stderr,"]\n");
2416 *lpdsf = (LPDIRECTDRAWSURFACE)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,sizeof(IDirectDrawSurface));
2418 this->lpvtbl->fnAddRef(this);
2419 (*lpdsf)->s.ddraw = this;
2421 (*lpdsf)->lpvtbl = (LPDIRECTDRAWSURFACE_VTABLE)&xlib_dds4vt;
2422 (*lpdsf)->s.palette = NULL;
2423 (*lpdsf)->t.xlib.image = NULL; /* This is for off-screen buffers */
2425 if (!(lpddsd->dwFlags & DDSD_WIDTH))
2426 lpddsd->dwWidth = this->d.width;
2427 if (!(lpddsd->dwFlags & DDSD_HEIGHT))
2428 lpddsd->dwHeight = this->d.height;
2430 /* Check if this a 'primary surface' or not */
2431 if ((lpddsd->dwFlags & DDSD_CAPS) &&
2432 (lpddsd->ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE)) {
2435 TRACE(ddraw,"using standard XImage for a primary surface (%p)\n", *lpdsf);
2437 /* First, store the surface description */
2438 (*lpdsf)->s.surface_desc = *lpddsd;
2440 /* Create the XImage */
2441 img = create_ximage(this, (LPDIRECTDRAWSURFACE4) *lpdsf);
2443 return DDERR_OUTOFMEMORY;
2444 (*lpdsf)->t.xlib.image = img;
2446 /* Add flags if there were not present */
2447 (*lpdsf)->s.surface_desc.dwFlags |= DDSD_WIDTH|DDSD_HEIGHT|DDSD_PITCH|DDSD_LPSURFACE;
2448 (*lpdsf)->s.surface_desc.dwWidth = this->d.width;
2449 (*lpdsf)->s.surface_desc.dwHeight = this->d.height;
2450 (*lpdsf)->s.surface_desc.ddsCaps.dwCaps |= DDSCAPS_VISIBLE|DDSCAPS_VIDEOMEMORY;
2451 _getpixelformat(this,&((*lpdsf)->s.surface_desc.ddpfPixelFormat));
2452 (*lpdsf)->s.backbuffer = NULL;
2454 /* Check for backbuffers */
2455 if (lpddsd->dwFlags & DDSD_BACKBUFFERCOUNT) {
2456 LPDIRECTDRAWSURFACE4 back;
2459 if (lpddsd->dwBackBufferCount>1)
2460 FIXME(ddraw,"urks, wants to have more than one backbuffer (%ld)!\n",lpddsd->dwBackBufferCount);
2462 (*lpdsf)->s.backbuffer = back =
2463 (LPDIRECTDRAWSURFACE4)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,sizeof(IDirectDrawSurface4));
2465 TRACE(ddraw,"allocated back-buffer (%p)\n", back);
2467 this->lpvtbl->fnAddRef(this);
2468 back->s.ddraw = this;
2471 back->lpvtbl = (LPDIRECTDRAWSURFACE4_VTABLE)&xlib_dds4vt;
2472 /* Copy the surface description from the front buffer */
2473 back->s.surface_desc = (*lpdsf)->s.surface_desc;
2475 /* Create the XImage */
2476 img = create_ximage(this, back);
2478 return DDERR_OUTOFMEMORY;
2479 back->t.xlib.image = img;
2481 back->s.backbuffer = NULL; /* does not have a backbuffer, it is
2484 /* Add relevant info to front and back buffers */
2485 (*lpdsf)->s.surface_desc.ddsCaps.dwCaps |= DDSCAPS_FRONTBUFFER;
2486 back->s.surface_desc.ddsCaps.dwCaps |= DDSCAPS_BACKBUFFER;
2487 back->s.surface_desc.dwFlags &= ~DDSD_BACKBUFFERCOUNT;
2488 back->s.surface_desc.ddsCaps.dwCaps &= ~DDSCAPS_VISIBLE;
2489 back->s.surface_desc.ddsCaps.dwCaps |= DDSCAPS_VIDEOMEMORY;
2492 /* There is no Xlib-specific code here...
2493 Go to the common surface creation function */
2494 return common_off_screen_CreateSurface(this, lpddsd, *lpdsf);
2500 static HRESULT WINAPI IDirectDraw2_DuplicateSurface(
2501 LPDIRECTDRAW2 this,LPDIRECTDRAWSURFACE src,LPDIRECTDRAWSURFACE *dst
2503 FIXME(ddraw,"(%p)->(%p,%p) simply copies\n",this,src,dst);
2504 *dst = src; /* FIXME */
2509 * The Xlib Implementation tries to use the passed hwnd as drawing window,
2510 * even when the approbiate bitmasks are not specified.
2512 static HRESULT WINAPI IDirectDraw2_SetCooperativeLevel(
2513 LPDIRECTDRAW2 this,HWND32 hwnd,DWORD cooplevel
2520 FE(DDSCL_FULLSCREEN)
2521 FE(DDSCL_ALLOWREBOOT)
2522 FE(DDSCL_NOWINDOWCHANGES)
2524 FE(DDSCL_ALLOWMODEX)
2526 FE(DDSCL_SETFOCUSWINDOW)
2527 FE(DDSCL_SETDEVICEWINDOW)
2528 FE(DDSCL_CREATEDEVICEWINDOW)
2531 FIXME(ddraw,"(%p)->(%08lx,%08lx)\n",this,(DWORD)hwnd,cooplevel);
2532 if(TRACE_ON(ddraw)){
2533 dbg_decl_str(ddraw, 512);
2534 for (i=0;i<sizeof(flagmap)/sizeof(flagmap[0]);i++)
2535 if (flagmap[i].mask & cooplevel)
2536 dsprintf(ddraw, "%s ", flagmap[i].name);
2537 TRACE(ddraw," cooperative level %s\n", dbg_str(ddraw));
2539 this->d.mainWindow = hwnd;
2541 /* This will be overwritten in the case of Full Screen mode.
2542 Windowed games could work with that :-) */
2544 this->d.drawable = X11DRV_WND_GetXWindow(WIN_FindWndPtr(hwnd));
2549 /* Small helper to either use the cooperative window or create a new
2550 * one (for mouse and keyboard input) and drawing in the Xlib implementation.
2552 static void _common_IDirectDraw_SetDisplayMode(LPDIRECTDRAW this) {
2555 /* Do not destroy the application supplied cooperative window */
2556 if (this->d.window && this->d.window != this->d.mainWindow) {
2557 DestroyWindow32(this->d.window);
2560 /* Sanity check cooperative window before assigning it to drawing. */
2561 if ( IsWindow32(this->d.mainWindow) &&
2562 IsWindowVisible32(this->d.mainWindow)
2564 GetWindowRect32(this->d.mainWindow,&rect);
2565 if (((rect.right-rect.left) >= this->d.width) &&
2566 ((rect.bottom-rect.top) >= this->d.height)
2568 this->d.window = this->d.mainWindow;
2570 /* ... failed, create new one. */
2571 if (!this->d.window) {
2572 this->d.window = CreateWindowEx32A(
2576 WS_VISIBLE|WS_SYSMENU|WS_THICKFRAME,
2585 /*Store THIS with the window. We'll use it in the window procedure*/
2586 SetWindowLong32A(this->d.window,ddrawXlibThisOffset,(LONG)this);
2587 ShowWindow32(this->d.window,TRUE);
2588 UpdateWindow32(this->d.window);
2590 SetFocus32(this->d.window);
2593 static HRESULT WINAPI DGA_IDirectDraw_SetDisplayMode(
2594 LPDIRECTDRAW this,DWORD width,DWORD height,DWORD depth
2596 #ifdef HAVE_LIBXXF86DGA
2597 int i,*depths,depcount,mode_count;
2599 TRACE(ddraw, "(%p)->(%ld,%ld,%ld)\n", this, width, height, depth);
2601 /* We hope getting the asked for depth */
2602 this->d.screen_depth = depth;
2604 depths = TSXListDepths(display,DefaultScreen(display),&depcount);
2606 for (i=0;i<depcount;i++)
2607 if (depths[i]==depth)
2610 if (i==depcount) {/* not found */
2611 ERR(ddraw,"(w=%ld,h=%ld,d=%ld), unsupported depth!\n",width,height,depth);
2612 return DDERR_UNSUPPORTEDMODE;
2614 if (this->d.width < width) {
2615 ERR(ddraw,"SetDisplayMode(w=%ld,h=%ld,d=%ld), width %ld exceeds framebuffer width %ld\n",width,height,depth,width,this->d.width);
2616 return DDERR_UNSUPPORTEDMODE;
2618 this->d.width = width;
2619 this->d.height = height;
2620 this->d.depth = depth;
2622 /* adjust fb_height, so we don't overlap */
2623 if (this->e.dga.fb_height < height)
2624 this->e.dga.fb_height = height;
2625 _common_IDirectDraw_SetDisplayMode(this);
2627 #ifdef HAVE_LIBXXF86VM
2629 XF86VidModeModeInfo **all_modes, *vidmode = NULL;
2630 XF86VidModeModeLine mod_tmp;
2631 /* int dotclock_tmp; */
2633 /* save original video mode and set fullscreen if available*/
2634 orig_mode = (XF86VidModeModeInfo *) malloc (sizeof(XF86VidModeModeInfo));
2635 TSXF86VidModeGetModeLine(display, DefaultScreen(display), &orig_mode->dotclock, &mod_tmp);
2636 orig_mode->hdisplay = mod_tmp.hdisplay;
2637 orig_mode->hsyncstart = mod_tmp.hsyncstart;
2638 orig_mode->hsyncend = mod_tmp.hsyncend;
2639 orig_mode->htotal = mod_tmp.htotal;
2640 orig_mode->vdisplay = mod_tmp.vdisplay;
2641 orig_mode->vsyncstart = mod_tmp.vsyncstart;
2642 orig_mode->vsyncend = mod_tmp.vsyncend;
2643 orig_mode->vtotal = mod_tmp.vtotal;
2644 orig_mode->flags = mod_tmp.flags;
2645 orig_mode->private = mod_tmp.private;
2647 TSXF86VidModeGetAllModeLines(display,DefaultScreen(display),&mode_count,&all_modes);
2648 for (i=0;i<mode_count;i++)
2650 if (all_modes[i]->hdisplay == width && all_modes[i]->vdisplay == height)
2652 vidmode = (XF86VidModeModeInfo *)malloc(sizeof(XF86VidModeModeInfo));
2653 *vidmode = *(all_modes[i]);
2656 TSXFree(all_modes[i]->private);
2658 for (i++;i<mode_count;i++) TSXFree(all_modes[i]->private);
2662 WARN(ddraw, "Fullscreen mode not available!\n");
2666 TRACE(ddraw,"SwitchToMode(%dx%d)\n",vidmode->hdisplay,vidmode->vdisplay);
2667 TSXF86VidModeSwitchToMode(display, DefaultScreen(display), vidmode);
2668 #if 0 /* This messes up my screen (XF86_Mach64, 3.3.2.3a) for some reason, and should now be unnecessary */
2669 TSXF86VidModeSetViewPort(display, DefaultScreen(display), 0, 0);
2675 /* FIXME: this function OVERWRITES several signal handlers.
2676 * can we save them? and restore them later? In a way that
2677 * it works for the library too?
2679 TSXF86DGADirectVideo(display,DefaultScreen(display),XF86DGADirectGraphics);
2681 TSXF86DGASetViewPort(display,DefaultScreen(display),0,this->e.dga.fb_height);
2683 TSXF86DGASetViewPort(display,DefaultScreen(display),0,0);
2686 #ifdef RESTORE_SIGNALS
2687 if (SIGNAL_Reinit) SIGNAL_Reinit();
2690 #else /* defined(HAVE_LIBXXF86DGA) */
2691 return E_UNEXPECTED;
2692 #endif /* defined(HAVE_LIBXXF86DGA) */
2695 static HRESULT WINAPI Xlib_IDirectDraw_SetDisplayMode(
2696 LPDIRECTDRAW this,DWORD width,DWORD height,DWORD depth
2698 int i,*depths,depcount;
2701 TRACE(ddraw, "(%p)->SetDisplayMode(%ld,%ld,%ld)\n",
2702 this, width, height, depth);
2704 /* We hope getting the asked for depth */
2705 this->d.screen_depth = depth;
2707 depths = TSXListDepths(display,DefaultScreen(display),&depcount);
2709 for (i=0;i<depcount;i++)
2710 if (depths[i]==depth)
2712 if (i==depcount) {/* not found */
2713 for (i=0;i<depcount;i++)
2718 sprintf(buf,"SetDisplayMode(w=%ld,h=%ld,d=%ld), unsupported depth!",width,height,depth);
2719 MessageBox32A(0,buf,"WINE DirectDraw",MB_OK|MB_ICONSTOP);
2721 return DDERR_UNSUPPORTEDMODE;
2723 WARN(ddraw, "Warning : running in depth-convertion mode. Should run using a %ld depth for optimal performances.\n", depth);
2724 this->d.screen_depth = 16;
2729 this->d.width = width;
2730 this->d.height = height;
2731 this->d.depth = depth;
2733 _common_IDirectDraw_SetDisplayMode(this);
2735 this->d.paintable = 1;
2736 this->d.drawable = ((X11DRV_WND_DATA *) WIN_FindWndPtr(this->d.window)->pDriverData)->window;
2737 /* We don't have a context for this window. Host off the desktop */
2738 if( !this->d.drawable )
2739 this->d.drawable = ((X11DRV_WND_DATA *) WIN_GetDesktop()->pDriverData)->window;
2743 static HRESULT WINAPI DGA_IDirectDraw2_GetCaps(
2744 LPDIRECTDRAW2 this,LPDDCAPS caps1,LPDDCAPS caps2
2746 #ifdef HAVE_LIBXXF86DGA
2747 TRACE(ddraw,"(%p)->GetCaps(%p,%p)\n",this,caps1,caps2);
2748 caps1->dwVidMemTotal = this->e.dga.fb_memsize;
2749 caps1->dwCaps = 0xffffffff&~(DDCAPS_BANKSWITCHED); /* we can do anything */
2750 caps1->ddsCaps.dwCaps = 0xffffffff; /* we can do anything */
2752 caps2->dwVidMemTotal = this->e.dga.fb_memsize;
2753 caps2->dwCaps = 0xffffffff&~(DDCAPS_BANKSWITCHED); /* we can do anything */
2754 caps2->ddsCaps.dwCaps = 0xffffffff; /* we can do anything */
2757 #else /* defined(HAVE_LIBXXF86DGA) */
2758 return E_UNEXPECTED;
2759 #endif /* defined(HAVE_LIBXXF86DGA) */
2762 static void fill_caps(LPDDCAPS caps) {
2763 /* This function tries to fill the capabilities of Wine's DDraw implementation.
2764 Need to be fixed, though.. */
2768 caps->dwSize = sizeof(*caps);
2769 caps->dwCaps = DDCAPS_3D | DDCAPS_ALPHA | DDCAPS_BLT | DDCAPS_BLTSTRETCH | DDCAPS_BLTCOLORFILL | DDCAPS_BLTDEPTHFILL |
2770 DDCAPS_CANBLTSYSMEM | DDCAPS_COLORKEY | DDCAPS_PALETTE | DDCAPS_ZBLTS;
2771 caps->dwCaps2 = DDCAPS2_CERTIFIED | DDCAPS2_NO2DDURING3DSCENE | DDCAPS2_NOPAGELOCKREQUIRED |
2772 DDCAPS2_WIDESURFACES;
2773 caps->dwCKeyCaps = 0xFFFFFFFF; /* Should put real caps here one day... */
2775 caps->dwFXAlphaCaps = 0;
2776 caps->dwPalCaps = DDPCAPS_8BIT | DDPCAPS_ALLOW256;
2778 caps->dwZBufferBitDepths = DDBD_16;
2779 /* I put here 8 Mo so that D3D applications will believe they have enough memory
2780 to put textures in video memory.
2781 BTW, is this only frame buffer memory or also texture memory (for Voodoo boards
2783 caps->dwVidMemTotal = 8192 * 1024;
2784 caps->dwVidMemFree = 8192 * 1024;
2785 /* These are all the supported capabilities of the surfaces */
2786 caps->ddsCaps.dwCaps = DDSCAPS_3DDEVICE | DDSCAPS_ALPHA | DDSCAPS_BACKBUFFER | DDSCAPS_COMPLEX | DDSCAPS_FLIP |
2787 DDSCAPS_FRONTBUFFER | DDSCAPS_LOCALVIDMEM | DDSCAPS_MIPMAP | DDSCAPS_NONLOCALVIDMEM | DDSCAPS_OFFSCREENPLAIN |
2788 DDSCAPS_OVERLAY | DDSCAPS_PALETTE | DDSCAPS_PRIMARYSURFACE | DDSCAPS_SYSTEMMEMORY | DDSCAPS_TEXTURE |
2789 DDSCAPS_VIDEOMEMORY | DDSCAPS_VISIBLE | DDSCAPS_ZBUFFER;
2792 static HRESULT WINAPI Xlib_IDirectDraw2_GetCaps(
2793 LPDIRECTDRAW2 this,LPDDCAPS caps1,LPDDCAPS caps2
2795 TRACE(ddraw,"(%p)->GetCaps(%p,%p)\n",this,caps1,caps2);
2797 /* Put the same caps for the two capabilities */
2804 static HRESULT WINAPI IDirectDraw2_CreateClipper(
2805 LPDIRECTDRAW2 this,DWORD x,LPDIRECTDRAWCLIPPER *lpddclip,LPUNKNOWN lpunk
2807 FIXME(ddraw,"(%p)->(%08lx,%p,%p),stub!\n",
2808 this,x,lpddclip,lpunk
2810 *lpddclip = (LPDIRECTDRAWCLIPPER)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,sizeof(IDirectDrawClipper));
2811 (*lpddclip)->ref = 1;
2812 (*lpddclip)->lpvtbl = &ddclipvt;
2816 static HRESULT WINAPI common_IDirectDraw2_CreatePalette(
2817 LPDIRECTDRAW2 this,DWORD dwFlags,LPPALETTEENTRY palent,LPDIRECTDRAWPALETTE *lpddpal,LPUNKNOWN lpunk,int *psize
2821 if (TRACE_ON(ddraw))
2822 _dump_paletteformat(dwFlags);
2824 *lpddpal = (LPDIRECTDRAWPALETTE)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,sizeof(IDirectDrawPalette));
2825 if (*lpddpal == NULL) return E_OUTOFMEMORY;
2826 (*lpddpal)->ref = 1;
2827 (*lpddpal)->ddraw = (LPDIRECTDRAW)this;
2828 (*lpddpal)->installed = 0;
2830 if (dwFlags & DDPCAPS_1BIT)
2832 else if (dwFlags & DDPCAPS_2BIT)
2834 else if (dwFlags & DDPCAPS_4BIT)
2836 else if (dwFlags & DDPCAPS_8BIT)
2839 ERR(ddraw, "unhandled palette format\n");
2844 /* Now, if we are in 'depth conversion mode', create the screen palette */
2845 if (this->d.depth != this->d.screen_depth) {
2848 switch (this->d.screen_depth) {
2850 unsigned short *screen_palette = (unsigned short *) (*lpddpal)->screen_palents;
2852 for (i = 0; i < size; i++) {
2853 screen_palette[i] = (((((unsigned short) palent[i].peRed) & 0xF8) << 8) |
2854 ((((unsigned short) palent[i].peBlue) & 0xF8) >> 3) |
2855 ((((unsigned short) palent[i].peGreen) & 0xFC) << 3));
2860 ERR(ddraw, "Memory corruption ! (depth=%ld, screen_depth=%ld)\n",this->d.depth,this->d.screen_depth);
2865 memcpy((*lpddpal)->palents, palent, size * sizeof(PALETTEENTRY));
2866 } else if (this->d.depth != this->d.screen_depth) {
2869 switch (this->d.screen_depth) {
2871 unsigned short *screen_palette = (unsigned short *) (*lpddpal)->screen_palents;
2873 for (i = 0; i < size; i++) {
2874 screen_palette[i] = 0xFFFF;
2879 ERR(ddraw, "Memory corruption !\n");
2887 static HRESULT WINAPI DGA_IDirectDraw2_CreatePalette(
2888 LPDIRECTDRAW2 this,DWORD dwFlags,LPPALETTEENTRY palent,LPDIRECTDRAWPALETTE *lpddpal,LPUNKNOWN lpunk
2893 TRACE(ddraw,"(%p)->(%08lx,%p,%p,%p)\n",this,dwFlags,palent,lpddpal,lpunk);
2894 res = common_IDirectDraw2_CreatePalette(this,dwFlags,palent,lpddpal,lpunk,&xsize);
2895 if (res != 0) return res;
2896 (*lpddpal)->lpvtbl = &dga_ddpalvt;
2897 if (this->d.depth<=8) {
2898 (*lpddpal)->cm = TSXCreateColormap(display,DefaultRootWindow(display),DefaultVisualOfScreen(X11DRV_GetXScreen()),AllocAll);
2900 FIXME(ddraw,"why are we doing CreatePalette in hi/truecolor?\n");
2903 if (((*lpddpal)->cm)&&xsize) {
2904 for (i=0;i<xsize;i++) {
2907 xc.red = (*lpddpal)->palents[i].peRed<<8;
2908 xc.blue = (*lpddpal)->palents[i].peBlue<<8;
2909 xc.green = (*lpddpal)->palents[i].peGreen<<8;
2910 xc.flags = DoRed|DoBlue|DoGreen;
2912 TSXStoreColor(display,(*lpddpal)->cm,&xc);
2918 static HRESULT WINAPI Xlib_IDirectDraw2_CreatePalette(
2919 LPDIRECTDRAW2 this,DWORD dwFlags,LPPALETTEENTRY palent,LPDIRECTDRAWPALETTE *lpddpal,LPUNKNOWN lpunk
2924 TRACE(ddraw,"(%p)->(%08lx,%p,%p,%p)\n",this,dwFlags,palent,lpddpal,lpunk);
2925 res = common_IDirectDraw2_CreatePalette(this,dwFlags,palent,lpddpal,lpunk,&xsize);
2926 if (res != 0) return res;
2927 (*lpddpal)->lpvtbl = &xlib_ddpalvt;
2931 static HRESULT WINAPI DGA_IDirectDraw2_RestoreDisplayMode(LPDIRECTDRAW2 this) {
2932 #ifdef HAVE_LIBXXF86DGA
2933 TRACE(ddraw, "(%p)->()\n",this);
2935 TSXF86DGADirectVideo(display,DefaultScreen(display),0);
2936 #ifdef RESTORE_SIGNALS
2937 if (SIGNAL_Reinit) SIGNAL_Reinit();
2940 #else /* defined(HAVE_LIBXXF86DGA) */
2941 return E_UNEXPECTED;
2945 static HRESULT WINAPI Xlib_IDirectDraw2_RestoreDisplayMode(LPDIRECTDRAW2 this) {
2946 TRACE(ddraw, "(%p)->RestoreDisplayMode()\n", this);
2951 static HRESULT WINAPI IDirectDraw2_WaitForVerticalBlank(
2952 LPDIRECTDRAW2 this,DWORD x,HANDLE32 h
2954 TRACE(ddraw,"(%p)->(0x%08lx,0x%08x)\n",this,x,h);
2958 static ULONG WINAPI IDirectDraw2_AddRef(LPDIRECTDRAW2 this) {
2959 TRACE( ddraw, "(%p)->() incrementing from %lu.\n", this, this->ref );
2961 return ++(this->ref);
2964 static ULONG WINAPI DGA_IDirectDraw2_Release(LPDIRECTDRAW2 this) {
2965 TRACE( ddraw, "(%p)->() decrementing from %lu.\n", this, this->ref );
2967 #ifdef HAVE_LIBXXF86DGA
2968 if (!--(this->ref)) {
2969 TSXF86DGADirectVideo(display,DefaultScreen(display),0);
2971 #ifdef HAVE_LIBXXF86VM
2973 TSXF86VidModeSwitchToMode(
2975 DefaultScreen(display),
2977 if (orig_mode->privsize)
2978 TSXFree(orig_mode->private);
2984 #ifdef RESTORE_SIGNALS
2985 if (SIGNAL_Reinit) SIGNAL_Reinit();
2987 HeapFree(GetProcessHeap(),0,this);
2990 #endif /* defined(HAVE_LIBXXF86DGA) */
2994 static ULONG WINAPI Xlib_IDirectDraw2_Release(LPDIRECTDRAW2 this) {
2995 TRACE( ddraw, "(%p)->() decrementing from %lu.\n", this, this->ref );
2997 if (!--(this->ref)) {
2998 HeapFree(GetProcessHeap(),0,this);
3001 /* FIXME: destroy window ... */
3005 static HRESULT WINAPI DGA_IDirectDraw2_QueryInterface(
3006 LPDIRECTDRAW2 this,REFIID refiid,LPVOID *obj
3010 WINE_StringFromCLSID((LPCLSID)refiid,xrefiid);
3011 TRACE(ddraw,"(%p)->(%s,%p)\n",this,xrefiid,obj);
3012 if (!memcmp(&IID_IUnknown,refiid,sizeof(IID_IUnknown))) {
3014 this->lpvtbl->fnAddRef(this);
3016 TRACE(ddraw, " Creating IUnknown interface (%p)\n", *obj);
3020 if (!memcmp(&IID_IDirectDraw,refiid,sizeof(IID_IDirectDraw))) {
3021 this->lpvtbl = (LPDIRECTDRAW2_VTABLE)&dga_ddvt;
3022 this->lpvtbl->fnAddRef(this);
3025 TRACE(ddraw, " Creating IDirectDraw interface (%p)\n", *obj);
3029 if (!memcmp(&IID_IDirectDraw2,refiid,sizeof(IID_IDirectDraw2))) {
3030 this->lpvtbl = (LPDIRECTDRAW2_VTABLE)&dga_dd2vt;
3031 this->lpvtbl->fnAddRef(this);
3034 TRACE(ddraw, " Creating IDirectDraw2 interface (%p)\n", *obj);
3038 if (!memcmp(&IID_IDirectDraw4,refiid,sizeof(IID_IDirectDraw4))) {
3039 this->lpvtbl = (LPDIRECTDRAW2_VTABLE)&dga_dd4vt;
3040 this->lpvtbl->fnAddRef(this);
3043 TRACE(ddraw, " Creating IDirectDraw4 interface (%p)\n", *obj);
3047 if (!memcmp(&IID_IDirect3D,refiid,sizeof(IID_IDirect3D))) {
3050 d3d = HeapAlloc(GetProcessHeap(),0,sizeof(*d3d));
3052 d3d->ddraw = (LPDIRECTDRAW)this;
3053 this->lpvtbl->fnAddRef(this);
3054 d3d->lpvtbl = &d3dvt;
3057 TRACE(ddraw, " Creating IDirect3D interface (%p)\n", *obj);
3061 if (!memcmp(&IID_IDirect3D2,refiid,sizeof(IID_IDirect3D2))) {
3064 d3d = HeapAlloc(GetProcessHeap(),0,sizeof(*d3d));
3066 d3d->ddraw = (LPDIRECTDRAW)this;
3067 this->lpvtbl->fnAddRef(this);
3068 d3d->lpvtbl = &d3d2vt;
3071 TRACE(ddraw, " Creating IDirect3D2 interface (%p)\n", *obj);
3075 WARN(ddraw,"(%p):interface for IID %s _NOT_ found!\n",this,xrefiid);
3076 return OLE_E_ENUM_NOMORE;
3079 static HRESULT WINAPI Xlib_IDirectDraw2_QueryInterface(
3080 LPDIRECTDRAW2 this,REFIID refiid,LPVOID *obj
3084 WINE_StringFromCLSID((LPCLSID)refiid,xrefiid);
3085 TRACE(ddraw,"(%p)->(%s,%p)\n",this,xrefiid,obj);
3086 if (!memcmp(&IID_IUnknown,refiid,sizeof(IID_IUnknown))) {
3088 this->lpvtbl->fnAddRef(this);
3090 TRACE(ddraw, " Creating IUnknown interface (%p)\n", *obj);
3094 if (!memcmp(&IID_IDirectDraw,refiid,sizeof(IID_IDirectDraw))) {
3095 this->lpvtbl = (LPDIRECTDRAW2_VTABLE)&xlib_ddvt;
3096 this->lpvtbl->fnAddRef(this);
3099 TRACE(ddraw, " Creating IDirectDraw interface (%p)\n", *obj);
3103 if (!memcmp(&IID_IDirectDraw2,refiid,sizeof(IID_IDirectDraw2))) {
3104 this->lpvtbl = (LPDIRECTDRAW2_VTABLE)&xlib_dd2vt;
3105 this->lpvtbl->fnAddRef(this);
3108 TRACE(ddraw, " Creating IDirectDraw2 interface (%p)\n", *obj);
3112 if (!memcmp(&IID_IDirectDraw4,refiid,sizeof(IID_IDirectDraw4))) {
3113 this->lpvtbl = (LPDIRECTDRAW2_VTABLE)&xlib_dd4vt;
3114 this->lpvtbl->fnAddRef(this);
3117 TRACE(ddraw, " Creating IDirectDraw4 interface (%p)\n", *obj);
3121 if (!memcmp(&IID_IDirect3D,refiid,sizeof(IID_IDirect3D))) {
3124 d3d = HeapAlloc(GetProcessHeap(),0,sizeof(*d3d));
3126 d3d->ddraw = (LPDIRECTDRAW)this;
3127 this->lpvtbl->fnAddRef(this);
3128 d3d->lpvtbl = &d3dvt;
3131 TRACE(ddraw, " Creating IDirect3D interface (%p)\n", *obj);
3135 if (!memcmp(&IID_IDirect3D2,refiid,sizeof(IID_IDirect3D))) {
3138 d3d = HeapAlloc(GetProcessHeap(),0,sizeof(*d3d));
3140 d3d->ddraw = (LPDIRECTDRAW)this;
3141 this->lpvtbl->fnAddRef(this);
3142 d3d->lpvtbl = &d3d2vt;
3145 TRACE(ddraw, " Creating IDirect3D2 interface (%p)\n", *obj);
3149 WARN(ddraw,"(%p):interface for IID %s _NOT_ found!\n",this,xrefiid);
3150 return OLE_E_ENUM_NOMORE;
3153 static HRESULT WINAPI IDirectDraw2_GetVerticalBlankStatus(
3154 LPDIRECTDRAW2 this,BOOL32 *status
3156 TRACE(ddraw,"(%p)->(%p)\n",this,status);
3161 static HRESULT WINAPI IDirectDraw2_EnumDisplayModes(
3162 LPDIRECTDRAW2 this,DWORD dwFlags,LPDDSURFACEDESC lpddsfd,LPVOID context,LPDDENUMMODESCALLBACK modescb
3164 DDSURFACEDESC ddsfd;
3167 } modes[5] = { /* some of the usual modes */
3174 static int depths[4] = {8,16,24,32};
3177 TRACE(ddraw,"(%p)->(0x%08lx,%p,%p,%p)\n",this,dwFlags,lpddsfd,context,modescb);
3178 ddsfd.dwSize = sizeof(ddsfd);
3179 ddsfd.dwFlags = DDSD_HEIGHT|DDSD_WIDTH|DDSD_BACKBUFFERCOUNT|DDSD_PIXELFORMAT|DDSD_CAPS;
3180 if (dwFlags & DDEDM_REFRESHRATES) {
3181 ddsfd.dwFlags |= DDSD_REFRESHRATE;
3182 ddsfd.x.dwRefreshRate = 60;
3185 for (i=0;i<sizeof(depths)/sizeof(depths[0]);i++) {
3186 ddsfd.dwBackBufferCount = 1;
3187 ddsfd.ddpfPixelFormat.dwFourCC = 0;
3188 ddsfd.ddpfPixelFormat.dwFlags = DDPF_RGB;
3189 ddsfd.ddpfPixelFormat.x.dwRGBBitCount = depths[i];
3190 /* FIXME: those masks would have to be set in depth > 8 */
3192 ddsfd.ddpfPixelFormat.y.dwRBitMask = 0;
3193 ddsfd.ddpfPixelFormat.z.dwGBitMask = 0;
3194 ddsfd.ddpfPixelFormat.xx.dwBBitMask = 0;
3195 ddsfd.ddpfPixelFormat.xy.dwRGBAlphaBitMask= 0;
3196 ddsfd.ddsCaps.dwCaps=DDSCAPS_PALETTE;
3197 ddsfd.ddpfPixelFormat.dwFlags|=DDPF_PALETTEINDEXED8;
3199 ddsfd.ddpfPixelFormat.xy.dwRGBAlphaBitMask= 0;
3201 /* FIXME: We should query those from X itself */
3202 switch (depths[i]) {
3204 ddsfd.ddpfPixelFormat.y.dwRBitMask = 0xF800;
3205 ddsfd.ddpfPixelFormat.z.dwGBitMask = 0x07E0;
3206 ddsfd.ddpfPixelFormat.xx.dwBBitMask= 0x001F;
3209 ddsfd.ddpfPixelFormat.y.dwRBitMask = 0x00FF0000;
3210 ddsfd.ddpfPixelFormat.z.dwGBitMask = 0x0000FF00;
3211 ddsfd.ddpfPixelFormat.xx.dwBBitMask= 0x000000FF;
3214 ddsfd.ddpfPixelFormat.y.dwRBitMask = 0x00FF0000;
3215 ddsfd.ddpfPixelFormat.z.dwGBitMask = 0x0000FF00;
3216 ddsfd.ddpfPixelFormat.xx.dwBBitMask= 0x000000FF;
3221 ddsfd.dwWidth = MONITOR_GetWidth(&MONITOR_PrimaryMonitor);
3222 ddsfd.dwHeight = MONITOR_GetHeight(&MONITOR_PrimaryMonitor);
3223 TRACE(ddraw," enumerating (%ldx%ldx%d)\n",ddsfd.dwWidth,ddsfd.dwHeight,depths[i]);
3224 if (!modescb(&ddsfd,context)) return DD_OK;
3226 for (j=0;j<sizeof(modes)/sizeof(modes[0]);j++) {
3227 ddsfd.dwWidth = modes[j].w;
3228 ddsfd.dwHeight = modes[j].h;
3229 TRACE(ddraw," enumerating (%ldx%ldx%d)\n",ddsfd.dwWidth,ddsfd.dwHeight,depths[i]);
3230 if (!modescb(&ddsfd,context)) return DD_OK;
3233 if (!(dwFlags & DDEDM_STANDARDVGAMODES)) {
3234 /* modeX is not standard VGA */
3236 ddsfd.dwHeight = 200;
3237 ddsfd.dwWidth = 320;
3238 TRACE(ddraw," enumerating (320x200x%d)\n",depths[i]);
3239 if (!modescb(&ddsfd,context)) return DD_OK;
3245 static HRESULT WINAPI DGA_IDirectDraw2_GetDisplayMode(
3246 LPDIRECTDRAW2 this,LPDDSURFACEDESC lpddsfd
3248 #ifdef HAVE_LIBXXF86DGA
3249 TRACE(ddraw,"(%p)->(%p)\n",this,lpddsfd);
3250 lpddsfd->dwFlags = DDSD_HEIGHT|DDSD_WIDTH|DDSD_PITCH|DDSD_BACKBUFFERCOUNT|DDSD_PIXELFORMAT|DDSD_CAPS;
3251 lpddsfd->dwHeight = MONITOR_GetHeight(&MONITOR_PrimaryMonitor);
3252 lpddsfd->dwWidth = MONITOR_GetWidth(&MONITOR_PrimaryMonitor);
3253 lpddsfd->lPitch = this->e.dga.fb_width*this->d.depth/8;
3254 lpddsfd->dwBackBufferCount = 1;
3255 lpddsfd->x.dwRefreshRate = 60;
3256 lpddsfd->ddsCaps.dwCaps = DDSCAPS_PALETTE;
3257 _getpixelformat(this,&(lpddsfd->ddpfPixelFormat));
3259 #else /* defined(HAVE_LIBXXF86DGA) */
3260 return E_UNEXPECTED;
3261 #endif /* defined(HAVE_LIBXXF86DGA) */
3264 static HRESULT WINAPI Xlib_IDirectDraw2_GetDisplayMode(
3265 LPDIRECTDRAW2 this,LPDDSURFACEDESC lpddsfd
3267 TRACE(ddraw,"(%p)->GetDisplayMode(%p)\n",this,lpddsfd);
3268 lpddsfd->dwFlags = DDSD_HEIGHT|DDSD_WIDTH|DDSD_PITCH|DDSD_BACKBUFFERCOUNT|DDSD_PIXELFORMAT|DDSD_CAPS;
3269 lpddsfd->dwHeight = MONITOR_GetHeight(&MONITOR_PrimaryMonitor);
3270 lpddsfd->dwWidth = MONITOR_GetWidth(&MONITOR_PrimaryMonitor);
3271 /* POOLE FIXME: Xlib */
3272 lpddsfd->lPitch = this->e.dga.fb_width*this->d.depth/8;
3273 /* END FIXME: Xlib */
3274 lpddsfd->dwBackBufferCount = 1;
3275 lpddsfd->x.dwRefreshRate = 60;
3276 lpddsfd->ddsCaps.dwCaps = DDSCAPS_PALETTE;
3277 _getpixelformat(this,&(lpddsfd->ddpfPixelFormat));
3281 static HRESULT WINAPI IDirectDraw2_FlipToGDISurface(LPDIRECTDRAW2 this) {
3282 TRACE(ddraw,"(%p)->()\n",this);
3286 static HRESULT WINAPI IDirectDraw2_GetMonitorFrequency(
3287 LPDIRECTDRAW2 this,LPDWORD freq
3289 FIXME(ddraw,"(%p)->(%p) returns 60 Hz always\n",this,freq);
3290 *freq = 60*100; /* 60 Hz */
3294 /* what can we directly decompress? */
3295 static HRESULT WINAPI IDirectDraw2_GetFourCCCodes(
3296 LPDIRECTDRAW2 this,LPDWORD x,LPDWORD y
3298 FIXME(ddraw,"(%p,%p,%p), stub\n",this,x,y);
3302 static HRESULT WINAPI IDirectDraw2_EnumSurfaces(
3303 LPDIRECTDRAW2 this,DWORD x,LPDDSURFACEDESC ddsfd,LPVOID context,LPDDENUMSURFACESCALLBACK ddsfcb
3305 FIXME(ddraw,"(%p)->(0x%08lx,%p,%p,%p),stub!\n",this,x,ddsfd,context,ddsfcb);
3309 static HRESULT WINAPI IDirectDraw2_Compact(
3310 LPDIRECTDRAW2 this )
3312 FIXME(ddraw,"(%p)->()\n", this );
3317 static HRESULT WINAPI IDirectDraw2_GetGDISurface(LPDIRECTDRAW2 this,
3318 LPDIRECTDRAWSURFACE *lplpGDIDDSSurface) {
3319 FIXME(ddraw,"(%p)->(%p)\n", this, lplpGDIDDSSurface);
3324 static HRESULT WINAPI IDirectDraw2_GetScanLine(LPDIRECTDRAW2 this,
3325 LPDWORD lpdwScanLine) {
3326 FIXME(ddraw,"(%p)->(%p)\n", this, lpdwScanLine);
3331 static HRESULT WINAPI IDirectDraw2_Initialize(LPDIRECTDRAW2 this,
3333 FIXME(ddraw,"(%p)->(%p)\n", this, lpGUID);
3338 /* Note: Hack so we can reuse the old functions without compiler warnings */
3340 # define XCAST(fun) (typeof(dga_ddvt.fn##fun))
3342 # define XCAST(fun) (void*)
3345 static struct IDirectDraw_VTable dga_ddvt = {
3346 XCAST(QueryInterface)DGA_IDirectDraw2_QueryInterface,
3347 XCAST(AddRef)IDirectDraw2_AddRef,
3348 XCAST(Release)DGA_IDirectDraw2_Release,
3349 XCAST(Compact)IDirectDraw2_Compact,
3350 XCAST(CreateClipper)IDirectDraw2_CreateClipper,
3351 XCAST(CreatePalette)DGA_IDirectDraw2_CreatePalette,
3352 XCAST(CreateSurface)DGA_IDirectDraw2_CreateSurface,
3353 XCAST(DuplicateSurface)IDirectDraw2_DuplicateSurface,
3354 XCAST(EnumDisplayModes)IDirectDraw2_EnumDisplayModes,
3355 XCAST(EnumSurfaces)IDirectDraw2_EnumSurfaces,
3356 XCAST(FlipToGDISurface)IDirectDraw2_FlipToGDISurface,
3357 XCAST(GetCaps)DGA_IDirectDraw2_GetCaps,
3358 XCAST(GetDisplayMode)DGA_IDirectDraw2_GetDisplayMode,
3359 XCAST(GetFourCCCodes)IDirectDraw2_GetFourCCCodes,
3360 XCAST(GetGDISurface)IDirectDraw2_GetGDISurface,
3361 XCAST(GetMonitorFrequency)IDirectDraw2_GetMonitorFrequency,
3362 XCAST(GetScanLine)IDirectDraw2_GetScanLine,
3363 XCAST(GetVerticalBlankStatus)IDirectDraw2_GetVerticalBlankStatus,
3364 XCAST(Initialize)IDirectDraw2_Initialize,
3365 XCAST(RestoreDisplayMode)DGA_IDirectDraw2_RestoreDisplayMode,
3366 XCAST(SetCooperativeLevel)IDirectDraw2_SetCooperativeLevel,
3367 DGA_IDirectDraw_SetDisplayMode,
3368 XCAST(WaitForVerticalBlank)IDirectDraw2_WaitForVerticalBlank,
3371 static struct IDirectDraw_VTable xlib_ddvt = {
3372 XCAST(QueryInterface)Xlib_IDirectDraw2_QueryInterface,
3373 XCAST(AddRef)IDirectDraw2_AddRef,
3374 XCAST(Release)Xlib_IDirectDraw2_Release,
3375 XCAST(Compact)IDirectDraw2_Compact,
3376 XCAST(CreateClipper)IDirectDraw2_CreateClipper,
3377 XCAST(CreatePalette)Xlib_IDirectDraw2_CreatePalette,
3378 XCAST(CreateSurface)Xlib_IDirectDraw2_CreateSurface,
3379 XCAST(DuplicateSurface)IDirectDraw2_DuplicateSurface,
3380 XCAST(EnumDisplayModes)IDirectDraw2_EnumDisplayModes,
3381 XCAST(EnumSurfaces)IDirectDraw2_EnumSurfaces,
3382 XCAST(FlipToGDISurface)IDirectDraw2_FlipToGDISurface,
3383 XCAST(GetCaps)Xlib_IDirectDraw2_GetCaps,
3384 XCAST(GetDisplayMode)Xlib_IDirectDraw2_GetDisplayMode,
3385 XCAST(GetFourCCCodes)IDirectDraw2_GetFourCCCodes,
3386 XCAST(GetGDISurface)IDirectDraw2_GetGDISurface,
3387 XCAST(GetMonitorFrequency)IDirectDraw2_GetMonitorFrequency,
3388 XCAST(GetScanLine)IDirectDraw2_GetScanLine,
3389 XCAST(GetVerticalBlankStatus)IDirectDraw2_GetVerticalBlankStatus,
3390 XCAST(Initialize)IDirectDraw2_Initialize,
3391 XCAST(RestoreDisplayMode)Xlib_IDirectDraw2_RestoreDisplayMode,
3392 XCAST(SetCooperativeLevel)IDirectDraw2_SetCooperativeLevel,
3393 Xlib_IDirectDraw_SetDisplayMode,
3394 XCAST(WaitForVerticalBlank)IDirectDraw2_WaitForVerticalBlank,
3399 /*****************************************************************************
3405 static HRESULT WINAPI DGA_IDirectDraw2_SetDisplayMode(
3406 LPDIRECTDRAW2 this,DWORD width,DWORD height,DWORD depth,DWORD xx,DWORD yy
3408 return DGA_IDirectDraw_SetDisplayMode((LPDIRECTDRAW)this,width,height,depth);
3411 static HRESULT WINAPI Xlib_IDirectDraw2_SetDisplayMode(
3412 LPDIRECTDRAW2 this,DWORD width,DWORD height,DWORD depth,DWORD xx,DWORD yy
3414 return Xlib_IDirectDraw_SetDisplayMode((LPDIRECTDRAW)this,width,height,depth);
3417 static HRESULT WINAPI DGA_IDirectDraw2_GetAvailableVidMem(
3418 LPDIRECTDRAW2 this,LPDDSCAPS ddscaps,LPDWORD total,LPDWORD free
3420 TRACE(ddraw,"(%p)->(%p,%p,%p)\n",
3421 this,ddscaps,total,free
3423 if (total) *total = this->e.dga.fb_memsize * 1024;
3424 if (free) *free = this->e.dga.fb_memsize * 1024;
3428 static HRESULT WINAPI Xlib_IDirectDraw2_GetAvailableVidMem(
3429 LPDIRECTDRAW2 this,LPDDSCAPS ddscaps,LPDWORD total,LPDWORD free
3431 TRACE(ddraw,"(%p)->(%p,%p,%p)\n",
3432 this,ddscaps,total,free
3434 if (total) *total = 2048 * 1024;
3435 if (free) *free = 2048 * 1024;
3439 static IDirectDraw2_VTable dga_dd2vt = {
3440 DGA_IDirectDraw2_QueryInterface,
3441 IDirectDraw2_AddRef,
3442 DGA_IDirectDraw2_Release,
3443 IDirectDraw2_Compact,
3444 IDirectDraw2_CreateClipper,
3445 DGA_IDirectDraw2_CreatePalette,
3446 DGA_IDirectDraw2_CreateSurface,
3447 IDirectDraw2_DuplicateSurface,
3448 IDirectDraw2_EnumDisplayModes,
3449 IDirectDraw2_EnumSurfaces,
3450 IDirectDraw2_FlipToGDISurface,
3451 DGA_IDirectDraw2_GetCaps,
3452 DGA_IDirectDraw2_GetDisplayMode,
3453 IDirectDraw2_GetFourCCCodes,
3454 IDirectDraw2_GetGDISurface,
3455 IDirectDraw2_GetMonitorFrequency,
3456 IDirectDraw2_GetScanLine,
3457 IDirectDraw2_GetVerticalBlankStatus,
3458 IDirectDraw2_Initialize,
3459 DGA_IDirectDraw2_RestoreDisplayMode,
3460 IDirectDraw2_SetCooperativeLevel,
3461 DGA_IDirectDraw2_SetDisplayMode,
3462 IDirectDraw2_WaitForVerticalBlank,
3463 DGA_IDirectDraw2_GetAvailableVidMem
3466 static struct IDirectDraw2_VTable xlib_dd2vt = {
3467 Xlib_IDirectDraw2_QueryInterface,
3468 IDirectDraw2_AddRef,
3469 Xlib_IDirectDraw2_Release,
3470 IDirectDraw2_Compact,
3471 IDirectDraw2_CreateClipper,
3472 Xlib_IDirectDraw2_CreatePalette,
3473 Xlib_IDirectDraw2_CreateSurface,
3474 IDirectDraw2_DuplicateSurface,
3475 IDirectDraw2_EnumDisplayModes,
3476 IDirectDraw2_EnumSurfaces,
3477 IDirectDraw2_FlipToGDISurface,
3478 Xlib_IDirectDraw2_GetCaps,
3479 Xlib_IDirectDraw2_GetDisplayMode,
3480 IDirectDraw2_GetFourCCCodes,
3481 IDirectDraw2_GetGDISurface,
3482 IDirectDraw2_GetMonitorFrequency,
3483 IDirectDraw2_GetScanLine,
3484 IDirectDraw2_GetVerticalBlankStatus,
3485 IDirectDraw2_Initialize,
3486 Xlib_IDirectDraw2_RestoreDisplayMode,
3487 IDirectDraw2_SetCooperativeLevel,
3488 Xlib_IDirectDraw2_SetDisplayMode,
3489 IDirectDraw2_WaitForVerticalBlank,
3490 Xlib_IDirectDraw2_GetAvailableVidMem
3493 /*****************************************************************************
3498 static HRESULT WINAPI IDirectDraw4_GetSurfaceFromDC(LPDIRECTDRAW4 this,
3500 LPDIRECTDRAWSURFACE *lpDDS) {
3501 FIXME(ddraw, "(%p)->(%08ld,%p)\n", this, (DWORD) hdc, lpDDS);
3506 static HRESULT WINAPI IDirectDraw4_RestoreAllSurfaces(LPDIRECTDRAW4 this) {
3507 FIXME(ddraw, "(%p)->()\n", this);
3512 static HRESULT WINAPI IDirectDraw4_TestCooperativeLevel(LPDIRECTDRAW4 this) {
3513 FIXME(ddraw, "(%p)->()\n", this);
3518 static HRESULT WINAPI IDirectDraw4_GetDeviceIdentifier(LPDIRECTDRAW4 this,
3519 LPDDDEVICEIDENTIFIER lpdddi,
3521 FIXME(ddraw, "(%p)->(%p,%08lx)\n", this, lpdddi, dwFlags);
3527 # define XCAST(fun) (typeof(dga_dd4vt.fn##fun))
3529 # define XCAST(fun) (void*)
3533 static struct IDirectDraw4_VTable dga_dd4vt = {
3534 XCAST(QueryInterface)DGA_IDirectDraw2_QueryInterface,
3535 XCAST(AddRef)IDirectDraw2_AddRef,
3536 XCAST(Release)DGA_IDirectDraw2_Release,
3537 XCAST(Compact)IDirectDraw2_Compact,
3538 XCAST(CreateClipper)IDirectDraw2_CreateClipper,
3539 XCAST(CreatePalette)DGA_IDirectDraw2_CreatePalette,
3540 XCAST(CreateSurface)DGA_IDirectDraw2_CreateSurface,
3541 XCAST(DuplicateSurface)IDirectDraw2_DuplicateSurface,
3542 XCAST(EnumDisplayModes)IDirectDraw2_EnumDisplayModes,
3543 XCAST(EnumSurfaces)IDirectDraw2_EnumSurfaces,
3544 XCAST(FlipToGDISurface)IDirectDraw2_FlipToGDISurface,
3545 XCAST(GetCaps)DGA_IDirectDraw2_GetCaps,
3546 XCAST(GetDisplayMode)DGA_IDirectDraw2_GetDisplayMode,
3547 XCAST(GetFourCCCodes)IDirectDraw2_GetFourCCCodes,
3548 XCAST(GetGDISurface)IDirectDraw2_GetGDISurface,
3549 XCAST(GetMonitorFrequency)IDirectDraw2_GetMonitorFrequency,
3550 XCAST(GetScanLine)IDirectDraw2_GetScanLine,
3551 XCAST(GetVerticalBlankStatus)IDirectDraw2_GetVerticalBlankStatus,
3552 XCAST(Initialize)IDirectDraw2_Initialize,
3553 XCAST(RestoreDisplayMode)DGA_IDirectDraw2_RestoreDisplayMode,
3554 XCAST(SetCooperativeLevel)IDirectDraw2_SetCooperativeLevel,
3555 XCAST(SetDisplayMode)DGA_IDirectDraw_SetDisplayMode,
3556 XCAST(WaitForVerticalBlank)IDirectDraw2_WaitForVerticalBlank,
3557 XCAST(GetAvailableVidMem)DGA_IDirectDraw2_GetAvailableVidMem,
3558 IDirectDraw4_GetSurfaceFromDC,
3559 IDirectDraw4_RestoreAllSurfaces,
3560 IDirectDraw4_TestCooperativeLevel,
3561 IDirectDraw4_GetDeviceIdentifier
3564 static struct IDirectDraw4_VTable xlib_dd4vt = {
3565 XCAST(QueryInterface)Xlib_IDirectDraw2_QueryInterface,
3566 XCAST(AddRef)IDirectDraw2_AddRef,
3567 XCAST(Release)Xlib_IDirectDraw2_Release,
3568 XCAST(Compact)IDirectDraw2_Compact,
3569 XCAST(CreateClipper)IDirectDraw2_CreateClipper,
3570 XCAST(CreatePalette)Xlib_IDirectDraw2_CreatePalette,
3571 XCAST(CreateSurface)Xlib_IDirectDraw2_CreateSurface,
3572 XCAST(DuplicateSurface)IDirectDraw2_DuplicateSurface,
3573 XCAST(EnumDisplayModes)IDirectDraw2_EnumDisplayModes,
3574 XCAST(EnumSurfaces)IDirectDraw2_EnumSurfaces,
3575 XCAST(FlipToGDISurface)IDirectDraw2_FlipToGDISurface,
3576 XCAST(GetCaps)Xlib_IDirectDraw2_GetCaps,
3577 XCAST(GetDisplayMode)Xlib_IDirectDraw2_GetDisplayMode,
3578 XCAST(GetFourCCCodes)IDirectDraw2_GetFourCCCodes,
3579 XCAST(GetGDISurface)IDirectDraw2_GetGDISurface,
3580 XCAST(GetMonitorFrequency)IDirectDraw2_GetMonitorFrequency,
3581 XCAST(GetScanLine)IDirectDraw2_GetScanLine,
3582 XCAST(GetVerticalBlankStatus)IDirectDraw2_GetVerticalBlankStatus,
3583 XCAST(Initialize)IDirectDraw2_Initialize,
3584 XCAST(RestoreDisplayMode)Xlib_IDirectDraw2_RestoreDisplayMode,
3585 XCAST(SetCooperativeLevel)IDirectDraw2_SetCooperativeLevel,
3586 XCAST(SetDisplayMode)Xlib_IDirectDraw_SetDisplayMode,
3587 XCAST(WaitForVerticalBlank)IDirectDraw2_WaitForVerticalBlank,
3588 XCAST(GetAvailableVidMem)Xlib_IDirectDraw2_GetAvailableVidMem,
3589 IDirectDraw4_GetSurfaceFromDC,
3590 IDirectDraw4_RestoreAllSurfaces,
3591 IDirectDraw4_TestCooperativeLevel,
3592 IDirectDraw4_GetDeviceIdentifier
3597 /******************************************************************************
3601 LRESULT WINAPI Xlib_DDWndProc(HWND32 hwnd,UINT32 msg,WPARAM32 wParam,LPARAM lParam)
3604 LPDIRECTDRAW ddraw = NULL;
3607 /* FIXME(ddraw,"(0x%04x,%s,0x%08lx,0x%08lx),stub!\n",(int)hwnd,SPY_GetMsgName(msg),(long)wParam,(long)lParam); */
3609 SetLastError( ERROR_SUCCESS );
3610 ddraw = (LPDIRECTDRAW)GetWindowLong32A( hwnd, ddrawXlibThisOffset );
3612 ( ( lastError = GetLastError() ) != ERROR_SUCCESS )
3615 ERR( ddraw, "Unable to retrieve this ptr from window. Error %08lx\n", lastError );
3620 /* Perform any special direct draw functions */
3622 ddraw->d.paintable = 1;
3624 /* Now let the application deal with the rest of this */
3625 if( ddraw->d.mainWindow )
3628 /* Don't think that we actually need to call this but...
3629 might as well be on the safe side of things... */
3631 /* I changed hwnd to ddraw->d.mainWindow as I did not see why
3632 it should be the procedures of our fake window that gets called
3633 instead of those of the window provided by the application.
3634 And with this patch, mouse clicks work with Monkey Island III
3636 ret = DefWindowProc32A( ddraw->d.mainWindow, msg, wParam, lParam );
3640 /* We didn't handle the message - give it to the application */
3641 if (ddraw && ddraw->d.mainWindow && WIN_FindWndPtr(ddraw->d.mainWindow)) {
3642 ret = CallWindowProc32A( WIN_FindWndPtr( ddraw->d.mainWindow )->winproc,
3643 ddraw->d.mainWindow, msg, wParam, lParam );
3648 ret = DefWindowProc32A(hwnd, msg, wParam, lParam );
3654 ret = DefWindowProc32A(hwnd,msg,wParam,lParam);
3660 HRESULT WINAPI DGA_DirectDrawCreate( LPDIRECTDRAW *lplpDD, LPUNKNOWN pUnkOuter) {
3661 #ifdef HAVE_LIBXXF86DGA
3662 int memsize,banksize,width,major,minor,flags,height;
3666 /* Must be able to access /dev/mem for DGA extensions to work, root is not neccessary. --stephenc */
3667 if ((fd = open("/dev/mem", O_RDWR)) != -1)
3671 MSG("Must be able to access /dev/mem to use XF86DGA!\n");
3672 MessageBox32A(0,"Using the XF86DGA extension requires access to /dev/mem.","WINE DirectDraw",MB_OK|MB_ICONSTOP);
3673 return E_UNEXPECTED;
3675 if (!DDRAW_DGA_Available()) {
3676 TRACE(ddraw,"No XF86DGA detected.\n");
3677 return DDERR_GENERIC;
3679 *lplpDD = (LPDIRECTDRAW)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,sizeof(IDirectDraw));
3680 (*lplpDD)->lpvtbl = &dga_ddvt;
3682 TSXF86DGAQueryVersion(display,&major,&minor);
3683 TRACE(ddraw,"XF86DGA is version %d.%d\n",major,minor);
3684 TSXF86DGAQueryDirectVideo(display,DefaultScreen(display),&flags);
3685 if (!(flags & XF86DGADirectPresent))
3686 MSG("direct video is NOT PRESENT.\n");
3687 TSXF86DGAGetVideo(display,DefaultScreen(display),&addr,&width,&banksize,&memsize);
3688 TRACE(ddraw,"video framebuffer: begin %p, width %d,banksize %d,memsize %d\n",
3689 addr,width,banksize,memsize
3691 (*lplpDD)->e.dga.fb_width = width;
3692 (*lplpDD)->d.width = width;
3693 (*lplpDD)->e.dga.fb_addr = addr;
3694 (*lplpDD)->e.dga.fb_memsize = memsize;
3695 (*lplpDD)->e.dga.fb_banksize = banksize;
3697 TSXF86DGAGetViewPortSize(display,DefaultScreen(display),&width,&height);
3698 TSXF86DGASetViewPort(display,DefaultScreen(display),0,0);
3699 (*lplpDD)->e.dga.fb_height = MONITOR_GetHeight(&MONITOR_PrimaryMonitor);
3701 (*lplpDD)->e.dga.vpmask = 1;
3703 (*lplpDD)->e.dga.vpmask = 0;
3706 /* just assume the default depth is the DGA depth too */
3707 (*lplpDD)->d.screen_depth = DefaultDepthOfScreen(X11DRV_GetXScreen());
3708 (*lplpDD)->d.depth = DefaultDepthOfScreen(X11DRV_GetXScreen());
3709 #ifdef RESTORE_SIGNALS
3710 if (SIGNAL_Reinit) SIGNAL_Reinit();
3714 #else /* defined(HAVE_LIBXXF86DGA) */
3715 return DDERR_INVALIDDIRECTDRAWGUID;
3716 #endif /* defined(HAVE_LIBXXF86DGA) */
3720 DDRAW_XSHM_Available(void)
3722 #ifdef HAVE_LIBXXSHM
3723 if (TSXShmQueryExtension(display))
3728 if (TSXShmQueryVersion(display, &major, &minor, &shpix))
3740 HRESULT WINAPI Xlib_DirectDrawCreate( LPDIRECTDRAW *lplpDD, LPUNKNOWN pUnkOuter) {
3742 *lplpDD = (LPDIRECTDRAW)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,sizeof(IDirectDraw));
3743 (*lplpDD)->lpvtbl = &xlib_ddvt;
3745 (*lplpDD)->d.drawable = 0; /* in SetDisplayMode */
3747 (*lplpDD)->d.screen_depth = DefaultDepthOfScreen(X11DRV_GetXScreen());
3748 (*lplpDD)->d.height = MONITOR_GetHeight(&MONITOR_PrimaryMonitor);
3749 (*lplpDD)->d.width = MONITOR_GetWidth(&MONITOR_PrimaryMonitor);
3751 #ifdef HAVE_LIBXXSHM
3752 /* Test if XShm is available. */
3753 if (((*lplpDD)->e.xlib.xshm_active = DDRAW_XSHM_Available()))
3754 TRACE(ddraw, "Using XShm extension.\n");
3760 HRESULT WINAPI DirectDrawCreate( LPGUID lpGUID, LPDIRECTDRAW *lplpDD, LPUNKNOWN pUnkOuter ) {
3767 WINE_StringFromCLSID(lpGUID,xclsid);
3769 sprintf(xclsid,"<guid-0x%08x>",(int)lpGUID);
3773 TRACE(ddraw,"(%s,%p,%p)\n",xclsid,lplpDD,pUnkOuter);
3776 /* if they didn't request a particular interface, use the best
3778 if (DDRAW_DGA_Available())
3779 lpGUID = &DGA_DirectDraw_GUID;
3781 lpGUID = &XLIB_DirectDraw_GUID;
3784 wc.style = CS_GLOBALCLASS;
3785 wc.lpfnWndProc = Xlib_DDWndProc;
3787 wc.cbWndExtra = /* Defines extra mem for window. This is used for storing this */
3788 sizeof( LPDIRECTDRAW ); /* ddrawXlibThisOffset */
3790 /* We can be a child of the desktop since we're really important */
3791 pParentWindow = WIN_GetDesktop();
3792 wc.hInstance = pParentWindow ? pParentWindow->hwndSelf : 0;
3796 wc.hCursor = (HCURSOR32)IDC_ARROW32A;
3797 wc.hbrBackground= NULL_BRUSH;
3798 wc.lpszMenuName = 0;
3799 wc.lpszClassName= "WINE_DirectDraw";
3800 RegisterClass32A(&wc);
3802 if (!memcmp(lpGUID, &DGA_DirectDraw_GUID, sizeof(GUID)))
3803 ret = DGA_DirectDrawCreate(lplpDD, pUnkOuter);
3804 else if (!memcmp(lpGUID, &XLIB_DirectDraw_GUID, sizeof(GUID)))
3805 ret = Xlib_DirectDrawCreate(lplpDD, pUnkOuter);
3810 (*lplpDD)->d.winclass = RegisterClass32A(&wc);
3814 fprintf(stderr,"DirectDrawCreate(%s,%p,%p): did not recognize requested GUID\n",xclsid,lplpDD,pUnkOuter);
3815 return DDERR_INVALIDDIRECTDRAWGUID;