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.
22 #include <sys/signal.h>
28 #ifdef HAVE_LIBXXF86VM
29 /* X is retarted and insists on declaring INT32, INT16 etc in Xmd.h,
30 this is a crude hack to get around it */
32 #include "ts_xf86vmode.h"
36 #include "interfaces.h"
52 #ifdef HAVE_LIBXXF86DGA
53 #include "ts_xf86dga.h"
57 #include <sys/types.h>
63 /* This for all the enumeration and creation of D3D-related objects */
64 #include "d3d_private.h"
66 /* define this if you want to play Diablo using XF86DGA. (bug workaround) */
69 /* Restore signal handlers overwritten by XF86DGA
70 * this is a define, for it will only work in emulator mode
72 #undef RESTORE_SIGNALS
74 /* Where do these GUIDs come from? mkuuid.
75 * They exist solely to distinguish between the targets Wine support,
76 * and should be different than any other GUIDs in existence.
78 static GUID DGA_DirectDraw_GUID
= { /* e2dcb020-dc60-11d1-8407-9714f5d50802 */
82 {0x84, 0x07, 0x97, 0x14, 0xf5, 0xd5, 0x08, 0x02}
85 static GUID XLIB_DirectDraw_GUID
= { /* 1574a740-dc61-11d1-8407-f7875a7d1879 */
89 {0x84, 0x07, 0xf7, 0x87, 0x5a, 0x7d, 0x18, 0x79}
92 static struct IDirectDrawSurface3_VTable dga_dds3vt
, xlib_dds3vt
;
93 static struct IDirectDraw_VTable dga_ddvt
, xlib_ddvt
;
94 static struct IDirectDraw2_VTable dga_dd2vt
, xlib_dd2vt
;
95 static struct IDirectDrawClipper_VTable ddclipvt
;
96 static struct IDirectDrawPalette_VTable dga_ddpalvt
, xlib_ddpalvt
;
97 static struct IDirect3D_VTable d3dvt
;
98 static struct IDirect3D2_VTable d3d2vt
;
100 #ifdef HAVE_LIBXXF86VM
101 static XF86VidModeModeInfo
*orig_mode
= NULL
;
105 DDRAW_DGA_Available()
107 #ifdef HAVE_LIBXXF86DGA
108 int evbase
, evret
, fd
;
113 /* You don't have to be root to use DGA extensions. Simply having access to /dev/mem will do the trick */
114 /* This can be achieved by adding the user to the "kmem" group on Debian 2.x systems, don't know about */
115 /* others. --stephenc */
116 if ((fd
= open("/dev/mem", O_RDWR
)) != -1)
119 return (fd
!= -1) && TSXF86DGAQueryExtension(display
,&evbase
,&evret
);
120 #else /* defined(HAVE_LIBXXF86DGA) */
122 #endif /* defined(HAVE_LIBXXF86DGA) */
126 DirectDrawEnumerate32A(LPDDENUMCALLBACK32A ddenumproc
,LPVOID data
) {
127 if (DDRAW_DGA_Available()) {
128 TRACE(ddraw
, "Enumerating DGA interface\n");
129 ddenumproc(&DGA_DirectDraw_GUID
,"WINE with XFree86 DGA","display",data
);
131 TRACE(ddraw
, "Enumerating Xlib interface\n");
132 ddenumproc(&XLIB_DirectDraw_GUID
,"WINE with Xlib","display",data
);
133 TRACE(ddraw
, "Enumerating Default interface\n");
134 ddenumproc(NULL
,"WINE (default)","display",data
);
138 /* What is this doing here? */
140 DSoundHelp(DWORD x
,DWORD y
,DWORD z
) {
141 FIXME(ddraw
,"(0x%08lx,0x%08lx,0x%08lx),stub!\n",x
,y
,z
);
146 /******************************************************************************
147 * internal helper functions
149 static void _dump_DDBLTFX(DWORD flagmask
) {
155 #define FE(x) { x, #x},
156 FE(DDBLTFX_ARITHSTRETCHY
)
157 FE(DDBLTFX_MIRRORLEFTRIGHT
)
158 FE(DDBLTFX_MIRRORUPDOWN
)
159 FE(DDBLTFX_NOTEARING
)
160 FE(DDBLTFX_ROTATE180
)
161 FE(DDBLTFX_ROTATE270
)
163 FE(DDBLTFX_ZBUFFERRANGE
)
164 FE(DDBLTFX_ZBUFFERBASEDEST
)
166 for (i
=0;i
<sizeof(flags
)/sizeof(flags
[0]);i
++)
167 if (flags
[i
].mask
& flagmask
) {
168 DUMP("%s ",flags
[i
].name
);
175 static void _dump_DDBLTFAST(DWORD flagmask
) {
181 #define FE(x) { x, #x},
182 FE(DDBLTFAST_NOCOLORKEY
)
183 FE(DDBLTFAST_SRCCOLORKEY
)
184 FE(DDBLTFAST_DESTCOLORKEY
)
187 for (i
=0;i
<sizeof(flags
)/sizeof(flags
[0]);i
++)
188 if (flags
[i
].mask
& flagmask
)
189 DUMP("%s ",flags
[i
].name
);
193 static void _dump_DDBLT(DWORD flagmask
) {
199 #define FE(x) { x, #x},
201 FE(DDBLT_ALPHADESTCONSTOVERRIDE
)
202 FE(DDBLT_ALPHADESTNEG
)
203 FE(DDBLT_ALPHADESTSURFACEOVERRIDE
)
204 FE(DDBLT_ALPHAEDGEBLEND
)
206 FE(DDBLT_ALPHASRCCONSTOVERRIDE
)
207 FE(DDBLT_ALPHASRCNEG
)
208 FE(DDBLT_ALPHASRCSURFACEOVERRIDE
)
214 FE(DDBLT_KEYDESTOVERRIDE
)
216 FE(DDBLT_KEYSRCOVERRIDE
)
218 FE(DDBLT_ROTATIONANGLE
)
220 FE(DDBLT_ZBUFFERDESTCONSTOVERRIDE
)
221 FE(DDBLT_ZBUFFERDESTOVERRIDE
)
222 FE(DDBLT_ZBUFFERSRCCONSTOVERRIDE
)
223 FE(DDBLT_ZBUFFERSRCOVERRIDE
)
227 for (i
=0;i
<sizeof(flags
)/sizeof(flags
[0]);i
++)
228 if (flags
[i
].mask
& flagmask
)
229 DUMP("%s ",flags
[i
].name
);
232 static void _dump_DDSCAPS(DWORD flagmask
) {
238 #define FE(x) { x, #x},
239 FE(DDSCAPS_RESERVED1
)
241 FE(DDSCAPS_BACKBUFFER
)
244 FE(DDSCAPS_FRONTBUFFER
)
245 FE(DDSCAPS_OFFSCREENPLAIN
)
248 FE(DDSCAPS_PRIMARYSURFACE
)
249 FE(DDSCAPS_PRIMARYSURFACELEFT
)
250 FE(DDSCAPS_SYSTEMMEMORY
)
253 FE(DDSCAPS_VIDEOMEMORY
)
255 FE(DDSCAPS_WRITEONLY
)
258 FE(DDSCAPS_LIVEVIDEO
)
262 FE(DDSCAPS_RESERVED2
)
263 FE(DDSCAPS_ALLOCONLOAD
)
264 FE(DDSCAPS_VIDEOPORT
)
265 FE(DDSCAPS_LOCALVIDMEM
)
266 FE(DDSCAPS_NONLOCALVIDMEM
)
267 FE(DDSCAPS_STANDARDVGAMODE
)
268 FE(DDSCAPS_OPTIMIZED
)
270 for (i
=0;i
<sizeof(flags
)/sizeof(flags
[0]);i
++)
271 if (flags
[i
].mask
& flagmask
)
272 DUMP("%s ",flags
[i
].name
);
276 static void _dump_DDSD(DWORD flagmask
) {
286 FE(DDSD_BACKBUFFERCOUNT
)
287 FE(DDSD_ZBUFFERBITDEPTH
)
288 FE(DDSD_ALPHABITDEPTH
)
290 FE(DDSD_CKDESTOVERLAY
)
292 FE(DDSD_CKSRCOVERLAY
)
299 for (i
=0;i
<sizeof(flags
)/sizeof(flags
[0]);i
++)
300 if (flags
[i
].mask
& flagmask
)
301 DUMP("%s ",flags
[i
].name
);
305 static void _dump_DDCOLORKEY(DWORD flagmask
) {
311 #define FE(x) { x, #x},
315 FE(DDPF_PALETTEINDEXED4
)
316 FE(DDPF_PALETTEINDEXEDTO8
)
317 FE(DDPF_PALETTEINDEXED8
)
323 FE(DDPF_PALETTEINDEXED1
)
324 FE(DDPF_PALETTEINDEXED2
)
327 for (i
=0;i
<sizeof(flags
)/sizeof(flags
[0]);i
++)
328 if (flags
[i
].mask
& flagmask
)
329 DUMP("%s ",flags
[i
].name
);
333 static void _dump_pixelformat(LPDDPIXELFORMAT pf
) {
334 DUMP("Size : %ld\n", pf
->dwSize
);
336 _dump_DDCOLORKEY(pf
->dwFlags
);
337 DUMP("dwFourCC : %ld\n", pf
->dwFourCC
);
338 DUMP("RGB bit count : %ld\n", pf
->x
.dwRGBBitCount
);
339 DUMP("Masks : R %08lx G %08lx B %08lx A %08lx\n",
340 pf
->y
.dwRBitMask
, pf
->z
.dwGBitMask
, pf
->xx
.dwBBitMask
, pf
->xy
.dwRGBAlphaBitMask
);
343 static int _getpixelformat(LPDIRECTDRAW2 ddraw
,LPDDPIXELFORMAT pf
) {
344 static XVisualInfo
*vi
;
349 vi
= TSXGetVisualInfo(display
,VisualNoMask
,&vt
,&nitems
);
352 pf
->dwSize
= sizeof(DDPIXELFORMAT
);
353 if (ddraw
->d
.depth
==8) {
354 pf
->dwFlags
= DDPF_RGB
|DDPF_PALETTEINDEXED8
;
355 pf
->x
.dwRGBBitCount
= 8;
356 pf
->y
.dwRBitMask
= 0;
357 pf
->z
.dwGBitMask
= 0;
358 pf
->xx
.dwBBitMask
= 0;
359 pf
->xy
.dwRGBAlphaBitMask
= 0;
362 if (ddraw
->d
.depth
==16) {
363 pf
->dwFlags
= DDPF_RGB
;
364 pf
->x
.dwRGBBitCount
= 16;
365 pf
->y
.dwRBitMask
= vi
[0].red_mask
;
366 pf
->z
.dwGBitMask
= vi
[0].green_mask
;
367 pf
->xx
.dwBBitMask
= vi
[0].blue_mask
;
368 pf
->xy
.dwRGBAlphaBitMask
= 0;
371 FIXME(ddraw
,"_getpixelformat:unknown depth %ld?\n",ddraw
->d
.depth
);
372 return DDERR_GENERIC
;
375 /******************************************************************************
376 * IDirectDrawSurface,IDirectDrawSurface2,IDirectDrawSurface3
378 * Since DDS3 and DDS2 are supersets of DDS, we implement DDS3 and let
379 * DDS and DDS2 use those functions. (Function calls did not change (except
380 * using different DirectDrawSurfaceX version), just added flags and functions)
382 static HRESULT WINAPI
IDirectDrawSurface3_Lock(
383 LPDIRECTDRAWSURFACE3
this,LPRECT32 lprect
,LPDDSURFACEDESC lpddsd
,DWORD flags
, HANDLE32 hnd
385 TRACE(ddraw
, "(%p)->Lock(%p,%p,%08lx,%08lx)\n",
386 this,lprect
,lpddsd
,flags
,(DWORD
)hnd
);
387 if (flags
& ~(DDLOCK_WAIT
|DDLOCK_READONLY
|DDLOCK_WRITEONLY
))
388 WARN(ddraw
, "(%p)->Lock(%p,%p,%08lx,%08lx)\n",
389 this,lprect
,lpddsd
,flags
,(DWORD
)hnd
);
391 /* First, copy the Surface description */
392 *lpddsd
= this->s
.surface_desc
;
394 /* If asked only for a part, change the surface pointer */
396 FIXME(ddraw
," lprect: %dx%d-%dx%d\n",
397 lprect
->top
,lprect
->left
,lprect
->bottom
,lprect
->right
399 lpddsd
->y
.lpSurface
= this->s
.surface_desc
.y
.lpSurface
+
400 (lprect
->top
*this->s
.surface_desc
.lPitch
) +
401 (lprect
->left
*(this->s
.surface_desc
.ddpfPixelFormat
.x
.dwRGBBitCount
/ 8));
403 assert(this->s
.surface_desc
.y
.lpSurface
);
408 static HRESULT WINAPI
DGA_IDirectDrawSurface3_Unlock(
409 LPDIRECTDRAWSURFACE3
this,LPVOID surface
411 TRACE(ddraw
,"(%p)->Unlock(%p)\n",this,surface
);
415 static HRESULT WINAPI
Xlib_IDirectDrawSurface3_Unlock(
416 LPDIRECTDRAWSURFACE3
this,LPVOID surface
)
418 TRACE(ddraw
,"(%p)->Unlock(%p)\n",this,surface
);
420 if (!this->s
.ddraw
->e
.xlib
.paintable
)
423 /* Only redraw the screen when unlocking the buffer that is on screen */
424 if ((this->t
.xlib
.image
!= NULL
) &&
425 (this->s
.surface_desc
.ddsCaps
.dwCaps
& DDSCAPS_VISIBLE
)) {
427 if (this->s
.ddraw
->e
.xlib
.xshm_active
)
428 TSXShmPutImage(display
,
429 this->s
.ddraw
->e
.xlib
.drawable
,
430 DefaultGCOfScreen(screen
),
433 this->t
.xlib
.image
->width
,
434 this->t
.xlib
.image
->height
,
438 TSXPutImage( display
,
439 this->s
.ddraw
->e
.xlib
.drawable
,
440 DefaultGCOfScreen(screen
),
443 this->t
.xlib
.image
->width
,
444 this->t
.xlib
.image
->height
);
446 if (this->s
.palette
&& this->s
.palette
->cm
)
447 TSXSetWindowColormap(display
,this->s
.ddraw
->e
.xlib
.drawable
,this->s
.palette
->cm
);
453 static HRESULT WINAPI
DGA_IDirectDrawSurface3_Flip(
454 LPDIRECTDRAWSURFACE3
this,LPDIRECTDRAWSURFACE3 flipto
,DWORD dwFlags
456 #ifdef HAVE_LIBXXF86DGA
457 TRACE(ddraw
,"(%p)->Flip(%p,%08lx)\n",this,flipto
,dwFlags
);
459 if (this->s
.backbuffer
)
460 flipto
= this->s
.backbuffer
;
464 TSXF86DGASetViewPort(display
,DefaultScreen(display
),0,flipto
->t
.dga
.fb_height
);
466 if (flipto
->s
.palette
&& flipto
->s
.palette
->cm
) {
467 TSXF86DGAInstallColormap(display
,DefaultScreen(display
),flipto
->s
.palette
->cm
);
469 while (!TSXF86DGAViewPortChanged(display
,DefaultScreen(display
),2)) {
475 tmp
= this->t
.dga
.fb_height
;
476 this->t
.dga
.fb_height
= flipto
->t
.dga
.fb_height
;
477 flipto
->t
.dga
.fb_height
= tmp
;
479 ptmp
= this->s
.surface_desc
.y
.lpSurface
;
480 this->s
.surface_desc
.y
.lpSurface
= flipto
->s
.surface_desc
.y
.lpSurface
;
481 flipto
->s
.surface_desc
.y
.lpSurface
= ptmp
;
484 #else /* defined(HAVE_LIBXXF86DGA) */
486 #endif /* defined(HAVE_LIBXXF86DGA) */
489 static HRESULT WINAPI
Xlib_IDirectDrawSurface3_Flip(
490 LPDIRECTDRAWSURFACE3
this,LPDIRECTDRAWSURFACE3 flipto
,DWORD dwFlags
492 TRACE(ddraw
,"(%p)->Flip(%p,%08lx)\n",this,flipto
,dwFlags
);
493 if (!this->s
.ddraw
->e
.xlib
.paintable
)
497 if (this->s
.backbuffer
)
498 flipto
= this->s
.backbuffer
;
504 if (this->s
.ddraw
->e
.xlib
.xshm_active
) {
505 TSXShmPutImage(display
,
506 this->s
.ddraw
->e
.xlib
.drawable
,
507 DefaultGCOfScreen(screen
),
508 flipto
->t
.xlib
.image
,
510 flipto
->t
.xlib
.image
->width
,
511 flipto
->t
.xlib
.image
->height
,
516 this->s
.ddraw
->e
.xlib
.drawable
,
517 DefaultGCOfScreen(screen
),
518 flipto
->t
.xlib
.image
,
520 flipto
->t
.xlib
.image
->width
,
521 flipto
->t
.xlib
.image
->height
);
523 if (flipto
->s
.palette
&& flipto
->s
.palette
->cm
) {
524 TSXSetWindowColormap(display
,this->s
.ddraw
->e
.xlib
.drawable
,flipto
->s
.palette
->cm
);
529 tmp
= this->t
.xlib
.image
;
530 this->t
.xlib
.image
= flipto
->t
.xlib
.image
;
531 flipto
->t
.xlib
.image
= tmp
;
532 surf
= this->s
.surface_desc
.y
.lpSurface
;
533 this->s
.surface_desc
.y
.lpSurface
= flipto
->s
.surface_desc
.y
.lpSurface
;
534 flipto
->s
.surface_desc
.y
.lpSurface
= surf
;
540 /* The IDirectDrawSurface3::SetPalette method attaches the specified
541 * DirectDrawPalette object to a surface. The surface uses this palette for all
542 * subsequent operations. The palette change takes place immediately.
544 static HRESULT WINAPI
Xlib_IDirectDrawSurface3_SetPalette(
545 LPDIRECTDRAWSURFACE3
this,LPDIRECTDRAWPALETTE pal
548 TRACE(ddraw
,"(%p)->(%p)\n",this,pal
);
550 if( !(pal
->cm
) && (this->s
.ddraw
->d
.depth
<=8))
552 pal
->cm
= TSXCreateColormap(display
,this->s
.ddraw
->e
.xlib
.drawable
,DefaultVisualOfScreen(screen
),AllocAll
);
554 /* FIXME: this is not correct, when using -managed (XSetWindowColormap??) */
555 TSXInstallColormap(display
,pal
->cm
);
557 for (i
=0;i
<256;i
++) {
560 xc
.red
= pal
->palents
[i
].peRed
<<8;
561 xc
.blue
= pal
->palents
[i
].peBlue
<<8;
562 xc
.green
= pal
->palents
[i
].peGreen
<<8;
563 xc
.flags
= DoRed
|DoBlue
|DoGreen
;
565 TSXStoreColor(display
,pal
->cm
,&xc
);
569 /* According to spec, we are only supposed to
570 * AddRef if this is not the same palette.
572 if( this->s
.palette
!= pal
)
575 pal
->lpvtbl
->fnAddRef( pal
);
576 if( this->s
.palette
!= NULL
)
577 this->s
.palette
->lpvtbl
->fnRelease( this->s
.palette
);
578 this->s
.palette
= pal
;
580 /* I think that we need to attach it to all backbuffers...*/
581 if( this->s
.backbuffer
) {
582 if( this->s
.backbuffer
->s
.palette
)
583 this->s
.backbuffer
->s
.palette
->lpvtbl
->fnRelease(
584 this->s
.backbuffer
->s
.palette
);
585 this->s
.backbuffer
->s
.palette
= pal
;
587 pal
->lpvtbl
->fnAddRef( pal
);
589 /* Perform the refresh */
590 TSXSetWindowColormap(display
,this->s
.ddraw
->e
.xlib
.drawable
,this->s
.palette
->cm
);
595 static HRESULT WINAPI
DGA_IDirectDrawSurface3_SetPalette(
596 LPDIRECTDRAWSURFACE3
this,LPDIRECTDRAWPALETTE pal
598 TRACE(ddraw
,"(%p)->(%p)\n",this,pal
);
599 #ifdef HAVE_LIBXXF86DGA
600 /* According to spec, we are only supposed to
601 * AddRef if this is not the same palette.
603 if( this->s
.palette
!= pal
)
606 pal
->lpvtbl
->fnAddRef( pal
);
607 if( this->s
.palette
!= NULL
)
608 this->s
.palette
->lpvtbl
->fnRelease( this->s
.palette
);
609 this->s
.palette
= pal
;
611 /* I think that we need to attach it to all backbuffers...*/
612 if( this->s
.backbuffer
) {
613 if( this->s
.backbuffer
->s
.palette
)
614 this->s
.backbuffer
->s
.palette
->lpvtbl
->fnRelease(this->s
.backbuffer
->s
.palette
);
615 this->s
.backbuffer
->s
.palette
= pal
;
616 if( pal
) pal
->lpvtbl
->fnAddRef( pal
);
618 TSXF86DGAInstallColormap(display
,DefaultScreen(display
),this->s
.palette
->cm
);
621 #else /* defined(HAVE_LIBXXF86DGA) */
623 #endif /* defined(HAVE_LIBXXF86DGA) */
628 static HRESULT WINAPI
IDirectDrawSurface3_Blt(
629 LPDIRECTDRAWSURFACE3
this,LPRECT32 rdst
,LPDIRECTDRAWSURFACE3 src
,LPRECT32 rsrc
,DWORD dwFlags
,LPDDBLTFX lpbltfx
632 DDSURFACEDESC ddesc
,sdesc
;
635 TRACE(ddraw
,"(%p)->(%p,%p,%p,%08lx,%p)\n",
636 this,rdst
,src
,rsrc
,dwFlags
,lpbltfx
);
639 src
->lpvtbl
->fnLock(src
, NULL
,&sdesc
,0,0);
640 this->lpvtbl
->fnLock(this,NULL
,&ddesc
,0,0);
642 if (TRACE_ON(ddraw
)) {
643 if (rdst
) TRACE(ddraw
," destrect :%dx%d-%dx%d\n",rdst
->left
,rdst
->top
,rdst
->right
,rdst
->bottom
);
644 if (rsrc
) TRACE(ddraw
," srcrect :%dx%d-%dx%d\n",rsrc
->left
,rsrc
->top
,rsrc
->right
,rsrc
->bottom
);
645 TRACE(ddraw
,"\tflags: ");_dump_DDBLT(dwFlags
);fprintf(stderr
,"\n");
646 if (dwFlags
& DDBLT_DDFX
) {
647 TRACE(ddraw
," blitfx: \n");_dump_DDBLTFX(lpbltfx
->dwDDFX
);
652 memcpy(&xdst
,rdst
,sizeof(xdst
));
655 xdst
.bottom
= ddesc
.dwHeight
;
657 xdst
.right
= ddesc
.dwWidth
;
661 memcpy(&xsrc
,rsrc
,sizeof(xsrc
));
665 xsrc
.bottom
= sdesc
.dwHeight
;
667 xsrc
.right
= sdesc
.dwWidth
;
669 memset(&xsrc
,0,sizeof(xsrc
));
673 dwFlags
&= ~(DDBLT_WAIT
|DDBLT_ASYNC
);/* FIXME: can't handle right now */
675 if (dwFlags
& DDBLT_COLORFILL
) {
676 int bpp
= ddesc
.ddpfPixelFormat
.x
.dwRGBBitCount
/ 8;
679 xline
= (LPBYTE
) ddesc
.y
.lpSurface
+ xdst
.top
* ddesc
.lPitch
;
680 for (i
=xdst
.top
;i
<xdst
.bottom
;i
++) {
681 xpixel
= xline
+bpp
*xdst
.left
;
683 for (j
=xdst
.left
;j
<xdst
.right
;j
++) {
684 /* FIXME: this only works on little endian
685 * architectures, where DWORD starts with low
688 memcpy(xpixel
,&(lpbltfx
->b
.dwFillColor
),bpp
);
691 xline
+= ddesc
.lPitch
;
693 dwFlags
&= ~(DDBLT_COLORFILL
);
698 TRACE(ddraw
,"\t(src=NULL):Unsupported flags: ");_dump_DDBLT(dwFlags
);fprintf(stderr
,"\n");
703 if ( (xsrc
.top
==0) && (xsrc
.bottom
==ddesc
.dwHeight
) &&
704 (xsrc
.left
==0) && (xsrc
.right
==ddesc
.dwWidth
) &&
705 (xdst
.top
==0) && (xdst
.bottom
==ddesc
.dwHeight
) &&
706 (xdst
.left
==0) && (xdst
.right
==ddesc
.dwWidth
) &&
709 memcpy(ddesc
.y
.lpSurface
,
711 ddesc
.dwHeight
* ddesc
.lPitch
);
713 int bpp
= ddesc
.ddpfPixelFormat
.x
.dwRGBBitCount
/ 8;
714 int srcheight
= xsrc
.bottom
- xsrc
.top
;
715 int srcwidth
= xsrc
.right
- xsrc
.left
;
716 int dstheight
= xdst
.bottom
- xdst
.top
;
717 int dstwidth
= xdst
.right
- xdst
.left
;
718 int width
= (xsrc
.right
- xsrc
.left
) * bpp
;
721 /* Sanity check for rectangle sizes */
722 if ((srcheight
!= dstheight
) || (srcwidth
!= dstwidth
)) {
725 /* I think we should do a Blit with 'stretching' here....
726 Tomb Raider II uses this to display the background during the menu selection
727 when the screen resolution is != than 40x480 */
728 TRACE(ddraw
, "Blt with stretching\n");
730 /* This is a basic stretch implementation. It is painfully slow and quite ugly. */
732 /* In this case, we cannot do any anti-aliasing */
733 for (y
= xdst
.top
; y
< xdst
.bottom
; y
++) {
734 for (x
= xdst
.left
; x
< xdst
.right
; x
++) {
736 unsigned char *dbuf
= (unsigned char *) ddesc
.y
.lpSurface
;
737 unsigned char *sbuf
= (unsigned char *) sdesc
.y
.lpSurface
;
739 sx
= (((double) (x
- xdst
.left
) / dstwidth
) * srcwidth
) + xsrc
.left
;
740 sy
= (((double) (y
- xdst
.top
) / dstheight
) * srcheight
) + xsrc
.top
;
742 dbuf
[(y
* ddesc
.lPitch
) + x
] = sbuf
[(((int) sy
) * sdesc
.lPitch
) + ((int) sx
)];
746 FIXME(ddraw
, "Not done yet for depth != 8\n");
749 /* Same size => fast blit */
750 for (h
= 0; h
< srcheight
; h
++) {
751 memcpy(ddesc
.y
.lpSurface
+ ((h
+ xdst
.top
) * ddesc
.lPitch
) + xdst
.left
* bpp
,
752 sdesc
.y
.lpSurface
+ ((h
+ xsrc
.top
) * sdesc
.lPitch
) + xsrc
.left
* bpp
,
758 if (dwFlags
&& FIXME_ON(ddraw
)) {
759 FIXME(ddraw
,"\tUnsupported flags: ");_dump_DDBLT(dwFlags
);
762 this->lpvtbl
->fnUnlock(this,ddesc
.y
.lpSurface
);
763 src
->lpvtbl
->fnUnlock(src
,sdesc
.y
.lpSurface
);
768 static HRESULT WINAPI
IDirectDrawSurface3_BltFast(
769 LPDIRECTDRAWSURFACE3
this,DWORD dstx
,DWORD dsty
,LPDIRECTDRAWSURFACE3 src
,LPRECT32 rsrc
,DWORD trans
772 DDSURFACEDESC ddesc
,sdesc
;
774 if (TRACE_ON(ddraw
)) {
775 TRACE(ddraw
,"(%p)->(%ld,%ld,%p,%p,%08lx)\n",
776 this,dstx
,dsty
,src
,rsrc
,trans
778 TRACE(ddraw
," trans:");_dump_DDBLTFAST(trans
);fprintf(stderr
,"\n");
779 TRACE(ddraw
," srcrect: %dx%d-%dx%d\n",rsrc
->left
,rsrc
->top
,rsrc
->right
,rsrc
->bottom
);
781 /* We need to lock the surfaces, or we won't get refreshes when done. */
782 src
->lpvtbl
->fnLock(src
, NULL
,&sdesc
,DDLOCK_READONLY
, 0);
783 this->lpvtbl
->fnLock(this,NULL
,&ddesc
,DDLOCK_WRITEONLY
,0);
784 bpp
= this->s
.surface_desc
.ddpfPixelFormat
.x
.dwRGBBitCount
/ 8;
785 for (i
=0;i
<rsrc
->bottom
-rsrc
->top
;i
++) {
786 memcpy( ddesc
.y
.lpSurface
+(dsty
+i
)*ddesc
.lPitch
+dstx
*bpp
,
787 sdesc
.y
.lpSurface
+(rsrc
->top
+i
)*sdesc
.lPitch
+rsrc
->left
*bpp
,
788 (rsrc
->right
-rsrc
->left
)*bpp
791 this->lpvtbl
->fnUnlock(this,ddesc
.y
.lpSurface
);
792 src
->lpvtbl
->fnUnlock(src
,sdesc
.y
.lpSurface
);
796 static HRESULT WINAPI
IDirectDrawSurface3_BltBatch(
797 LPDIRECTDRAWSURFACE3
this,LPDDBLTBATCH ddbltbatch
,DWORD x
,DWORD y
799 FIXME(ddraw
,"(%p)->BltBatch(%p,%08lx,%08lx),stub!\n",
805 static HRESULT WINAPI
IDirectDrawSurface3_GetCaps(
806 LPDIRECTDRAWSURFACE3
this,LPDDSCAPS caps
808 TRACE(ddraw
,"(%p)->GetCaps(%p)\n",this,caps
);
809 caps
->dwCaps
= DDSCAPS_PALETTE
; /* probably more */
813 static HRESULT WINAPI
IDirectDrawSurface3_GetSurfaceDesc(
814 LPDIRECTDRAWSURFACE3
this,LPDDSURFACEDESC ddsd
816 TRACE(ddraw
, "(%p)->GetSurfaceDesc(%p)\n",
819 /* Simply copy the surface description stored in the object */
820 *ddsd
= this->s
.surface_desc
;
822 if (TRACE_ON(ddraw
)) {
823 fprintf(stderr
," flags: ");
824 _dump_DDSD(ddsd
->dwFlags
);
825 if (ddsd
->dwFlags
& DDSD_CAPS
) {
826 fprintf(stderr
, " caps: ");
827 _dump_DDSCAPS(ddsd
->ddsCaps
.dwCaps
);
829 fprintf(stderr
,"\n");
835 static ULONG WINAPI
IDirectDrawSurface3_AddRef(LPDIRECTDRAWSURFACE3
this) {
836 TRACE( ddraw
, "(%p)->() incrementing from %lu.\n", this, this->ref
);
838 return ++(this->ref
);
841 static ULONG WINAPI
DGA_IDirectDrawSurface3_Release(LPDIRECTDRAWSURFACE3
this) {
842 TRACE( ddraw
, "(%p)->() decrementing from %lu.\n", this, this->ref
);
844 #ifdef HAVE_LIBXXF86DGA
845 if (!--(this->ref
)) {
846 this->s
.ddraw
->lpvtbl
->fnRelease(this->s
.ddraw
);
847 /* clear out of surface list */
848 if (this->t
.dga
.fb_height
== -1) {
849 HeapFree(GetProcessHeap(),0,this->s
.surface_desc
.y
.lpSurface
);
851 this->s
.ddraw
->e
.dga
.vpmask
&= ~(1<<(this->t
.dga
.fb_height
/this->s
.ddraw
->e
.dga
.fb_height
));
853 HeapFree(GetProcessHeap(),0,this);
856 #endif /* defined(HAVE_LIBXXF86DGA) */
860 static ULONG WINAPI
Xlib_IDirectDrawSurface3_Release(LPDIRECTDRAWSURFACE3
this) {
861 TRACE( ddraw
, "(%p)->() decrementing from %lu.\n", this, this->ref
);
863 if (!--(this->ref
)) {
864 this->s
.ddraw
->lpvtbl
->fnRelease(this->s
.ddraw
);
866 if( this->s
.backbuffer
)
867 this->s
.backbuffer
->lpvtbl
->fnRelease(this->s
.backbuffer
);
869 if (this->t
.xlib
.image
!= NULL
) {
870 this->t
.xlib
.image
->data
= NULL
;
873 if (this->s
.ddraw
->e
.xlib
.xshm_active
) {
874 TSXShmDetach(display
, &(this->t
.xlib
.shminfo
));
875 TSXDestroyImage(this->t
.xlib
.image
);
876 shmdt(this->t
.xlib
.shminfo
.shmaddr
);
879 HeapFree(GetProcessHeap(),0,this->s
.surface_desc
.y
.lpSurface
);
880 TSXDestroyImage(this->t
.xlib
.image
);
885 this->t
.xlib
.image
= 0;
887 HeapFree(GetProcessHeap(),0,this->s
.surface_desc
.y
.lpSurface
);
891 this->s
.palette
->lpvtbl
->fnRelease(this->s
.palette
);
893 HeapFree(GetProcessHeap(),0,this);
900 static HRESULT WINAPI
IDirectDrawSurface3_GetAttachedSurface(
901 LPDIRECTDRAWSURFACE3
this,LPDDSCAPS lpddsd
,LPDIRECTDRAWSURFACE3
*lpdsf
903 TRACE(ddraw
, "(%p)->GetAttachedSurface(%p,%p)\n",
904 this, lpddsd
, lpdsf
);
906 if (TRACE_ON(ddraw
)) {
907 TRACE(ddraw
," caps ");
908 _dump_DDSCAPS(lpddsd
->dwCaps
);
911 if (!(lpddsd
->dwCaps
& DDSCAPS_BACKBUFFER
)) {
912 FIXME(ddraw
,"whoops, can only handle backbuffers for now\n");
916 /* FIXME: should handle more than one backbuffer */
917 *lpdsf
= this->s
.backbuffer
;
919 if( this->s
.backbuffer
)
920 this->s
.backbuffer
->lpvtbl
->fnAddRef( this->s
.backbuffer
);
925 static HRESULT WINAPI
IDirectDrawSurface3_Initialize(
926 LPDIRECTDRAWSURFACE3
this,LPDIRECTDRAW ddraw
,LPDDSURFACEDESC lpdsfd
928 TRACE(ddraw
,"(%p)->(%p, %p)\n",this,ddraw
,lpdsfd
);
930 return DDERR_ALREADYINITIALIZED
;
933 static HRESULT WINAPI
IDirectDrawSurface3_GetPixelFormat(
934 LPDIRECTDRAWSURFACE3
this,LPDDPIXELFORMAT pf
936 TRACE(ddraw
,"(%p)->(%p)\n",this,pf
);
938 *pf
= this->s
.surface_desc
.ddpfPixelFormat
;
943 static HRESULT WINAPI
IDirectDrawSurface3_GetBltStatus(LPDIRECTDRAWSURFACE3
this,DWORD dwFlags
) {
944 FIXME(ddraw
,"(%p)->(0x%08lx),stub!\n",this,dwFlags
);
948 static HRESULT WINAPI
IDirectDrawSurface3_GetOverlayPosition(
949 LPDIRECTDRAWSURFACE3
this,LPLONG x1
,LPLONG x2
951 FIXME(ddraw
,"(%p)->(%p,%p),stub!\n",this,x1
,x2
);
955 static HRESULT WINAPI
IDirectDrawSurface3_SetClipper(
956 LPDIRECTDRAWSURFACE3
this,LPDIRECTDRAWCLIPPER clipper
958 FIXME(ddraw
,"(%p)->(%p),stub!\n",this,clipper
);
962 static HRESULT WINAPI
IDirectDrawSurface3_AddAttachedSurface(
963 LPDIRECTDRAWSURFACE3
this,LPDIRECTDRAWSURFACE3 surf
965 FIXME(ddraw
,"(%p)->(%p),stub!\n",this,surf
);
967 /* This hack will be enough for the moment */
968 if (this->s
.backbuffer
== NULL
)
969 this->s
.backbuffer
= surf
;
973 static HRESULT WINAPI
IDirectDrawSurface3_GetDC(LPDIRECTDRAWSURFACE3
this,HDC32
* lphdc
) {
974 FIXME(ddraw
,"(%p)->GetDC(%p)\n",this,lphdc
);
975 *lphdc
= BeginPaint32(this->s
.ddraw
->d
.window
,&this->s
.ddraw
->d
.ps
);
979 static HRESULT WINAPI
IDirectDrawSurface3_ReleaseDC(LPDIRECTDRAWSURFACE3
this,HDC32 hdc
) {
980 FIXME(ddraw
,"(%p)->(0x%08lx),stub!\n",this,(long)hdc
);
981 EndPaint32(this->s
.ddraw
->d
.window
,&this->s
.ddraw
->d
.ps
);
986 static HRESULT WINAPI
IDirectDrawSurface3_QueryInterface(LPDIRECTDRAWSURFACE3
this,REFIID refiid
,LPVOID
*obj
) {
989 WINE_StringFromCLSID((LPCLSID
)refiid
,xrefiid
);
990 TRACE(ddraw
,"(%p)->(%s,%p)\n",this,xrefiid
,obj
);
992 /* DirectDrawSurface,DirectDrawSurface2 and DirectDrawSurface3 use
993 * the same interface. And IUnknown does that too of course.
995 if ( !memcmp(&IID_IDirectDrawSurface3
,refiid
,sizeof(IID
)) ||
996 !memcmp(&IID_IDirectDrawSurface2
,refiid
,sizeof(IID
)) ||
997 !memcmp(&IID_IDirectDrawSurface
,refiid
,sizeof(IID
)) ||
998 !memcmp(&IID_IUnknown
,refiid
,sizeof(IID
))
1001 this->lpvtbl
->fnAddRef(this);
1003 TRACE(ddraw
, " Creating IDirect3DSurfaceX interface (%p)\n", *obj
);
1007 else if (!memcmp(&IID_IDirect3DTexture2
,refiid
,sizeof(IID
)))
1009 /* Texture interface */
1010 *obj
= d3dtexture2_create(this);
1011 this->lpvtbl
->fnAddRef(this);
1013 TRACE(ddraw
, " Creating IDirect3DTexture2 interface (%p)\n", *obj
);
1017 else if (!memcmp(&IID_IDirect3DTexture
,refiid
,sizeof(IID
)))
1019 /* Texture interface */
1020 *obj
= d3dtexture_create(this);
1021 this->lpvtbl
->fnAddRef(this);
1023 TRACE(ddraw
, " Creating IDirect3DTexture interface (%p)\n", *obj
);
1027 else if (is_OpenGL_dx3(refiid
, (LPDIRECTDRAWSURFACE
) this, (LPDIRECT3DDEVICE
*) obj
))
1029 /* It is the OpenGL Direct3D Device */
1030 this->lpvtbl
->fnAddRef(this);
1032 TRACE(ddraw
, " Creating IDirect3DDevice interface (%p)\n", *obj
);
1037 FIXME(ddraw
,"(%p):interface for IID %s NOT found!\n",this,xrefiid
);
1038 return OLE_E_ENUM_NOMORE
;
1041 static HRESULT WINAPI
IDirectDrawSurface3_IsLost(LPDIRECTDRAWSURFACE3
this) {
1042 TRACE(ddraw
,"(%p)->(), stub!\n",this);
1043 return DD_OK
; /* hmm */
1046 static HRESULT WINAPI
IDirectDrawSurface3_EnumAttachedSurfaces(LPDIRECTDRAWSURFACE3
this,LPVOID context
,LPDDENUMSURFACESCALLBACK esfcb
) {
1047 FIXME(ddraw
,"(%p)->(%p,%p),stub!\n",this,context
,esfcb
);
1051 static HRESULT WINAPI
IDirectDrawSurface3_Restore(LPDIRECTDRAWSURFACE3
this) {
1052 FIXME(ddraw
,"(%p)->(),stub!\n",this);
1056 static HRESULT WINAPI
IDirectDrawSurface3_SetColorKey(
1057 LPDIRECTDRAWSURFACE3
this, DWORD dwFlags
, LPDDCOLORKEY ckey
)
1059 TRACE(ddraw
,"(%p)->(0x%08lx,%p)\n",this,dwFlags
,ckey
);
1061 if( dwFlags
& DDCKEY_SRCBLT
)
1063 dwFlags
&= ~DDCKEY_SRCBLT
;
1064 memcpy( &(this->s
.ckSrcBlt
), ckey
, sizeof( *ckey
) );
1067 if( dwFlags
& DDCKEY_DESTBLT
)
1069 dwFlags
&= ~DDCKEY_DESTBLT
;
1070 memcpy( &(this->s
.ckDestBlt
), ckey
, sizeof( *ckey
) );
1073 if( dwFlags
& DDCKEY_SRCOVERLAY
)
1075 dwFlags
&= ~DDCKEY_SRCOVERLAY
;
1076 memcpy( &(this->s
.ckSrcOverlay
), ckey
, sizeof( *ckey
) );
1078 if( dwFlags
& DDCKEY_DESTOVERLAY
)
1080 dwFlags
&= ~DDCKEY_DESTOVERLAY
;
1081 memcpy( &(this->s
.ckDestOverlay
), ckey
, sizeof( *ckey
) );
1086 FIXME( ddraw
, "unhandled dwFlags: 0x%08lx\n", dwFlags
);
1093 static HRESULT WINAPI
IDirectDrawSurface3_AddOverlayDirtyRect(
1094 LPDIRECTDRAWSURFACE3
this,
1097 FIXME(ddraw
,"(%p)->(%p),stub!\n",this,lpRect
);
1102 static HRESULT WINAPI
IDirectDrawSurface3_DeleteAttachedSurface(
1103 LPDIRECTDRAWSURFACE3
this,
1105 LPDIRECTDRAWSURFACE3 lpDDSAttachedSurface
)
1107 FIXME(ddraw
,"(%p)->(0x%08lx,%p),stub!\n",this,dwFlags
,lpDDSAttachedSurface
);
1112 static HRESULT WINAPI
IDirectDrawSurface3_EnumOverlayZOrders(
1113 LPDIRECTDRAWSURFACE3
this,
1116 LPDDENUMSURFACESCALLBACK lpfnCallback
)
1118 FIXME(ddraw
,"(%p)->(0x%08lx,%p,%p),stub!\n", this,dwFlags
,
1119 lpContext
, lpfnCallback
);
1124 static HRESULT WINAPI
IDirectDrawSurface3_GetClipper(
1125 LPDIRECTDRAWSURFACE3
this,
1126 LPDIRECTDRAWCLIPPER
* lplpDDClipper
)
1128 FIXME(ddraw
,"(%p)->(%p),stub!\n", this, lplpDDClipper
);
1133 static HRESULT WINAPI
IDirectDrawSurface3_GetColorKey(
1134 LPDIRECTDRAWSURFACE3
this,
1136 LPDDCOLORKEY lpDDColorKey
)
1138 TRACE(ddraw
,"(%p)->(0x%08lx,%p)\n", this, dwFlags
, lpDDColorKey
);
1140 if( dwFlags
& DDCKEY_SRCBLT
) {
1141 dwFlags
&= ~DDCKEY_SRCBLT
;
1142 memcpy( lpDDColorKey
, &(this->s
.ckSrcBlt
), sizeof( *lpDDColorKey
) );
1145 if( dwFlags
& DDCKEY_DESTBLT
)
1147 dwFlags
&= ~DDCKEY_DESTBLT
;
1148 memcpy( lpDDColorKey
, &(this->s
.ckDestBlt
), sizeof( *lpDDColorKey
) );
1151 if( dwFlags
& DDCKEY_SRCOVERLAY
)
1153 dwFlags
&= ~DDCKEY_SRCOVERLAY
;
1154 memcpy( lpDDColorKey
, &(this->s
.ckSrcOverlay
), sizeof( *lpDDColorKey
) );
1157 if( dwFlags
& DDCKEY_DESTOVERLAY
)
1159 dwFlags
&= ~DDCKEY_DESTOVERLAY
;
1160 memcpy( lpDDColorKey
, &(this->s
.ckDestOverlay
), sizeof( *lpDDColorKey
) );
1165 FIXME( ddraw
, "unhandled dwFlags: 0x%08lx\n", dwFlags
);
1171 static HRESULT WINAPI
IDirectDrawSurface3_GetFlipStatus(
1172 LPDIRECTDRAWSURFACE3
this,
1175 FIXME(ddraw
,"(%p)->(0x%08lx),stub!\n", this, dwFlags
);
1180 static HRESULT WINAPI
IDirectDrawSurface3_GetPalette(
1181 LPDIRECTDRAWSURFACE3
this,
1182 LPDIRECTDRAWPALETTE
* lplpDDPalette
)
1184 FIXME(ddraw
,"(%p)->(%p),stub!\n", this, lplpDDPalette
);
1189 static HRESULT WINAPI
IDirectDrawSurface3_SetOverlayPosition(
1190 LPDIRECTDRAWSURFACE3
this,
1194 FIXME(ddraw
,"(%p)->(%ld,%ld),stub!\n", this, lX
, lY
);
1199 static HRESULT WINAPI
IDirectDrawSurface3_UpdateOverlay(
1200 LPDIRECTDRAWSURFACE3
this,
1202 LPDIRECTDRAWSURFACE3 lpDDDestSurface
,
1203 LPRECT32 lpDestRect
,
1205 LPDDOVERLAYFX lpDDOverlayFx
)
1207 FIXME(ddraw
,"(%p)->(%p,%p,%p,0x%08lx,%p),stub!\n", this,
1208 lpSrcRect
, lpDDDestSurface
, lpDestRect
, dwFlags
, lpDDOverlayFx
);
1213 static HRESULT WINAPI
IDirectDrawSurface3_UpdateOverlayDisplay(
1214 LPDIRECTDRAWSURFACE3
this,
1217 FIXME(ddraw
,"(%p)->(0x%08lx),stub!\n", this, dwFlags
);
1222 static HRESULT WINAPI
IDirectDrawSurface3_UpdateOverlayZOrder(
1223 LPDIRECTDRAWSURFACE3
this,
1225 LPDIRECTDRAWSURFACE3 lpDDSReference
)
1227 FIXME(ddraw
,"(%p)->(0x%08lx,%p),stub!\n", this, dwFlags
, lpDDSReference
);
1232 static HRESULT WINAPI
IDirectDrawSurface3_GetDDInterface(
1233 LPDIRECTDRAWSURFACE3
this,
1236 FIXME(ddraw
,"(%p)->(%p),stub!\n", this, lplpDD
);
1238 /* Not sure about that... */
1239 *lplpDD
= (void *) this->s
.ddraw
;
1244 static HRESULT WINAPI
IDirectDrawSurface3_PageLock(
1245 LPDIRECTDRAWSURFACE3
this,
1248 FIXME(ddraw
,"(%p)->(0x%08lx),stub!\n", this, dwFlags
);
1253 static HRESULT WINAPI
IDirectDrawSurface3_PageUnlock(
1254 LPDIRECTDRAWSURFACE3
this,
1257 FIXME(ddraw
,"(%p)->(0x%08lx),stub!\n", this, dwFlags
);
1262 static HRESULT WINAPI
IDirectDrawSurface3_SetSurfaceDesc(
1263 LPDIRECTDRAWSURFACE3
this,
1264 LPDDSURFACEDESC lpDDSD
,
1267 FIXME(ddraw
,"(%p)->(%p,0x%08lx),stub!\n", this, lpDDSD
, dwFlags
);
1272 static struct IDirectDrawSurface3_VTable dga_dds3vt
= {
1273 IDirectDrawSurface3_QueryInterface
,
1274 IDirectDrawSurface3_AddRef
,
1275 DGA_IDirectDrawSurface3_Release
,
1276 IDirectDrawSurface3_AddAttachedSurface
,
1277 IDirectDrawSurface3_AddOverlayDirtyRect
,
1278 IDirectDrawSurface3_Blt
,
1279 IDirectDrawSurface3_BltBatch
,
1280 IDirectDrawSurface3_BltFast
,
1281 IDirectDrawSurface3_DeleteAttachedSurface
,
1282 IDirectDrawSurface3_EnumAttachedSurfaces
,
1283 IDirectDrawSurface3_EnumOverlayZOrders
,
1284 DGA_IDirectDrawSurface3_Flip
,
1285 IDirectDrawSurface3_GetAttachedSurface
,
1286 IDirectDrawSurface3_GetBltStatus
,
1287 IDirectDrawSurface3_GetCaps
,
1288 IDirectDrawSurface3_GetClipper
,
1289 IDirectDrawSurface3_GetColorKey
,
1290 IDirectDrawSurface3_GetDC
,
1291 IDirectDrawSurface3_GetFlipStatus
,
1292 IDirectDrawSurface3_GetOverlayPosition
,
1293 IDirectDrawSurface3_GetPalette
,
1294 IDirectDrawSurface3_GetPixelFormat
,
1295 IDirectDrawSurface3_GetSurfaceDesc
,
1296 IDirectDrawSurface3_Initialize
,
1297 IDirectDrawSurface3_IsLost
,
1298 IDirectDrawSurface3_Lock
,
1299 IDirectDrawSurface3_ReleaseDC
,
1300 IDirectDrawSurface3_Restore
,
1301 IDirectDrawSurface3_SetClipper
,
1302 IDirectDrawSurface3_SetColorKey
,
1303 IDirectDrawSurface3_SetOverlayPosition
,
1304 DGA_IDirectDrawSurface3_SetPalette
,
1305 DGA_IDirectDrawSurface3_Unlock
,
1306 IDirectDrawSurface3_UpdateOverlay
,
1307 IDirectDrawSurface3_UpdateOverlayDisplay
,
1308 IDirectDrawSurface3_UpdateOverlayZOrder
,
1309 IDirectDrawSurface3_GetDDInterface
,
1310 IDirectDrawSurface3_PageLock
,
1311 IDirectDrawSurface3_PageUnlock
,
1312 IDirectDrawSurface3_SetSurfaceDesc
,
1315 static struct IDirectDrawSurface3_VTable xlib_dds3vt
= {
1316 IDirectDrawSurface3_QueryInterface
,
1317 IDirectDrawSurface3_AddRef
,
1318 Xlib_IDirectDrawSurface3_Release
,
1319 IDirectDrawSurface3_AddAttachedSurface
,
1320 IDirectDrawSurface3_AddOverlayDirtyRect
,
1321 IDirectDrawSurface3_Blt
,
1322 IDirectDrawSurface3_BltBatch
,
1323 IDirectDrawSurface3_BltFast
,
1324 IDirectDrawSurface3_DeleteAttachedSurface
,
1325 IDirectDrawSurface3_EnumAttachedSurfaces
,
1326 IDirectDrawSurface3_EnumOverlayZOrders
,
1327 Xlib_IDirectDrawSurface3_Flip
,
1328 IDirectDrawSurface3_GetAttachedSurface
,
1329 IDirectDrawSurface3_GetBltStatus
,
1330 IDirectDrawSurface3_GetCaps
,
1331 IDirectDrawSurface3_GetClipper
,
1332 IDirectDrawSurface3_GetColorKey
,
1333 IDirectDrawSurface3_GetDC
,
1334 IDirectDrawSurface3_GetFlipStatus
,
1335 IDirectDrawSurface3_GetOverlayPosition
,
1336 IDirectDrawSurface3_GetPalette
,
1337 IDirectDrawSurface3_GetPixelFormat
,
1338 IDirectDrawSurface3_GetSurfaceDesc
,
1339 IDirectDrawSurface3_Initialize
,
1340 IDirectDrawSurface3_IsLost
,
1341 IDirectDrawSurface3_Lock
,
1342 IDirectDrawSurface3_ReleaseDC
,
1343 IDirectDrawSurface3_Restore
,
1344 IDirectDrawSurface3_SetClipper
,
1345 IDirectDrawSurface3_SetColorKey
,
1346 IDirectDrawSurface3_SetOverlayPosition
,
1347 Xlib_IDirectDrawSurface3_SetPalette
,
1348 Xlib_IDirectDrawSurface3_Unlock
,
1349 IDirectDrawSurface3_UpdateOverlay
,
1350 IDirectDrawSurface3_UpdateOverlayDisplay
,
1351 IDirectDrawSurface3_UpdateOverlayZOrder
,
1352 IDirectDrawSurface3_GetDDInterface
,
1353 IDirectDrawSurface3_PageLock
,
1354 IDirectDrawSurface3_PageUnlock
,
1355 IDirectDrawSurface3_SetSurfaceDesc
,
1358 /******************************************************************************
1359 * DirectDrawCreateClipper (DDRAW.7)
1361 HRESULT WINAPI
DirectDrawCreateClipper( DWORD dwFlags
,
1362 LPDIRECTDRAWCLIPPER
*lplpDDClipper
,
1363 LPUNKNOWN pUnkOuter
)
1365 TRACE(ddraw
, "(%08lx,%p,%p)\n", dwFlags
, lplpDDClipper
, pUnkOuter
);
1367 *lplpDDClipper
= (LPDIRECTDRAWCLIPPER
)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY
,sizeof(IDirectDrawClipper
));
1368 (*lplpDDClipper
)->lpvtbl
= &ddclipvt
;
1369 (*lplpDDClipper
)->ref
= 1;
1374 /******************************************************************************
1375 * IDirectDrawClipper
1377 static HRESULT WINAPI
IDirectDrawClipper_SetHwnd(
1378 LPDIRECTDRAWCLIPPER
this,DWORD x
,HWND32 hwnd
1380 FIXME(ddraw
,"(%p)->SetHwnd(0x%08lx,0x%08lx),stub!\n",this,x
,(DWORD
)hwnd
);
1384 static ULONG WINAPI
IDirectDrawClipper_Release(LPDIRECTDRAWCLIPPER
this) {
1385 TRACE( ddraw
, "(%p)->() decrementing from %lu.\n", this, this->ref
);
1390 HeapFree(GetProcessHeap(),0,this);
1394 static HRESULT WINAPI
IDirectDrawClipper_GetClipList(
1395 LPDIRECTDRAWCLIPPER
this,LPRECT32 rects
,LPRGNDATA lprgn
,LPDWORD hmm
1397 FIXME(ddraw
,"(%p,%p,%p,%p),stub!\n",this,rects
,lprgn
,hmm
);
1402 static HRESULT WINAPI
IDirectDrawClipper_SetClipList(
1403 LPDIRECTDRAWCLIPPER
this,LPRGNDATA lprgn
,DWORD hmm
1405 FIXME(ddraw
,"(%p,%p,%ld),stub!\n",this,lprgn
,hmm
);
1409 static HRESULT WINAPI
IDirectDrawClipper_QueryInterface(
1410 LPDIRECTDRAWCLIPPER
this,
1414 FIXME(ddraw
,"(%p)->(%p,%p),stub!\n",this,riid
,ppvObj
);
1415 return OLE_E_ENUM_NOMORE
;
1418 static ULONG WINAPI
IDirectDrawClipper_AddRef( LPDIRECTDRAWCLIPPER
this )
1420 TRACE( ddraw
, "(%p)->() incrementing from %lu.\n", this, this->ref
);
1421 return ++(this->ref
);
1424 static HRESULT WINAPI
IDirectDrawClipper_GetHWnd(
1425 LPDIRECTDRAWCLIPPER
this,
1428 FIXME(ddraw
,"(%p)->(%p),stub!\n",this,HWndPtr
);
1432 static HRESULT WINAPI
IDirectDrawClipper_Initialize(
1433 LPDIRECTDRAWCLIPPER
this,
1437 FIXME(ddraw
,"(%p)->(%p,0x%08lx),stub!\n",this,lpDD
,dwFlags
);
1441 static HRESULT WINAPI
IDirectDrawClipper_IsClipListChanged(
1442 LPDIRECTDRAWCLIPPER
this,
1443 BOOL32
* lpbChanged
)
1445 FIXME(ddraw
,"(%p)->(%p),stub!\n",this,lpbChanged
);
1449 static struct IDirectDrawClipper_VTable ddclipvt
= {
1450 IDirectDrawClipper_QueryInterface
,
1451 IDirectDrawClipper_AddRef
,
1452 IDirectDrawClipper_Release
,
1453 IDirectDrawClipper_GetClipList
,
1454 IDirectDrawClipper_GetHWnd
,
1455 IDirectDrawClipper_Initialize
,
1456 IDirectDrawClipper_IsClipListChanged
,
1457 IDirectDrawClipper_SetClipList
,
1458 IDirectDrawClipper_SetHwnd
1462 /******************************************************************************
1463 * IDirectDrawPalette
1465 static HRESULT WINAPI
IDirectDrawPalette_GetEntries(
1466 LPDIRECTDRAWPALETTE
this,DWORD x
,DWORD start
,DWORD count
,LPPALETTEENTRY palent
1470 TRACE(ddraw
,"(%p)->GetEntries(%08lx,%ld,%ld,%p)\n",
1471 this,x
,start
,count
,palent
);
1473 if (!this->cm
) /* should not happen */ {
1474 FIXME(ddraw
,"app tried to read colormap for non-palettized mode\n");
1475 return DDERR_GENERIC
;
1477 for (i
=0;i
<count
;i
++) {
1478 palent
[i
].peRed
= this->palents
[start
+i
].peRed
;
1479 palent
[i
].peBlue
= this->palents
[start
+i
].peBlue
;
1480 palent
[i
].peGreen
= this->palents
[start
+i
].peGreen
;
1481 palent
[i
].peFlags
= this->palents
[start
+i
].peFlags
;
1487 static HRESULT WINAPI
Xlib_IDirectDrawPalette_SetEntries(
1488 LPDIRECTDRAWPALETTE
this,DWORD x
,DWORD start
,DWORD count
,LPPALETTEENTRY palent
1493 TRACE(ddraw
,"(%p)->SetEntries(%08lx,%ld,%ld,%p)\n",
1494 this,x
,start
,count
,palent
1496 for (i
=0;i
<count
;i
++) {
1497 xc
.red
= palent
[i
].peRed
<<8;
1498 xc
.blue
= palent
[i
].peBlue
<<8;
1499 xc
.green
= palent
[i
].peGreen
<<8;
1500 xc
.flags
= DoRed
|DoBlue
|DoGreen
;
1504 TSXStoreColor(display
,this->cm
,&xc
);
1506 this->palents
[start
+i
].peRed
= palent
[i
].peRed
;
1507 this->palents
[start
+i
].peBlue
= palent
[i
].peBlue
;
1508 this->palents
[start
+i
].peGreen
= palent
[i
].peGreen
;
1509 this->palents
[start
+i
].peFlags
= palent
[i
].peFlags
;
1511 if (!this->cm
) /* should not happen */ {
1516 static HRESULT WINAPI
DGA_IDirectDrawPalette_SetEntries(
1517 LPDIRECTDRAWPALETTE
this,DWORD x
,DWORD start
,DWORD count
,LPPALETTEENTRY palent
1519 #ifdef HAVE_LIBXXF86DGA
1524 TRACE(ddraw
,"(%p)->SetEntries(%08lx,%ld,%ld,%p)\n",
1525 this,x
,start
,count
,palent
1527 if (!this->cm
) /* should not happen */ {
1528 FIXME(ddraw
,"app tried to set colormap in non-palettized mode\n");
1529 return DDERR_GENERIC
;
1531 /* FIXME: free colorcells instead of freeing whole map */
1533 this->cm
= TSXCopyColormapAndFree(display
,this->cm
);
1534 TSXFreeColormap(display
,cm
);
1536 for (i
=0;i
<count
;i
++) {
1537 xc
.red
= palent
[i
].peRed
<<8;
1538 xc
.blue
= palent
[i
].peBlue
<<8;
1539 xc
.green
= palent
[i
].peGreen
<<8;
1540 xc
.flags
= DoRed
|DoBlue
|DoGreen
;
1543 TSXStoreColor(display
,this->cm
,&xc
);
1545 this->palents
[start
+i
].peRed
= palent
[i
].peRed
;
1546 this->palents
[start
+i
].peBlue
= palent
[i
].peBlue
;
1547 this->palents
[start
+i
].peGreen
= palent
[i
].peGreen
;
1548 this->palents
[start
+i
].peFlags
= palent
[i
].peFlags
;
1550 TSXF86DGAInstallColormap(display
,DefaultScreen(display
),this->cm
);
1552 #else /* defined(HAVE_LIBXXF86DGA) */
1553 return E_UNEXPECTED
;
1554 #endif /* defined(HAVE_LIBXXF86DGA) */
1557 static ULONG WINAPI
IDirectDrawPalette_Release(LPDIRECTDRAWPALETTE
this) {
1558 TRACE( ddraw
, "(%p)->() decrementing from %lu.\n", this, this->ref
);
1559 if (!--(this->ref
)) {
1561 TSXFreeColormap(display
,this->cm
);
1564 HeapFree(GetProcessHeap(),0,this);
1570 static ULONG WINAPI
IDirectDrawPalette_AddRef(LPDIRECTDRAWPALETTE
this) {
1572 TRACE( ddraw
, "(%p)->() incrementing from %lu.\n", this, this->ref
);
1573 return ++(this->ref
);
1576 static HRESULT WINAPI
IDirectDrawPalette_Initialize(
1577 LPDIRECTDRAWPALETTE
this,LPDIRECTDRAW ddraw
,DWORD x
,LPPALETTEENTRY palent
1579 TRACE(ddraw
,"(%p)->(%p,%ld,%p)\n", this, ddraw
, x
, palent
);
1581 return DDERR_ALREADYINITIALIZED
;
1584 static HRESULT WINAPI
IDirectDrawPalette_GetCaps(
1585 LPDIRECTDRAWPALETTE
this, LPDWORD lpdwCaps
)
1587 FIXME( ddraw
, "(%p)->(%p) stub.\n", this, lpdwCaps
);
1591 static HRESULT WINAPI
IDirectDrawPalette_QueryInterface(
1592 LPDIRECTDRAWPALETTE
this,REFIID refiid
,LPVOID
*obj
)
1596 WINE_StringFromCLSID((LPCLSID
)refiid
,xrefiid
);
1597 FIXME(ddraw
,"(%p)->(%s,%p) stub.\n",this,xrefiid
,obj
);
1602 static struct IDirectDrawPalette_VTable dga_ddpalvt
= {
1603 IDirectDrawPalette_QueryInterface
,
1604 IDirectDrawPalette_AddRef
,
1605 IDirectDrawPalette_Release
,
1606 IDirectDrawPalette_GetCaps
,
1607 IDirectDrawPalette_GetEntries
,
1608 IDirectDrawPalette_Initialize
,
1609 DGA_IDirectDrawPalette_SetEntries
1612 static struct IDirectDrawPalette_VTable xlib_ddpalvt
= {
1613 IDirectDrawPalette_QueryInterface
,
1614 IDirectDrawPalette_AddRef
,
1615 IDirectDrawPalette_Release
,
1616 IDirectDrawPalette_GetCaps
,
1617 IDirectDrawPalette_GetEntries
,
1618 IDirectDrawPalette_Initialize
,
1619 Xlib_IDirectDrawPalette_SetEntries
1622 /*******************************************************************************
1625 static HRESULT WINAPI
IDirect3D_QueryInterface(
1626 LPDIRECT3D
this,REFIID refiid
,LPVOID
*obj
1628 /* FIXME: Not sure if this is correct */
1631 WINE_StringFromCLSID((LPCLSID
)refiid
,xrefiid
);
1632 TRACE(ddraw
,"(%p)->(%s,%p)\n",this,xrefiid
,obj
);
1633 if (!memcmp(&IID_IUnknown
,refiid
,sizeof(IID_IUnknown
))) {
1635 this->lpvtbl
->fnAddRef(this);
1637 TRACE(ddraw
, " Creating IUnknown interface (%p)\n", *obj
);
1641 if (!memcmp(&IID_IDirect3D
,refiid
,sizeof(IID_IDirect3D
))) {
1644 d3d
= HeapAlloc(GetProcessHeap(),0,sizeof(*d3d
));
1646 d3d
->ddraw
= (LPDIRECTDRAW
)this;
1647 this->lpvtbl
->fnAddRef(this);
1648 d3d
->lpvtbl
= &d3dvt
;
1651 TRACE(ddraw
, " Creating IDirect3D interface (%p)\n", *obj
);
1655 if (!memcmp(&IID_IDirect3D2
,refiid
,sizeof(IID_IDirect3D
))) {
1658 d3d
= HeapAlloc(GetProcessHeap(),0,sizeof(*d3d
));
1660 d3d
->ddraw
= (LPDIRECTDRAW
)this;
1661 this->lpvtbl
->fnAddRef(this);
1662 d3d
->lpvtbl
= &d3d2vt
;
1665 TRACE(ddraw
, " Creating IDirect3D2 interface (%p)\n", *obj
);
1669 FIXME(ddraw
,"(%p):interface for IID %s NOT found!\n",this,xrefiid
);
1670 return OLE_E_ENUM_NOMORE
;
1673 static ULONG WINAPI
IDirect3D_AddRef(LPDIRECT3D
this) {
1674 TRACE( ddraw
, "(%p)->() incrementing from %lu.\n", this, this->ref
);
1676 return ++(this->ref
);
1679 static ULONG WINAPI
IDirect3D_Release(LPDIRECT3D
this)
1681 TRACE( ddraw
, "(%p)->() decrementing from %lu.\n", this, this->ref
);
1683 if (!--(this->ref
)) {
1684 this->ddraw
->lpvtbl
->fnRelease(this->ddraw
);
1685 HeapFree(GetProcessHeap(),0,this);
1691 static HRESULT WINAPI
IDirect3D_Initialize(
1692 LPDIRECT3D
this, REFIID refiid
)
1694 /* FIXME: Not sure if this is correct */
1697 WINE_StringFromCLSID((LPCLSID
)refiid
,xrefiid
);
1698 FIXME(ddraw
,"(%p)->(%s):stub.\n",this,xrefiid
);
1700 return DDERR_ALREADYINITIALIZED
;
1703 static HRESULT WINAPI
IDirect3D_EnumDevices(LPDIRECT3D
this,
1704 LPD3DENUMDEVICESCALLBACK cb
,
1706 FIXME(ddraw
,"(%p)->(%p,%p),stub!\n",this,cb
,context
);
1708 /* Call functions defined in d3ddevices.c */
1709 if (d3d_OpenGL_dx3(cb
, context
))
1715 static HRESULT WINAPI
IDirect3D_CreateLight(LPDIRECT3D
this,
1716 LPDIRECT3DLIGHT
*lplight
,
1719 TRACE(ddraw
, "(%p)->(%p,%p): stub\n", this, lplight
, lpunk
);
1721 /* Call the creation function that is located in d3dlight.c */
1722 *lplight
= d3dlight_create_dx3(this);
1727 static HRESULT WINAPI
IDirect3D_CreateMaterial(LPDIRECT3D
this,
1728 LPDIRECT3DMATERIAL
*lpmaterial
,
1731 TRACE(ddraw
, "(%p)->(%p,%p): stub\n", this, lpmaterial
, lpunk
);
1733 /* Call the creation function that is located in d3dviewport.c */
1734 *lpmaterial
= d3dmaterial_create(this);
1739 static HRESULT WINAPI
IDirect3D_CreateViewport(LPDIRECT3D
this,
1740 LPDIRECT3DVIEWPORT
*lpviewport
,
1743 TRACE(ddraw
, "(%p)->(%p,%p): stub\n", this, lpviewport
, lpunk
);
1745 /* Call the creation function that is located in d3dviewport.c */
1746 *lpviewport
= d3dviewport_create(this);
1751 static HRESULT WINAPI
IDirect3D_FindDevice(LPDIRECT3D
this,
1752 LPD3DFINDDEVICESEARCH lpfinddevsrc
,
1753 LPD3DFINDDEVICERESULT lpfinddevrst
)
1755 TRACE(ddraw
, "(%p)->(%p,%p): stub\n", this, lpfinddevsrc
, lpfinddevrst
);
1760 static struct IDirect3D_VTable d3dvt
= {
1761 IDirect3D_QueryInterface
,
1764 IDirect3D_Initialize
,
1765 IDirect3D_EnumDevices
,
1766 IDirect3D_CreateLight
,
1767 IDirect3D_CreateMaterial
,
1768 IDirect3D_CreateViewport
,
1769 IDirect3D_FindDevice
1772 /*******************************************************************************
1775 static HRESULT WINAPI
IDirect3D2_QueryInterface(
1776 LPDIRECT3D2
this,REFIID refiid
,LPVOID
*obj
) {
1777 /* For the moment, we use the same function as in IDirect3D */
1778 TRACE(ddraw
, "Calling IDirect3D enumerating function.\n");
1780 return IDirect3D_QueryInterface((LPDIRECT3D
) this, refiid
, obj
);
1783 static ULONG WINAPI
IDirect3D2_AddRef(LPDIRECT3D2
this) {
1784 TRACE( ddraw
, "(%p)->() incrementing from %lu.\n", this, this->ref
);
1786 return ++(this->ref
);
1789 static ULONG WINAPI
IDirect3D2_Release(LPDIRECT3D2
this) {
1790 TRACE( ddraw
, "(%p)->() decrementing from %lu.\n", this, this->ref
);
1792 if (!--(this->ref
)) {
1793 this->ddraw
->lpvtbl
->fnRelease(this->ddraw
);
1794 HeapFree(GetProcessHeap(),0,this);
1800 static HRESULT WINAPI
IDirect3D2_EnumDevices(
1801 LPDIRECT3D2
this,LPD3DENUMDEVICESCALLBACK cb
, LPVOID context
1803 FIXME(ddraw
,"(%p)->(%p,%p),stub!\n",this,cb
,context
);
1805 /* Call functions defined in d3ddevices.c */
1806 if (d3d_OpenGL(cb
, context
))
1812 static HRESULT WINAPI
IDirect3D2_CreateLight(LPDIRECT3D2
this,
1813 LPDIRECT3DLIGHT
*lplight
,
1816 TRACE(ddraw
, "(%p)->(%p,%p): stub\n", this, lplight
, lpunk
);
1818 /* Call the creation function that is located in d3dlight.c */
1819 *lplight
= d3dlight_create(this);
1824 static HRESULT WINAPI
IDirect3D2_CreateMaterial(LPDIRECT3D2
this,
1825 LPDIRECT3DMATERIAL2
*lpmaterial
,
1828 TRACE(ddraw
, "(%p)->(%p,%p): stub\n", this, lpmaterial
, lpunk
);
1830 /* Call the creation function that is located in d3dviewport.c */
1831 *lpmaterial
= d3dmaterial2_create(this);
1836 static HRESULT WINAPI
IDirect3D2_CreateViewport(LPDIRECT3D2
this,
1837 LPDIRECT3DVIEWPORT2
*lpviewport
,
1840 TRACE(ddraw
, "(%p)->(%p,%p): stub\n", this, lpviewport
, lpunk
);
1842 /* Call the creation function that is located in d3dviewport.c */
1843 *lpviewport
= d3dviewport2_create(this);
1848 static HRESULT WINAPI
IDirect3D2_FindDevice(LPDIRECT3D2
this,
1849 LPD3DFINDDEVICESEARCH lpfinddevsrc
,
1850 LPD3DFINDDEVICERESULT lpfinddevrst
)
1852 TRACE(ddraw
, "(%p)->(%p,%p): stub\n", this, lpfinddevsrc
, lpfinddevrst
);
1857 static HRESULT WINAPI
IDirect3D2_CreateDevice(LPDIRECT3D2
this,
1859 LPDIRECTDRAWSURFACE surface
,
1860 LPDIRECT3DDEVICE2
*device
)
1864 WINE_StringFromCLSID(rguid
,xbuf
);
1865 FIXME(ddraw
,"(%p)->(%s,%p,%p): stub\n",this,xbuf
,surface
,device
);
1867 if (is_OpenGL(rguid
, surface
, device
, this)) {
1868 this->lpvtbl
->fnAddRef(this);
1872 return DDERR_INVALIDPARAMS
;
1875 static struct IDirect3D2_VTable d3d2vt
= {
1876 IDirect3D2_QueryInterface
,
1879 IDirect3D2_EnumDevices
,
1880 IDirect3D2_CreateLight
,
1881 IDirect3D2_CreateMaterial
,
1882 IDirect3D2_CreateViewport
,
1883 IDirect3D2_FindDevice
,
1884 IDirect3D2_CreateDevice
1887 /*******************************************************************************
1891 /* Used in conjunction with cbWndExtra for storage of the this ptr for the window.
1892 * Please adjust allocation in Xlib_DirectDrawCreate if you store more data here.
1894 static INT32 ddrawXlibThisOffset
= 0;
1896 static HRESULT
common_off_screen_CreateSurface(LPDIRECTDRAW2
this,
1897 LPDDSURFACEDESC lpddsd
,
1898 LPDIRECTDRAWSURFACE lpdsf
)
1902 /* The surface was already allocated when entering in this function */
1903 TRACE(ddraw
,"using system memory for a surface (%p)\n", lpdsf
);
1905 if (lpddsd
->dwFlags
& DDSD_ZBUFFERBITDEPTH
) {
1906 /* This is a Z Buffer */
1907 bpp
= lpddsd
->x
.dwZBufferBitDepth
;
1909 /* This is a standard image */
1910 if (!(lpddsd
->dwFlags
& DDSD_PIXELFORMAT
)) {
1911 /* No pixel format => use DirectDraw's format */
1912 _getpixelformat(this,&(lpddsd
->ddpfPixelFormat
));
1913 lpddsd
->dwFlags
|= DDSD_PIXELFORMAT
;
1915 /* To check what the program wants */
1916 if (TRACE_ON(ddraw
)) {
1917 _dump_pixelformat(&(lpddsd
->ddpfPixelFormat
));
1922 if (lpddsd
->ddpfPixelFormat
.dwFlags
& DDPF_PALETTEINDEXED8
) {
1925 bpp
= lpddsd
->ddpfPixelFormat
.x
.dwRGBBitCount
/ 8;
1928 /* Copy the surface description */
1929 lpdsf
->s
.surface_desc
= *lpddsd
;
1931 lpdsf
->s
.surface_desc
.dwFlags
|= DDSD_WIDTH
|DDSD_HEIGHT
|DDSD_PITCH
|DDSD_LPSURFACE
;
1932 lpdsf
->s
.surface_desc
.y
.lpSurface
= (LPBYTE
)HeapAlloc(GetProcessHeap(),0,lpddsd
->dwWidth
* lpddsd
->dwHeight
* bpp
);
1933 lpdsf
->s
.surface_desc
.lPitch
= lpddsd
->dwWidth
* bpp
;
1938 static HRESULT WINAPI
DGA_IDirectDraw2_CreateSurface(
1939 LPDIRECTDRAW2
this,LPDDSURFACEDESC lpddsd
,LPDIRECTDRAWSURFACE
*lpdsf
,IUnknown
*lpunk
1941 #ifdef HAVE_LIBXXF86DGA
1944 TRACE(ddraw
, "(%p)->(%p,%p,%p)\n",this,lpddsd
,lpdsf
,lpunk
);
1945 if (TRACE_ON(ddraw
)) {
1946 DUMP("[w=%ld,h=%ld,flags ",lpddsd
->dwWidth
,lpddsd
->dwHeight
);
1947 _dump_DDSD(lpddsd
->dwFlags
);
1948 fprintf(stderr
,"caps ");
1949 _dump_DDSCAPS(lpddsd
->ddsCaps
.dwCaps
);
1950 fprintf(stderr
,"]\n");
1953 *lpdsf
= (LPDIRECTDRAWSURFACE
)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY
,sizeof(IDirectDrawSurface
));
1954 this->lpvtbl
->fnAddRef(this);
1957 (*lpdsf
)->lpvtbl
= (LPDIRECTDRAWSURFACE_VTABLE
)&dga_dds3vt
;
1958 (*lpdsf
)->s
.ddraw
= this;
1959 (*lpdsf
)->s
.palette
= NULL
;
1960 (*lpdsf
)->t
.dga
.fb_height
= -1; /* This is to have non-on screen surfaces freed */
1962 if (!(lpddsd
->dwFlags
& DDSD_WIDTH
))
1963 lpddsd
->dwWidth
= this->d
.width
;
1964 if (!(lpddsd
->dwFlags
& DDSD_HEIGHT
))
1965 lpddsd
->dwHeight
= this->d
.height
;
1967 /* Check if this a 'primary surface' or not */
1968 if ((lpddsd
->dwFlags
& DDSD_CAPS
) &&
1969 (lpddsd
->ddsCaps
.dwCaps
& DDSCAPS_PRIMARYSURFACE
)) {
1971 /* This is THE primary surface => there is DGA-specific code */
1972 /* First, store the surface description */
1973 (*lpdsf
)->s
.surface_desc
= *lpddsd
;
1975 /* Find a viewport */
1977 if (!(this->e
.dga
.vpmask
& (1<<i
)))
1979 TRACE(ddraw
,"using viewport %d for a primary surface\n",i
);
1980 /* if i == 32 or maximum ... return error */
1981 this->e
.dga
.vpmask
|=(1<<i
);
1982 (*lpdsf
)->s
.surface_desc
.y
.lpSurface
=
1983 this->e
.dga
.fb_addr
+((i
*this->e
.dga
.fb_height
)*this->e
.dga
.fb_width
*this->d
.depth
/8);
1984 (*lpdsf
)->t
.dga
.fb_height
= i
*this->e
.dga
.fb_height
;
1985 (*lpdsf
)->s
.surface_desc
.lPitch
= this->e
.dga
.fb_width
*this->d
.depth
/8;
1986 lpddsd
->lPitch
= (*lpdsf
)->s
.surface_desc
.lPitch
;
1988 /* Add flags if there were not present */
1989 (*lpdsf
)->s
.surface_desc
.dwFlags
|= DDSD_WIDTH
|DDSD_HEIGHT
|DDSD_PITCH
|DDSD_LPSURFACE
;
1990 (*lpdsf
)->s
.surface_desc
.dwWidth
= this->d
.width
;
1991 (*lpdsf
)->s
.surface_desc
.dwHeight
= this->d
.height
;
1992 (*lpdsf
)->s
.surface_desc
.ddsCaps
.dwCaps
|= DDSCAPS_VISIBLE
;
1993 _getpixelformat(this,&((*lpdsf
)->s
.surface_desc
.ddpfPixelFormat
));
1994 (*lpdsf
)->s
.backbuffer
= NULL
;
1996 if (lpddsd
->dwFlags
& DDSD_BACKBUFFERCOUNT
) {
1997 LPDIRECTDRAWSURFACE3 back
;
1999 if (lpddsd
->dwBackBufferCount
>1)
2000 FIXME(ddraw
,"urks, wants to have more than one backbuffer (%ld)!\n",lpddsd
->dwBackBufferCount
);
2002 (*lpdsf
)->s
.backbuffer
= back
=
2003 (LPDIRECTDRAWSURFACE3
)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY
,sizeof(IDirectDrawSurface3
));
2004 this->lpvtbl
->fnAddRef(this);
2006 back
->lpvtbl
= (LPDIRECTDRAWSURFACE3_VTABLE
)&dga_dds3vt
;
2008 if (!(this->e
.dga
.vpmask
& (1<<i
)))
2010 TRACE(ddraw
,"using viewport %d for backbuffer\n",i
);
2011 /* if i == 32 or maximum ... return error */
2012 this->e
.dga
.vpmask
|=(1<<i
);
2013 back
->t
.dga
.fb_height
= i
*this->e
.dga
.fb_height
;
2015 /* Copy the surface description from the front buffer */
2016 back
->s
.surface_desc
= (*lpdsf
)->s
.surface_desc
;
2017 /* Change the parameters that are not the same */
2018 back
->s
.surface_desc
.y
.lpSurface
= this->e
.dga
.fb_addr
+
2019 ((i
*this->e
.dga
.fb_height
)*this->e
.dga
.fb_width
*this->d
.depth
/8);
2020 back
->s
.ddraw
= this;
2021 back
->s
.backbuffer
= NULL
; /* does not have a backbuffer, it is
2024 /* Add relevant info to front and back buffers */
2025 (*lpdsf
)->s
.surface_desc
.ddsCaps
.dwCaps
|= DDSCAPS_FRONTBUFFER
;
2026 back
->s
.surface_desc
.ddsCaps
.dwCaps
|= DDSCAPS_BACKBUFFER
;
2027 back
->s
.surface_desc
.dwFlags
&= ~DDSD_BACKBUFFERCOUNT
;
2028 back
->s
.surface_desc
.ddsCaps
.dwCaps
&= ~DDSCAPS_VISIBLE
;
2031 /* There is no DGA-specific code here...
2032 Go to the common surface creation function */
2033 return common_off_screen_CreateSurface(this, lpddsd
, *lpdsf
);
2037 #else /* defined(HAVE_LIBXXF86DGA) */
2038 return E_UNEXPECTED
;
2039 #endif /* defined(HAVE_LIBXXF86DGA) */
2042 static XImage
*create_ximage(LPDIRECTDRAW2
this, LPDIRECTDRAWSURFACE3 lpdsf
) {
2045 #ifdef HAVE_LIBXXSHM
2046 if (this->e
.xlib
.xshm_active
) {
2047 img
= TSXShmCreateImage(display
,
2048 DefaultVisualOfScreen(screen
),
2052 &(lpdsf
->t
.xlib
.shminfo
),
2053 lpdsf
->s
.surface_desc
.dwWidth
,
2054 lpdsf
->s
.surface_desc
.dwHeight
);
2059 lpdsf
->t
.xlib
.shminfo
.shmid
= shmget( IPC_PRIVATE
, img
->bytes_per_line
* img
->height
, IPC_CREAT
|0777 );
2060 if (lpdsf
->t
.xlib
.shminfo
.shmid
< 0) {
2061 TSXDestroyImage(img
);
2065 lpdsf
->t
.xlib
.shminfo
.shmaddr
= img
->data
= (char*)shmat(lpdsf
->t
.xlib
.shminfo
.shmid
, 0, 0);
2067 if (img
->data
== (char *) -1) {
2068 TSXDestroyImage(img
);
2069 shmctl(lpdsf
->t
.xlib
.shminfo
.shmid
, IPC_RMID
, 0);
2072 lpdsf
->t
.xlib
.shminfo
.readOnly
= False
;
2074 TSXShmAttach(display
, &(lpdsf
->t
.xlib
.shminfo
));
2075 TSXSync(display
, False
);
2077 shmctl(lpdsf
->t
.xlib
.shminfo
.shmid
, IPC_RMID
, 0);
2079 lpdsf
->s
.surface_desc
.y
.lpSurface
= img
->data
;
2082 /* Allocate surface memory */
2083 lpdsf
->s
.surface_desc
.y
.lpSurface
= HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY
,
2084 lpdsf
->s
.surface_desc
.dwWidth
*
2085 lpdsf
->s
.surface_desc
.dwHeight
*
2086 (this->d
.depth
/ 8));
2088 /* In this case, create an XImage */
2090 TSXCreateImage(display
,
2091 DefaultVisualOfScreen(screen
),
2095 lpdsf
->s
.surface_desc
.y
.lpSurface
,
2096 lpdsf
->s
.surface_desc
.dwWidth
,
2097 lpdsf
->s
.surface_desc
.dwHeight
,
2099 lpdsf
->s
.surface_desc
.dwWidth
* (this->d
.depth
/ 8)
2102 #ifdef HAVE_LIBXXSHM
2105 lpdsf
->s
.surface_desc
.lPitch
= img
->bytes_per_line
;
2110 static HRESULT WINAPI
Xlib_IDirectDraw2_CreateSurface(
2111 LPDIRECTDRAW2
this,LPDDSURFACEDESC lpddsd
,LPDIRECTDRAWSURFACE
*lpdsf
,IUnknown
*lpunk
2113 TRACE(ddraw
, "(%p)->CreateSurface(%p,%p,%p)\n",
2114 this,lpddsd
,lpdsf
,lpunk
);
2116 if (TRACE_ON(ddraw
)) {
2117 fprintf(stderr
,"[w=%ld,h=%ld,flags ",lpddsd
->dwWidth
,lpddsd
->dwHeight
);
2118 _dump_DDSD(lpddsd
->dwFlags
);
2119 fprintf(stderr
,"caps ");
2120 _dump_DDSCAPS(lpddsd
->ddsCaps
.dwCaps
);
2121 fprintf(stderr
,"]\n");
2124 *lpdsf
= (LPDIRECTDRAWSURFACE
)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY
,sizeof(IDirectDrawSurface
));
2126 this->lpvtbl
->fnAddRef(this);
2127 (*lpdsf
)->s
.ddraw
= this;
2129 (*lpdsf
)->lpvtbl
= (LPDIRECTDRAWSURFACE_VTABLE
)&xlib_dds3vt
;
2130 (*lpdsf
)->s
.palette
= NULL
;
2131 (*lpdsf
)->t
.xlib
.image
= NULL
; /* This is for off-screen buffers */
2133 if (!(lpddsd
->dwFlags
& DDSD_WIDTH
))
2134 lpddsd
->dwWidth
= this->d
.width
;
2135 if (!(lpddsd
->dwFlags
& DDSD_HEIGHT
))
2136 lpddsd
->dwHeight
= this->d
.height
;
2138 /* Check if this a 'primary surface' or not */
2139 if ((lpddsd
->dwFlags
& DDSD_CAPS
) &&
2140 (lpddsd
->ddsCaps
.dwCaps
& DDSCAPS_PRIMARYSURFACE
)) {
2143 TRACE(ddraw
,"using standard XImage for a primary surface (%p)\n", *lpdsf
);
2145 /* First, store the surface description */
2146 (*lpdsf
)->s
.surface_desc
= *lpddsd
;
2148 /* Create the XImage */
2149 img
= create_ximage(this, (LPDIRECTDRAWSURFACE3
) *lpdsf
);
2151 return DDERR_OUTOFMEMORY
;
2152 (*lpdsf
)->t
.xlib
.image
= img
;
2154 /* Add flags if there were not present */
2155 (*lpdsf
)->s
.surface_desc
.dwFlags
|= DDSD_WIDTH
|DDSD_HEIGHT
|DDSD_PITCH
|DDSD_LPSURFACE
;
2156 (*lpdsf
)->s
.surface_desc
.dwWidth
= this->d
.width
;
2157 (*lpdsf
)->s
.surface_desc
.dwHeight
= this->d
.height
;
2158 (*lpdsf
)->s
.surface_desc
.ddsCaps
.dwCaps
|= DDSCAPS_VISIBLE
;
2159 _getpixelformat(this,&((*lpdsf
)->s
.surface_desc
.ddpfPixelFormat
));
2160 (*lpdsf
)->s
.backbuffer
= NULL
;
2162 /* Check for backbuffers */
2163 if (lpddsd
->dwFlags
& DDSD_BACKBUFFERCOUNT
) {
2164 LPDIRECTDRAWSURFACE3 back
;
2167 if (lpddsd
->dwBackBufferCount
>1)
2168 FIXME(ddraw
,"urks, wants to have more than one backbuffer (%ld)!\n",lpddsd
->dwBackBufferCount
);
2170 (*lpdsf
)->s
.backbuffer
= back
=
2171 (LPDIRECTDRAWSURFACE3
)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY
,sizeof(IDirectDrawSurface3
));
2173 TRACE(ddraw
,"allocated back-buffer (%p)\n", back
);
2175 this->lpvtbl
->fnAddRef(this);
2176 back
->s
.ddraw
= this;
2179 back
->lpvtbl
= (LPDIRECTDRAWSURFACE3_VTABLE
)&xlib_dds3vt
;
2180 /* Copy the surface description from the front buffer */
2181 back
->s
.surface_desc
= (*lpdsf
)->s
.surface_desc
;
2183 /* Create the XImage */
2184 img
= create_ximage(this, back
);
2186 return DDERR_OUTOFMEMORY
;
2187 back
->t
.xlib
.image
= img
;
2189 back
->s
.backbuffer
= NULL
; /* does not have a backbuffer, it is
2192 /* Add relevant info to front and back buffers */
2193 (*lpdsf
)->s
.surface_desc
.ddsCaps
.dwCaps
|= DDSCAPS_FRONTBUFFER
;
2194 back
->s
.surface_desc
.ddsCaps
.dwCaps
|= DDSCAPS_BACKBUFFER
;
2195 back
->s
.surface_desc
.dwFlags
&= ~DDSD_BACKBUFFERCOUNT
;
2196 back
->s
.surface_desc
.ddsCaps
.dwCaps
&= ~DDSCAPS_VISIBLE
;
2199 /* There is no Xlib-specific code here...
2200 Go to the common surface creation function */
2201 return common_off_screen_CreateSurface(this, lpddsd
, *lpdsf
);
2207 static HRESULT WINAPI
IDirectDraw2_DuplicateSurface(
2208 LPDIRECTDRAW2
this,LPDIRECTDRAWSURFACE src
,LPDIRECTDRAWSURFACE
*dst
2210 FIXME(ddraw
,"(%p)->(%p,%p) simply copies\n",this,src
,dst
);
2211 *dst
= src
; /* FIXME */
2216 * The Xlib Implementation tries to use the passed hwnd as drawing window,
2217 * even when the approbiate bitmasks are not specified.
2219 static HRESULT WINAPI
IDirectDraw2_SetCooperativeLevel(
2220 LPDIRECTDRAW2
this,HWND32 hwnd
,DWORD cooplevel
2227 FE(DDSCL_FULLSCREEN
)
2228 FE(DDSCL_ALLOWREBOOT
)
2229 FE(DDSCL_NOWINDOWCHANGES
)
2231 FE(DDSCL_ALLOWMODEX
)
2233 FE(DDSCL_SETFOCUSWINDOW
)
2234 FE(DDSCL_SETDEVICEWINDOW
)
2235 FE(DDSCL_CREATEDEVICEWINDOW
)
2238 FIXME(ddraw
,"(%p)->(%08lx,%08lx)\n",this,(DWORD
)hwnd
,cooplevel
);
2239 if(TRACE_ON(ddraw
)){
2240 dbg_decl_str(ddraw
, 512);
2241 for (i
=0;i
<sizeof(flagmap
)/sizeof(flagmap
[0]);i
++)
2242 if (flagmap
[i
].mask
& cooplevel
)
2243 dsprintf(ddraw
, "%s ", flagmap
[i
].name
);
2244 TRACE(ddraw
," cooperative level %s\n", dbg_str(ddraw
));
2246 this->d
.mainWindow
= hwnd
;
2248 /* This will be overwritten in the case of Full Screen mode.
2249 Windowed games could work with that :-) */
2250 this->e
.xlib
.drawable
= ((X11DRV_WND_DATA
*) WIN_FindWndPtr(hwnd
)->pDriverData
)->window
;
2255 /* Small helper to either use the cooperative window or create a new
2256 * one (for mouse and keyboard input) and drawing in the Xlib implementation.
2258 static void _common_IDirectDraw_SetDisplayMode(LPDIRECTDRAW
this) {
2261 /* Do not destroy the application supplied cooperative window */
2262 if (this->d
.window
&& this->d
.window
!= this->d
.mainWindow
) {
2263 DestroyWindow32(this->d
.window
);
2266 /* Sanity check cooperative window before assigning it to drawing. */
2267 if ( IsWindow32(this->d
.mainWindow
) &&
2268 IsWindowVisible32(this->d
.mainWindow
)
2270 GetWindowRect32(this->d
.mainWindow
,&rect
);
2271 if (((rect
.right
-rect
.left
) >= this->d
.width
) &&
2272 ((rect
.bottom
-rect
.top
) >= this->d
.height
)
2274 this->d
.window
= this->d
.mainWindow
;
2276 /* ... failed, create new one. */
2277 if (!this->d
.window
) {
2278 this->d
.window
= CreateWindowEx32A(
2282 WS_VISIBLE
|WS_SYSMENU
|WS_THICKFRAME
,
2291 /*Store THIS with the window. We'll use it in the window procedure*/
2292 SetWindowLong32A(this->d
.window
,ddrawXlibThisOffset
,(LONG
)this);
2293 ShowWindow32(this->d
.window
,TRUE
);
2294 UpdateWindow32(this->d
.window
);
2296 SetFocus32(this->d
.window
);
2299 static HRESULT WINAPI
DGA_IDirectDraw_SetDisplayMode(
2300 LPDIRECTDRAW
this,DWORD width
,DWORD height
,DWORD depth
2302 #ifdef HAVE_LIBXXF86DGA
2303 int i
,*depths
,depcount
,mode_count
;
2305 TRACE(ddraw
, "(%p)->(%ld,%ld,%ld)\n", this, width
, height
, depth
);
2307 depths
= TSXListDepths(display
,DefaultScreen(display
),&depcount
);
2308 for (i
=0;i
<depcount
;i
++)
2309 if (depths
[i
]==depth
)
2312 if (i
==depcount
) {/* not found */
2313 ERR(ddraw
,"(w=%ld,h=%ld,d=%ld), unsupported depth!\n",width
,height
,depth
);
2314 return DDERR_UNSUPPORTEDMODE
;
2316 if (this->d
.width
< width
) {
2317 ERR(ddraw
,"SetDisplayMode(w=%ld,h=%ld,d=%ld), width %ld exceeds framebuffer width %ld\n",width
,height
,depth
,width
,this->d
.width
);
2318 return DDERR_UNSUPPORTEDMODE
;
2320 this->d
.width
= width
;
2321 this->d
.height
= height
;
2322 this->d
.depth
= depth
;
2324 /* adjust fb_height, so we don't overlap */
2325 if (this->e
.dga
.fb_height
< height
)
2326 this->e
.dga
.fb_height
= height
;
2327 _common_IDirectDraw_SetDisplayMode(this);
2329 #ifdef HAVE_LIBXXF86VM
2331 XF86VidModeModeInfo
**all_modes
, *vidmode
= NULL
;
2332 XF86VidModeModeLine mod_tmp
;
2335 /* save original video mode and set fullscreen if available*/
2336 orig_mode
= (XF86VidModeModeInfo
*) malloc (sizeof(XF86VidModeModeInfo
));
2337 TSXF86VidModeGetModeLine(display
, DefaultScreen(display
), &orig_mode
->dotclock
, &mod_tmp
);
2338 orig_mode
->hdisplay
= mod_tmp
.hdisplay
;
2339 orig_mode
->hsyncstart
= mod_tmp
.hsyncstart
;
2340 orig_mode
->hsyncend
= mod_tmp
.hsyncend
;
2341 orig_mode
->htotal
= mod_tmp
.htotal
;
2342 orig_mode
->vdisplay
= mod_tmp
.vdisplay
;
2343 orig_mode
->vsyncstart
= mod_tmp
.vsyncstart
;
2344 orig_mode
->vsyncend
= mod_tmp
.vsyncend
;
2345 orig_mode
->vtotal
= mod_tmp
.vtotal
;
2346 orig_mode
->flags
= mod_tmp
.flags
;
2347 orig_mode
->private = mod_tmp
.private;
2349 TSXF86VidModeGetAllModeLines(display
,DefaultScreen(display
),&mode_count
,&all_modes
);
2350 for (i
=0;i
<mode_count
;i
++)
2352 if (all_modes
[i
]->hdisplay
== width
&& all_modes
[i
]->vdisplay
== height
)
2354 vidmode
= (XF86VidModeModeInfo
*)malloc(sizeof(XF86VidModeModeInfo
));
2355 *vidmode
= *(all_modes
[i
]);
2358 TSXFree(all_modes
[i
]->private);
2363 WARN(ddraw
, "Fullscreen mode not available!\n");
2367 TSXF86VidModeSwitchToMode(display
, DefaultScreen(display
), vidmode
);
2368 TSXF86VidModeSetViewPort(display
, DefaultScreen(display
), 0, 0);
2373 /* FIXME: this function OVERWRITES several signal handlers.
2374 * can we save them? and restore them later? In a way that
2375 * it works for the library too?
2377 TSXF86DGADirectVideo(display
,DefaultScreen(display
),XF86DGADirectGraphics
);
2379 TSXF86DGASetViewPort(display
,DefaultScreen(display
),0,this->e
.dga
.fb_height
);
2382 #ifdef RESTORE_SIGNALS
2383 SIGNAL_InitEmulator();
2386 #else /* defined(HAVE_LIBXXF86DGA) */
2387 return E_UNEXPECTED
;
2388 #endif /* defined(HAVE_LIBXXF86DGA) */
2391 static HRESULT WINAPI
Xlib_IDirectDraw_SetDisplayMode(
2392 LPDIRECTDRAW
this,DWORD width
,DWORD height
,DWORD depth
2394 int i
,*depths
,depcount
;
2397 TRACE(ddraw
, "(%p)->SetDisplayMode(%ld,%ld,%ld)\n",
2398 this, width
, height
, depth
);
2400 depths
= TSXListDepths(display
,DefaultScreen(display
),&depcount
);
2401 for (i
=0;i
<depcount
;i
++)
2402 if (depths
[i
]==depth
)
2405 if (i
==depcount
) {/* not found */
2406 sprintf(buf
,"SetDisplayMode(w=%ld,h=%ld,d=%ld), unsupported depth!",width
,height
,depth
);
2407 MessageBox32A(0,buf
,"WINE DirectDraw",MB_OK
|MB_ICONSTOP
);
2408 return DDERR_UNSUPPORTEDMODE
;
2410 this->d
.width
= width
;
2411 this->d
.height
= height
;
2412 this->d
.depth
= depth
;
2414 _common_IDirectDraw_SetDisplayMode(this);
2416 this->e
.xlib
.paintable
= 1;
2417 this->e
.xlib
.drawable
= ((X11DRV_WND_DATA
*) WIN_FindWndPtr(this->d
.window
)->pDriverData
)->window
;
2418 /* We don't have a context for this window. Host off the desktop */
2419 if( !this->e
.xlib
.drawable
)
2420 this->e
.xlib
.drawable
= ((X11DRV_WND_DATA
*) WIN_GetDesktop()->pDriverData
)->window
;
2424 static HRESULT WINAPI
DGA_IDirectDraw2_GetCaps(
2425 LPDIRECTDRAW2
this,LPDDCAPS caps1
,LPDDCAPS caps2
2427 #ifdef HAVE_LIBXXF86DGA
2428 TRACE(ddraw
,"(%p)->GetCaps(%p,%p)\n",this,caps1
,caps2
);
2429 caps1
->dwVidMemTotal
= this->e
.dga
.fb_memsize
;
2430 caps1
->dwCaps
= 0xffffffff&~(DDCAPS_BANKSWITCHED
); /* we can do anything */
2431 caps1
->ddsCaps
.dwCaps
= 0xffffffff; /* we can do anything */
2433 caps2
->dwVidMemTotal
= this->e
.dga
.fb_memsize
;
2434 caps2
->dwCaps
= 0xffffffff&~(DDCAPS_BANKSWITCHED
); /* we can do anything */
2435 caps2
->ddsCaps
.dwCaps
= 0xffffffff; /* we can do anything */
2438 #else /* defined(HAVE_LIBXXF86DGA) */
2439 return E_UNEXPECTED
;
2440 #endif /* defined(HAVE_LIBXXF86DGA) */
2443 static void fill_caps(LPDDCAPS caps
) {
2444 /* This function tries to fill the capabilities of Wine's DDraw implementation.
2445 Need to be fixed, though.. */
2449 caps
->dwSize
= sizeof(*caps
);
2450 caps
->dwCaps
= DDCAPS_3D
| DDCAPS_ALPHA
| DDCAPS_BLT
| DDCAPS_BLTCOLORFILL
| DDCAPS_BLTDEPTHFILL
|
2451 DDCAPS_CANBLTSYSMEM
| DDCAPS_PALETTE
| DDCAPS_ZBLTS
;
2452 caps
->dwCaps2
= DDCAPS2_CERTIFIED
| DDCAPS2_NO2DDURING3DSCENE
| DDCAPS2_NOPAGELOCKREQUIRED
|
2453 DDCAPS2_WIDESURFACES
;
2454 caps
->dwCKeyCaps
= 0;
2456 caps
->dwFXAlphaCaps
= 0;
2457 caps
->dwPalCaps
= DDPCAPS_8BIT
| DDPCAPS_ALLOW256
;
2459 caps
->dwZBufferBitDepths
= DDBD_16
;
2460 /* I put here 8 Mo so that D3D applications will believe they have enough memory
2461 to put textures in video memory.
2462 BTW, is this only frame buffer memory or also texture memory (for Voodoo boards
2464 caps
->dwVidMemTotal
= 8192 * 1024;
2465 caps
->dwVidMemFree
= 8192 * 1024;
2466 /* These are all the supported capabilities of the surfaces */
2467 caps
->ddsCaps
.dwCaps
= DDSCAPS_3DDEVICE
| DDSCAPS_ALPHA
| DDSCAPS_BACKBUFFER
| DDSCAPS_COMPLEX
| DDSCAPS_FLIP
|
2468 DDSCAPS_FRONTBUFFER
| DDSCAPS_LOCALVIDMEM
| DDSCAPS_MIPMAP
| DDSCAPS_NONLOCALVIDMEM
| DDSCAPS_OFFSCREENPLAIN
|
2469 DDSCAPS_OVERLAY
| DDSCAPS_PALETTE
| DDSCAPS_PRIMARYSURFACE
| DDSCAPS_SYSTEMMEMORY
| DDSCAPS_TEXTURE
|
2470 DDSCAPS_VIDEOMEMORY
| DDSCAPS_VISIBLE
| DDSCAPS_ZBUFFER
;
2473 static HRESULT WINAPI
Xlib_IDirectDraw2_GetCaps(
2474 LPDIRECTDRAW2
this,LPDDCAPS caps1
,LPDDCAPS caps2
2476 TRACE(ddraw
,"(%p)->GetCaps(%p,%p)\n",this,caps1
,caps2
);
2478 /* Put the same caps for the two capabilities */
2485 static HRESULT WINAPI
IDirectDraw2_CreateClipper(
2486 LPDIRECTDRAW2
this,DWORD x
,LPDIRECTDRAWCLIPPER
*lpddclip
,LPUNKNOWN lpunk
2488 FIXME(ddraw
,"(%p)->(%08lx,%p,%p),stub!\n",
2489 this,x
,lpddclip
,lpunk
2491 *lpddclip
= (LPDIRECTDRAWCLIPPER
)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY
,sizeof(IDirectDrawClipper
));
2492 (*lpddclip
)->ref
= 1;
2493 (*lpddclip
)->lpvtbl
= &ddclipvt
;
2497 static HRESULT WINAPI
common_IDirectDraw2_CreatePalette(
2498 LPDIRECTDRAW2
this,DWORD x
,LPPALETTEENTRY palent
,LPDIRECTDRAWPALETTE
*lpddpal
,LPUNKNOWN lpunk
2500 *lpddpal
= (LPDIRECTDRAWPALETTE
)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY
,sizeof(IDirectDrawPalette
));
2501 if (*lpddpal
== NULL
) return E_OUTOFMEMORY
;
2502 (*lpddpal
)->ref
= 1;
2503 (*lpddpal
)->ddraw
= (LPDIRECTDRAW
)this;
2504 (*lpddpal
)->installed
= 0;
2505 if (this->d
.depth
<=8) {
2506 (*lpddpal
)->cm
= TSXCreateColormap(display
,DefaultRootWindow(display
),DefaultVisualOfScreen(screen
),AllocAll
);
2508 /* we don't want palettes in hicolor or truecolor */
2514 /* Initialize the palette based on the passed palent struct */
2515 FIXME(ddraw
,"needs to handle palent (%p)\n",palent
);
2520 static HRESULT WINAPI
DGA_IDirectDraw2_CreatePalette(
2521 LPDIRECTDRAW2
this,DWORD x
,LPPALETTEENTRY palent
,LPDIRECTDRAWPALETTE
*lpddpal
,LPUNKNOWN lpunk
2524 TRACE(ddraw
,"(%p)->(%08lx,%p,%p,%p)\n",this,x
,palent
,lpddpal
,lpunk
);
2525 res
= common_IDirectDraw2_CreatePalette(this,x
,palent
,lpddpal
,lpunk
);
2526 if (res
!= 0) return res
;
2527 (*lpddpal
)->lpvtbl
= &dga_ddpalvt
;
2531 static HRESULT WINAPI
Xlib_IDirectDraw2_CreatePalette(
2532 LPDIRECTDRAW2
this,DWORD x
,LPPALETTEENTRY palent
,LPDIRECTDRAWPALETTE
*lpddpal
,LPUNKNOWN lpunk
2534 TRACE(ddraw
,"(%p)->(%08lx,%p,%p,%p)\n",this,x
,palent
,lpddpal
,lpunk
);
2535 *lpddpal
= (LPDIRECTDRAWPALETTE
)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY
,sizeof(IDirectDrawPalette
));
2537 if (*lpddpal
== NULL
)
2538 return E_OUTOFMEMORY
;
2540 (*lpddpal
)->ref
= 1;
2541 (*lpddpal
)->installed
= 0;
2542 (*lpddpal
)->lpvtbl
= &xlib_ddpalvt
;
2544 (*lpddpal
)->ddraw
= (LPDIRECTDRAW
)this;
2545 this->lpvtbl
->fnAddRef(this);
2548 FIXME(ddraw
,"needs to handle palent (%p)\n",palent
);
2553 static HRESULT WINAPI
DGA_IDirectDraw2_RestoreDisplayMode(LPDIRECTDRAW2
this) {
2554 #ifdef HAVE_LIBXXF86DGA
2555 TRACE(ddraw
, "(%p)->()\n",this);
2557 TSXF86DGADirectVideo(display
,DefaultScreen(display
),0);
2558 #ifdef RESTORE_SIGNALS
2559 SIGNAL_InitEmulator();
2562 #else /* defined(HAVE_LIBXXF86DGA) */
2563 return E_UNEXPECTED
;
2567 static HRESULT WINAPI
Xlib_IDirectDraw2_RestoreDisplayMode(LPDIRECTDRAW2
this) {
2568 TRACE(ddraw
, "(%p)->RestoreDisplayMode()\n", this);
2573 static HRESULT WINAPI
IDirectDraw2_WaitForVerticalBlank(
2574 LPDIRECTDRAW2
this,DWORD x
,HANDLE32 h
2576 TRACE(ddraw
,"(%p)->(0x%08lx,0x%08x)\n",this,x
,h
);
2580 static ULONG WINAPI
IDirectDraw2_AddRef(LPDIRECTDRAW2
this) {
2581 TRACE( ddraw
, "(%p)->() incrementing from %lu.\n", this, this->ref
);
2583 return ++(this->ref
);
2586 static ULONG WINAPI
DGA_IDirectDraw2_Release(LPDIRECTDRAW2
this) {
2587 TRACE( ddraw
, "(%p)->() decrementing from %lu.\n", this, this->ref
);
2589 #ifdef HAVE_LIBXXF86DGA
2590 if (!--(this->ref
)) {
2591 TSXF86DGADirectVideo(display
,DefaultScreen(display
),0);
2593 #ifdef HAVE_LIBXXF86VM
2595 TSXF86VidModeSwitchToMode(display
, DefaultScreen(display
), orig_mode
);
2596 if (orig_mode
->privsize
)
2597 TSXFree(orig_mode
->private);
2602 #ifdef RESTORE_SIGNALS
2603 SIGNAL_InitEmulator();
2605 HeapFree(GetProcessHeap(),0,this);
2608 #endif /* defined(HAVE_LIBXXF86DGA) */
2612 static ULONG WINAPI
Xlib_IDirectDraw2_Release(LPDIRECTDRAW2
this) {
2613 TRACE( ddraw
, "(%p)->() decrementing from %lu.\n", this, this->ref
);
2615 if (!--(this->ref
)) {
2616 HeapFree(GetProcessHeap(),0,this);
2619 /* FIXME: destroy window ... */
2623 static HRESULT WINAPI
DGA_IDirectDraw2_QueryInterface(
2624 LPDIRECTDRAW2
this,REFIID refiid
,LPVOID
*obj
2628 WINE_StringFromCLSID((LPCLSID
)refiid
,xrefiid
);
2629 TRACE(ddraw
,"(%p)->(%s,%p)\n",this,xrefiid
,obj
);
2630 if (!memcmp(&IID_IUnknown
,refiid
,sizeof(IID_IUnknown
))) {
2632 this->lpvtbl
->fnAddRef(this);
2634 TRACE(ddraw
, " Creating IUnknown interface (%p)\n", *obj
);
2638 if (!memcmp(&IID_IDirectDraw
,refiid
,sizeof(IID_IDirectDraw
))) {
2639 this->lpvtbl
= (LPDIRECTDRAW2_VTABLE
)&dga_ddvt
;
2640 this->lpvtbl
->fnAddRef(this);
2643 TRACE(ddraw
, " Creating IDirectDraw interface (%p)\n", *obj
);
2647 if (!memcmp(&IID_IDirectDraw2
,refiid
,sizeof(IID_IDirectDraw2
))) {
2648 this->lpvtbl
= (LPDIRECTDRAW2_VTABLE
)&dga_dd2vt
;
2649 this->lpvtbl
->fnAddRef(this);
2652 TRACE(ddraw
, " Creating IDirectDraw2 interface (%p)\n", *obj
);
2656 if (!memcmp(&IID_IDirect3D
,refiid
,sizeof(IID_IDirect3D
))) {
2659 d3d
= HeapAlloc(GetProcessHeap(),0,sizeof(*d3d
));
2661 d3d
->ddraw
= (LPDIRECTDRAW
)this;
2662 this->lpvtbl
->fnAddRef(this);
2663 d3d
->lpvtbl
= &d3dvt
;
2666 TRACE(ddraw
, " Creating IDirect3D interface (%p)\n", *obj
);
2670 if (!memcmp(&IID_IDirect3D2
,refiid
,sizeof(IID_IDirect3D
))) {
2673 d3d
= HeapAlloc(GetProcessHeap(),0,sizeof(*d3d
));
2675 d3d
->ddraw
= (LPDIRECTDRAW
)this;
2676 this->lpvtbl
->fnAddRef(this);
2677 d3d
->lpvtbl
= &d3d2vt
;
2680 TRACE(ddraw
, " Creating IDirect3D2 interface (%p)\n", *obj
);
2684 WARN(ddraw
,"(%p):interface for IID %s _NOT_ found!\n",this,xrefiid
);
2685 return OLE_E_ENUM_NOMORE
;
2688 static HRESULT WINAPI
Xlib_IDirectDraw2_QueryInterface(
2689 LPDIRECTDRAW2
this,REFIID refiid
,LPVOID
*obj
2693 WINE_StringFromCLSID((LPCLSID
)refiid
,xrefiid
);
2694 TRACE(ddraw
,"(%p)->(%s,%p)\n",this,xrefiid
,obj
);
2695 if (!memcmp(&IID_IUnknown
,refiid
,sizeof(IID_IUnknown
))) {
2697 this->lpvtbl
->fnAddRef(this);
2699 TRACE(ddraw
, " Creating IUnknown interface (%p)\n", *obj
);
2703 if (!memcmp(&IID_IDirectDraw
,refiid
,sizeof(IID_IDirectDraw
))) {
2704 this->lpvtbl
= (LPDIRECTDRAW2_VTABLE
)&xlib_ddvt
;
2705 this->lpvtbl
->fnAddRef(this);
2708 TRACE(ddraw
, " Creating IDirectDraw interface (%p)\n", *obj
);
2712 if (!memcmp(&IID_IDirectDraw2
,refiid
,sizeof(IID_IDirectDraw2
))) {
2713 this->lpvtbl
= (LPDIRECTDRAW2_VTABLE
)&xlib_dd2vt
;
2714 this->lpvtbl
->fnAddRef(this);
2717 TRACE(ddraw
, " Creating IDirectDraw2 interface (%p)\n", *obj
);
2721 if (!memcmp(&IID_IDirect3D
,refiid
,sizeof(IID_IDirect3D
))) {
2724 d3d
= HeapAlloc(GetProcessHeap(),0,sizeof(*d3d
));
2726 d3d
->ddraw
= (LPDIRECTDRAW
)this;
2727 this->lpvtbl
->fnAddRef(this);
2728 d3d
->lpvtbl
= &d3dvt
;
2731 TRACE(ddraw
, " Creating IDirect3D interface (%p)\n", *obj
);
2735 if (!memcmp(&IID_IDirect3D2
,refiid
,sizeof(IID_IDirect3D
))) {
2738 d3d
= HeapAlloc(GetProcessHeap(),0,sizeof(*d3d
));
2740 d3d
->ddraw
= (LPDIRECTDRAW
)this;
2741 this->lpvtbl
->fnAddRef(this);
2742 d3d
->lpvtbl
= &d3d2vt
;
2745 TRACE(ddraw
, " Creating IDirect3D2 interface (%p)\n", *obj
);
2749 WARN(ddraw
,"(%p):interface for IID %s _NOT_ found!\n",this,xrefiid
);
2750 return OLE_E_ENUM_NOMORE
;
2753 static HRESULT WINAPI
IDirectDraw2_GetVerticalBlankStatus(
2754 LPDIRECTDRAW2
this,BOOL32
*status
2756 TRACE(ddraw
,"(%p)->(%p)\n",this,status
);
2761 static HRESULT WINAPI
IDirectDraw2_EnumDisplayModes(
2762 LPDIRECTDRAW2
this,DWORD dwFlags
,LPDDSURFACEDESC lpddsfd
,LPVOID context
,LPDDENUMMODESCALLBACK modescb
2764 DDSURFACEDESC ddsfd
;
2767 } modes
[5] = { /* some of the usual modes */
2774 static int depths
[4] = {8,16,24,32};
2777 TRACE(ddraw
,"(%p)->(0x%08lx,%p,%p,%p)\n",this,dwFlags
,lpddsfd
,context
,modescb
);
2778 ddsfd
.dwSize
= sizeof(ddsfd
);
2779 ddsfd
.dwFlags
= DDSD_HEIGHT
|DDSD_WIDTH
|DDSD_BACKBUFFERCOUNT
|DDSD_PIXELFORMAT
|DDSD_CAPS
;
2780 if (dwFlags
& DDEDM_REFRESHRATES
) {
2781 ddsfd
.dwFlags
|= DDSD_REFRESHRATE
;
2782 ddsfd
.x
.dwRefreshRate
= 60;
2785 for (i
=0;i
<sizeof(depths
)/sizeof(depths
[0]);i
++) {
2786 ddsfd
.dwBackBufferCount
= 1;
2787 ddsfd
.ddpfPixelFormat
.dwFourCC
= 0;
2788 ddsfd
.ddpfPixelFormat
.dwFlags
= DDPF_RGB
;
2789 ddsfd
.ddpfPixelFormat
.x
.dwRGBBitCount
= depths
[i
];
2790 /* FIXME: those masks would have to be set in depth > 8 */
2792 ddsfd
.ddpfPixelFormat
.y
.dwRBitMask
= 0;
2793 ddsfd
.ddpfPixelFormat
.z
.dwGBitMask
= 0;
2794 ddsfd
.ddpfPixelFormat
.xx
.dwBBitMask
= 0;
2795 ddsfd
.ddpfPixelFormat
.xy
.dwRGBAlphaBitMask
= 0;
2796 ddsfd
.ddsCaps
.dwCaps
=DDSCAPS_PALETTE
;
2797 ddsfd
.ddpfPixelFormat
.dwFlags
|=DDPF_PALETTEINDEXED8
;
2799 ddsfd
.ddpfPixelFormat
.xy
.dwRGBAlphaBitMask
= 0;
2801 /* FIXME: We should query those from X itself */
2802 switch (depths
[i
]) {
2804 ddsfd
.ddpfPixelFormat
.y
.dwRBitMask
= 0x000f;
2805 ddsfd
.ddpfPixelFormat
.z
.dwGBitMask
= 0x00f0;
2806 ddsfd
.ddpfPixelFormat
.xx
.dwBBitMask
= 0x0f00;
2809 ddsfd
.ddpfPixelFormat
.y
.dwRBitMask
= 0x000000ff;
2810 ddsfd
.ddpfPixelFormat
.z
.dwGBitMask
= 0x0000ff00;
2811 ddsfd
.ddpfPixelFormat
.xx
.dwBBitMask
= 0x00ff0000;
2814 ddsfd
.ddpfPixelFormat
.y
.dwRBitMask
= 0x000000ff;
2815 ddsfd
.ddpfPixelFormat
.z
.dwGBitMask
= 0x0000ff00;
2816 ddsfd
.ddpfPixelFormat
.xx
.dwBBitMask
= 0x00ff0000;
2821 ddsfd
.dwWidth
= screenWidth
;
2822 ddsfd
.dwHeight
= screenHeight
;
2823 TRACE(ddraw
," enumerating (%ldx%ldx%d)\n",ddsfd
.dwWidth
,ddsfd
.dwHeight
,depths
[i
]);
2824 if (!modescb(&ddsfd
,context
)) return DD_OK
;
2826 for (j
=0;j
<sizeof(modes
)/sizeof(modes
[0]);j
++) {
2827 ddsfd
.dwWidth
= modes
[j
].w
;
2828 ddsfd
.dwHeight
= modes
[j
].h
;
2829 TRACE(ddraw
," enumerating (%ldx%ldx%d)\n",ddsfd
.dwWidth
,ddsfd
.dwHeight
,depths
[i
]);
2830 if (!modescb(&ddsfd
,context
)) return DD_OK
;
2833 if (!(dwFlags
& DDEDM_STANDARDVGAMODES
)) {
2834 /* modeX is not standard VGA */
2836 ddsfd
.dwHeight
= 200;
2837 ddsfd
.dwWidth
= 320;
2838 TRACE(ddraw
," enumerating (320x200x%d)\n",depths
[i
]);
2839 if (!modescb(&ddsfd
,context
)) return DD_OK
;
2845 static HRESULT WINAPI
DGA_IDirectDraw2_GetDisplayMode(
2846 LPDIRECTDRAW2
this,LPDDSURFACEDESC lpddsfd
2848 #ifdef HAVE_LIBXXF86DGA
2849 TRACE(ddraw
,"(%p)->(%p)\n",this,lpddsfd
);
2850 lpddsfd
->dwFlags
= DDSD_HEIGHT
|DDSD_WIDTH
|DDSD_PITCH
|DDSD_BACKBUFFERCOUNT
|DDSD_PIXELFORMAT
|DDSD_CAPS
;
2851 lpddsfd
->dwHeight
= screenHeight
;
2852 lpddsfd
->dwWidth
= screenWidth
;
2853 lpddsfd
->lPitch
= this->e
.dga
.fb_width
*this->d
.depth
/8;
2854 lpddsfd
->dwBackBufferCount
= 1;
2855 lpddsfd
->x
.dwRefreshRate
= 60;
2856 lpddsfd
->ddsCaps
.dwCaps
= DDSCAPS_PALETTE
;
2857 _getpixelformat(this,&(lpddsfd
->ddpfPixelFormat
));
2859 #else /* defined(HAVE_LIBXXF86DGA) */
2860 return E_UNEXPECTED
;
2861 #endif /* defined(HAVE_LIBXXF86DGA) */
2864 static HRESULT WINAPI
Xlib_IDirectDraw2_GetDisplayMode(
2865 LPDIRECTDRAW2
this,LPDDSURFACEDESC lpddsfd
2867 TRACE(ddraw
,"(%p)->GetDisplayMode(%p)\n",this,lpddsfd
);
2868 lpddsfd
->dwFlags
= DDSD_HEIGHT
|DDSD_WIDTH
|DDSD_PITCH
|DDSD_BACKBUFFERCOUNT
|DDSD_PIXELFORMAT
|DDSD_CAPS
;
2869 lpddsfd
->dwHeight
= screenHeight
;
2870 lpddsfd
->dwWidth
= screenWidth
;
2871 /* POOLE FIXME: Xlib */
2872 lpddsfd
->lPitch
= this->e
.dga
.fb_width
*this->d
.depth
/8;
2873 /* END FIXME: Xlib */
2874 lpddsfd
->dwBackBufferCount
= 1;
2875 lpddsfd
->x
.dwRefreshRate
= 60;
2876 lpddsfd
->ddsCaps
.dwCaps
= DDSCAPS_PALETTE
;
2877 _getpixelformat(this,&(lpddsfd
->ddpfPixelFormat
));
2881 static HRESULT WINAPI
IDirectDraw2_FlipToGDISurface(LPDIRECTDRAW2
this) {
2882 TRACE(ddraw
,"(%p)->()\n",this);
2886 static HRESULT WINAPI
IDirectDraw2_GetMonitorFrequency(
2887 LPDIRECTDRAW2
this,LPDWORD freq
2889 FIXME(ddraw
,"(%p)->(%p) returns 60 Hz always\n",this,freq
);
2890 *freq
= 60*100; /* 60 Hz */
2894 /* what can we directly decompress? */
2895 static HRESULT WINAPI
IDirectDraw2_GetFourCCCodes(
2896 LPDIRECTDRAW2
this,LPDWORD x
,LPDWORD y
2898 FIXME(ddraw
,"(%p,%p,%p), stub\n",this,x
,y
);
2902 static HRESULT WINAPI
IDirectDraw2_EnumSurfaces(
2903 LPDIRECTDRAW2
this,DWORD x
,LPDDSURFACEDESC ddsfd
,LPVOID context
,LPDDENUMSURFACESCALLBACK ddsfcb
2905 FIXME(ddraw
,"(%p)->(0x%08lx,%p,%p,%p),stub!\n",this,x
,ddsfd
,context
,ddsfcb
);
2909 static HRESULT WINAPI
IDirectDraw2_Compact(
2910 LPDIRECTDRAW2
this )
2912 FIXME(ddraw
,"(%p)->()\n", this );
2918 /* Note: Hack so we can reuse the old functions without compiler warnings */
2920 # define XCAST(fun) (typeof(dga_ddvt.fn##fun))
2922 # define XCAST(fun) (void*)
2925 static struct IDirectDraw_VTable dga_ddvt
= {
2926 XCAST(QueryInterface
)DGA_IDirectDraw2_QueryInterface
,
2927 XCAST(AddRef
)IDirectDraw2_AddRef
,
2928 XCAST(Release
)DGA_IDirectDraw2_Release
,
2929 XCAST(Compact
)IDirectDraw2_Compact
,
2930 XCAST(CreateClipper
)IDirectDraw2_CreateClipper
,
2931 XCAST(CreatePalette
)DGA_IDirectDraw2_CreatePalette
,
2932 XCAST(CreateSurface
)DGA_IDirectDraw2_CreateSurface
,
2933 XCAST(DuplicateSurface
)IDirectDraw2_DuplicateSurface
,
2934 XCAST(EnumDisplayModes
)IDirectDraw2_EnumDisplayModes
,
2935 XCAST(EnumSurfaces
)IDirectDraw2_EnumSurfaces
,
2936 XCAST(FlipToGDISurface
)IDirectDraw2_FlipToGDISurface
,
2937 XCAST(GetCaps
)DGA_IDirectDraw2_GetCaps
,
2938 XCAST(GetDisplayMode
)DGA_IDirectDraw2_GetDisplayMode
,
2939 XCAST(GetFourCCCodes
)IDirectDraw2_GetFourCCCodes
,
2940 XCAST(GetGDISurface
)15,
2941 XCAST(GetMonitorFrequency
)IDirectDraw2_GetMonitorFrequency
,
2942 XCAST(GetScanLine
)17,
2943 XCAST(GetVerticalBlankStatus
)IDirectDraw2_GetVerticalBlankStatus
,
2944 XCAST(Initialize
)19,
2945 XCAST(RestoreDisplayMode
)DGA_IDirectDraw2_RestoreDisplayMode
,
2946 XCAST(SetCooperativeLevel
)IDirectDraw2_SetCooperativeLevel
,
2947 DGA_IDirectDraw_SetDisplayMode
,
2948 XCAST(WaitForVerticalBlank
)IDirectDraw2_WaitForVerticalBlank
,
2951 static struct IDirectDraw_VTable xlib_ddvt
= {
2952 XCAST(QueryInterface
)Xlib_IDirectDraw2_QueryInterface
,
2953 XCAST(AddRef
)IDirectDraw2_AddRef
,
2954 XCAST(Release
)Xlib_IDirectDraw2_Release
,
2955 XCAST(Compact
)IDirectDraw2_Compact
,
2956 XCAST(CreateClipper
)IDirectDraw2_CreateClipper
,
2957 XCAST(CreatePalette
)Xlib_IDirectDraw2_CreatePalette
,
2958 XCAST(CreateSurface
)Xlib_IDirectDraw2_CreateSurface
,
2959 XCAST(DuplicateSurface
)IDirectDraw2_DuplicateSurface
,
2960 XCAST(EnumDisplayModes
)IDirectDraw2_EnumDisplayModes
,
2961 XCAST(EnumSurfaces
)IDirectDraw2_EnumSurfaces
,
2962 XCAST(FlipToGDISurface
)IDirectDraw2_FlipToGDISurface
,
2963 XCAST(GetCaps
)Xlib_IDirectDraw2_GetCaps
,
2964 XCAST(GetDisplayMode
)Xlib_IDirectDraw2_GetDisplayMode
,
2965 XCAST(GetFourCCCodes
)IDirectDraw2_GetFourCCCodes
,
2966 XCAST(GetGDISurface
)15,
2967 XCAST(GetMonitorFrequency
)IDirectDraw2_GetMonitorFrequency
,
2968 XCAST(GetScanLine
)17,
2969 XCAST(GetVerticalBlankStatus
)IDirectDraw2_GetVerticalBlankStatus
,
2970 XCAST(Initialize
)19,
2971 XCAST(RestoreDisplayMode
)Xlib_IDirectDraw2_RestoreDisplayMode
,
2972 XCAST(SetCooperativeLevel
)IDirectDraw2_SetCooperativeLevel
,
2973 Xlib_IDirectDraw_SetDisplayMode
,
2974 XCAST(WaitForVerticalBlank
)IDirectDraw2_WaitForVerticalBlank
,
2977 /*****************************************************************************
2983 static HRESULT WINAPI
DGA_IDirectDraw2_SetDisplayMode(
2984 LPDIRECTDRAW2
this,DWORD width
,DWORD height
,DWORD depth
,DWORD xx
,DWORD yy
2986 return DGA_IDirectDraw_SetDisplayMode((LPDIRECTDRAW
)this,width
,height
,depth
);
2989 static HRESULT WINAPI
Xlib_IDirectDraw2_SetDisplayMode(
2990 LPDIRECTDRAW2
this,DWORD width
,DWORD height
,DWORD depth
,DWORD xx
,DWORD yy
2992 return Xlib_IDirectDraw_SetDisplayMode((LPDIRECTDRAW
)this,width
,height
,depth
);
2995 static HRESULT WINAPI
DGA_IDirectDraw2_GetAvailableVidMem(
2996 LPDIRECTDRAW2
this,LPDDSCAPS ddscaps
,LPDWORD total
,LPDWORD free
2998 TRACE(ddraw
,"(%p)->(%p,%p,%p)\n",
2999 this,ddscaps
,total
,free
3001 if (total
) *total
= this->e
.dga
.fb_memsize
* 1024;
3002 if (free
) *free
= this->e
.dga
.fb_memsize
* 1024;
3006 static HRESULT WINAPI
Xlib_IDirectDraw2_GetAvailableVidMem(
3007 LPDIRECTDRAW2
this,LPDDSCAPS ddscaps
,LPDWORD total
,LPDWORD free
3009 TRACE(ddraw
,"(%p)->(%p,%p,%p)\n",
3010 this,ddscaps
,total
,free
3012 if (total
) *total
= 2048 * 1024;
3013 if (free
) *free
= 2048 * 1024;
3017 static IDirectDraw2_VTable dga_dd2vt
= {
3018 DGA_IDirectDraw2_QueryInterface
,
3019 IDirectDraw2_AddRef
,
3020 DGA_IDirectDraw2_Release
,
3021 IDirectDraw2_Compact
,
3022 IDirectDraw2_CreateClipper
,
3023 DGA_IDirectDraw2_CreatePalette
,
3024 DGA_IDirectDraw2_CreateSurface
,
3026 IDirectDraw2_EnumDisplayModes
,
3027 IDirectDraw2_EnumSurfaces
,
3028 IDirectDraw2_FlipToGDISurface
,
3029 DGA_IDirectDraw2_GetCaps
,
3030 DGA_IDirectDraw2_GetDisplayMode
,
3031 IDirectDraw2_GetFourCCCodes
,
3033 IDirectDraw2_GetMonitorFrequency
,
3035 IDirectDraw2_GetVerticalBlankStatus
,
3037 DGA_IDirectDraw2_RestoreDisplayMode
,
3038 IDirectDraw2_SetCooperativeLevel
,
3039 DGA_IDirectDraw2_SetDisplayMode
,
3040 IDirectDraw2_WaitForVerticalBlank
,
3041 DGA_IDirectDraw2_GetAvailableVidMem
3044 static struct IDirectDraw2_VTable xlib_dd2vt
= {
3045 Xlib_IDirectDraw2_QueryInterface
,
3046 IDirectDraw2_AddRef
,
3047 Xlib_IDirectDraw2_Release
,
3048 IDirectDraw2_Compact
,
3049 IDirectDraw2_CreateClipper
,
3050 Xlib_IDirectDraw2_CreatePalette
,
3051 Xlib_IDirectDraw2_CreateSurface
,
3053 IDirectDraw2_EnumDisplayModes
,
3054 IDirectDraw2_EnumSurfaces
,
3055 IDirectDraw2_FlipToGDISurface
,
3056 Xlib_IDirectDraw2_GetCaps
,
3057 Xlib_IDirectDraw2_GetDisplayMode
,
3058 IDirectDraw2_GetFourCCCodes
,
3060 IDirectDraw2_GetMonitorFrequency
,
3062 IDirectDraw2_GetVerticalBlankStatus
,
3064 Xlib_IDirectDraw2_RestoreDisplayMode
,
3065 IDirectDraw2_SetCooperativeLevel
,
3066 Xlib_IDirectDraw2_SetDisplayMode
,
3067 IDirectDraw2_WaitForVerticalBlank
,
3068 Xlib_IDirectDraw2_GetAvailableVidMem
3071 /******************************************************************************
3075 LRESULT WINAPI
Xlib_DDWndProc(HWND32 hwnd
,UINT32 msg
,WPARAM32 wParam
,LPARAM lParam
)
3078 LPDIRECTDRAW ddraw
= NULL
;
3081 /* FIXME(ddraw,"(0x%04x,%s,0x%08lx,0x%08lx),stub!\n",(int)hwnd,SPY_GetMsgName(msg),(long)wParam,(long)lParam); */
3083 SetLastError( ERROR_SUCCESS
);
3084 ddraw
= (LPDIRECTDRAW
)GetWindowLong32A( hwnd
, ddrawXlibThisOffset
);
3086 ( ( lastError
= GetLastError() ) != ERROR_SUCCESS
)
3089 ERR( ddraw
, "Unable to retrieve this ptr from window. Error %08lx\n", lastError
);
3094 /* Perform any special direct draw functions */
3096 ddraw
->e
.xlib
.paintable
= 1;
3098 /* Now let the application deal with the rest of this */
3099 if( ddraw
->d
.mainWindow
)
3102 /* Don't think that we actually need to call this but...
3103 might as well be on the safe side of things... */
3105 /* I changed hwnd to ddraw->d.mainWindow as I did not see why
3106 it should be the procedures of our fake window that gets called
3107 instead of those of the window provided by the application.
3108 And with this patch, mouse clicks work with Monkey Island III
3110 ret
= DefWindowProc32A( ddraw
->d
.mainWindow
, msg
, wParam
, lParam
);
3114 /* We didn't handle the message - give it to the application */
3115 if (ddraw
&& ddraw
->d
.mainWindow
&& WIN_FindWndPtr(ddraw
->d
.mainWindow
)) {
3116 ret
= CallWindowProc32A( WIN_FindWndPtr( ddraw
->d
.mainWindow
)->winproc
,
3117 ddraw
->d
.mainWindow
, msg
, wParam
, lParam
);
3122 ret
= DefWindowProc32A(hwnd
, msg
, wParam
, lParam
);
3128 ret
= DefWindowProc32A(hwnd
,msg
,wParam
,lParam
);
3134 HRESULT WINAPI
DGA_DirectDrawCreate( LPDIRECTDRAW
*lplpDD
, LPUNKNOWN pUnkOuter
) {
3135 #ifdef HAVE_LIBXXF86DGA
3136 int memsize
,banksize
,width
,major
,minor
,flags
,height
;
3140 /* Must be able to access /dev/mem for DGA extensions to work, root is not neccessary. --stephenc */
3141 if ((fd
= open("/dev/mem", O_RDWR
)) != -1)
3145 MSG("Must be able to access /dev/mem to use XF86DGA!\n");
3146 MessageBox32A(0,"Using the XF86DGA extension requires access to /dev/mem.","WINE DirectDraw",MB_OK
|MB_ICONSTOP
);
3147 return E_UNEXPECTED
;
3149 if (!DDRAW_DGA_Available()) {
3150 TRACE(ddraw
,"No XF86DGA detected.\n");
3151 return DDERR_GENERIC
;
3153 *lplpDD
= (LPDIRECTDRAW
)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY
,sizeof(IDirectDraw
));
3154 (*lplpDD
)->lpvtbl
= &dga_ddvt
;
3156 TSXF86DGAQueryVersion(display
,&major
,&minor
);
3157 TRACE(ddraw
,"XF86DGA is version %d.%d\n",major
,minor
);
3158 TSXF86DGAQueryDirectVideo(display
,DefaultScreen(display
),&flags
);
3159 if (!(flags
& XF86DGADirectPresent
))
3160 MSG("direct video is NOT PRESENT.\n");
3161 TSXF86DGAGetVideo(display
,DefaultScreen(display
),&addr
,&width
,&banksize
,&memsize
);
3162 TRACE(ddraw
,"video framebuffer: begin %p, width %d,banksize %d,memsize %d\n",
3163 addr
,width
,banksize
,memsize
3165 (*lplpDD
)->e
.dga
.fb_width
= width
;
3166 (*lplpDD
)->d
.width
= width
;
3167 (*lplpDD
)->e
.dga
.fb_addr
= addr
;
3168 (*lplpDD
)->e
.dga
.fb_memsize
= memsize
;
3169 (*lplpDD
)->e
.dga
.fb_banksize
= banksize
;
3171 TSXF86DGAGetViewPortSize(display
,DefaultScreen(display
),&width
,&height
);
3172 TSXF86DGASetViewPort(display
,DefaultScreen(display
),0,0);
3173 (*lplpDD
)->e
.dga
.fb_height
= screenHeight
;
3175 (*lplpDD
)->e
.dga
.vpmask
= 1;
3177 (*lplpDD
)->e
.dga
.vpmask
= 0;
3180 /* just assume the default depth is the DGA depth too */
3181 (*lplpDD
)->d
.depth
= DefaultDepthOfScreen(screen
);
3182 #ifdef RESTORE_SIGNALS
3183 SIGNAL_InitEmulator();
3187 #else /* defined(HAVE_LIBXXF86DGA) */
3188 return DDERR_INVALIDDIRECTDRAWGUID
;
3189 #endif /* defined(HAVE_LIBXXF86DGA) */
3193 DDRAW_XSHM_Available()
3195 #ifdef HAVE_LIBXXSHM
3196 if (TSXShmQueryExtension(display
))
3201 if (TSXShmQueryVersion(display
, &major
, &minor
, &shpix
))
3213 HRESULT WINAPI
Xlib_DirectDrawCreate( LPDIRECTDRAW
*lplpDD
, LPUNKNOWN pUnkOuter
) {
3215 *lplpDD
= (LPDIRECTDRAW
)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY
,sizeof(IDirectDraw
));
3216 (*lplpDD
)->lpvtbl
= &xlib_ddvt
;
3218 (*lplpDD
)->e
.xlib
.drawable
= 0; /* in SetDisplayMode */
3220 (*lplpDD
)->d
.depth
= DefaultDepthOfScreen(screen
);
3221 (*lplpDD
)->d
.height
= screenHeight
;
3222 (*lplpDD
)->d
.width
= screenWidth
;
3224 #ifdef HAVE_LIBXXSHM
3225 /* Test if XShm is available.
3226 As XShm is not ready yet for 'prime-time', it is disabled for now */
3227 if (((*lplpDD
)->e
.xlib
.xshm_active
= 0 /* DDRAW_XSHM_Available() */))
3228 TRACE(ddraw
, "Using XShm extesion.\n");
3234 HRESULT WINAPI
DirectDrawCreate( LPGUID lpGUID
, LPDIRECTDRAW
*lplpDD
, LPUNKNOWN pUnkOuter
) {
3241 WINE_StringFromCLSID(lpGUID
,xclsid
);
3243 sprintf(xclsid
,"<guid-0x%08x>",(int)lpGUID
);
3247 TRACE(ddraw
,"(%s,%p,%p)\n",xclsid
,lplpDD
,pUnkOuter
);
3250 /* if they didn't request a particular interface, use the best
3252 if (DDRAW_DGA_Available())
3253 lpGUID
= &DGA_DirectDraw_GUID
;
3255 lpGUID
= &XLIB_DirectDraw_GUID
;
3258 wc
.style
= CS_GLOBALCLASS
;
3259 wc
.lpfnWndProc
= Xlib_DDWndProc
;
3261 wc
.cbWndExtra
= /* Defines extra mem for window. This is used for storing this */
3262 sizeof( LPDIRECTDRAW
); /* ddrawXlibThisOffset */
3264 /* We can be a child of the desktop since we're really important */
3265 pParentWindow
= WIN_GetDesktop();
3266 wc
.hInstance
= pParentWindow
? pParentWindow
->hwndSelf
: 0;
3270 wc
.hCursor
= (HCURSOR32
)IDC_ARROW32A
;
3271 wc
.hbrBackground
= NULL_BRUSH
;
3272 wc
.lpszMenuName
= 0;
3273 wc
.lpszClassName
= "WINE_DirectDraw";
3274 RegisterClass32A(&wc
);
3276 if (!memcmp(lpGUID
, &DGA_DirectDraw_GUID
, sizeof(GUID
)))
3277 ret
= DGA_DirectDrawCreate(lplpDD
, pUnkOuter
);
3278 else if (!memcmp(lpGUID
, &XLIB_DirectDraw_GUID
, sizeof(GUID
)))
3279 ret
= Xlib_DirectDrawCreate(lplpDD
, pUnkOuter
);
3283 (*lplpDD
)->d
.winclass
= RegisterClass32A(&wc
);
3287 fprintf(stderr
,"DirectDrawCreate(%s,%p,%p): did not recognize requested GUID\n",xclsid
,lplpDD
,pUnkOuter
);
3288 return DDERR_INVALIDDIRECTDRAWGUID
;