4 * Copyright 1993 Alexandre Julliard
7 static char Copyright
[] = "Copyright Alexandre Julliard, 1993";
16 #define NB_DCE 5 /* Number of DCEs created at startup */
18 extern Display
* display
;
20 static HANDLE firstDCE
= 0;
21 static HDC defaultDCstate
= 0;
24 /***********************************************************************
29 HANDLE
DCE_AllocDCE( DCE_TYPE type
)
32 HANDLE handle
= USER_HEAP_ALLOC( GMEM_MOVEABLE
, sizeof(DCE
) );
33 if (!handle
) return 0;
34 dce
= (DCE
*) USER_HEAP_ADDR( handle
);
35 if (!(dce
->hdc
= CreateDC( "DISPLAY", NULL
, NULL
, NULL
)))
37 USER_HEAP_FREE( handle
);
42 dce
->inUse
= (type
!= DCE_CACHE_DC
);
45 dce
->hNext
= firstDCE
;
51 /***********************************************************************
54 void DCE_FreeDCE( HANDLE hdce
)
57 HANDLE
*handle
= &firstDCE
;
59 if (!(dce
= (DCE
*) USER_HEAP_ADDR( hdce
))) return;
60 while (*handle
&& (*handle
!= hdce
))
62 DCE
* prev
= (DCE
*) USER_HEAP_ADDR( *handle
);
63 handle
= &prev
->hNext
;
65 if (*handle
== hdce
) *handle
= dce
->hNext
;
67 USER_HEAP_FREE( hdce
);
71 /***********************************************************************
80 for (i
= 0; i
< NB_DCE
; i
++)
82 if (!(handle
= DCE_AllocDCE( DCE_CACHE_DC
))) return;
83 dce
= (DCE
*) USER_HEAP_ADDR( handle
);
84 if (!defaultDCstate
) defaultDCstate
= GetDCState( dce
->hdc
);
89 /***********************************************************************
92 /* Unimplemented flags: DCX_CLIPSIBLINGS, DCX_LOCKWINDOWUPDATE, DCX_PARENTCLIP
94 HDC
GetDCEx( HWND hwnd
, HRGN hrgnClip
, DWORD flags
)
104 if (!(wndPtr
= WIN_FindWndPtr( hwnd
))) return 0;
108 if (flags
& DCX_USESTYLE
)
110 /* Not sure if this is the real meaning of the DCX_USESTYLE flag... */
111 flags
&= ~(DCX_CACHE
| DCX_CLIPCHILDREN
| DCX_CLIPSIBLINGS
);
114 if (!(wndPtr
->flags
& (WIN_CLASS_DC
| WIN_OWN_DC
)))
116 if (wndPtr
->dwStyle
& WS_CLIPCHILDREN
) flags
|= DCX_CLIPCHILDREN
;
117 if (wndPtr
->dwStyle
& WS_CLIPSIBLINGS
) flags
|= DCX_CLIPSIBLINGS
;
119 else flags
|= DCX_CACHE
;
122 if (flags
& DCX_CACHE
)
124 for (hdce
= firstDCE
; (hdce
); hdce
= dce
->hNext
)
126 if (!(dce
= (DCE
*) USER_HEAP_ADDR( hdce
))) return 0;
127 if ((dce
->type
== DCE_CACHE_DC
) && (!dce
->inUse
)) break;
130 else hdce
= wndPtr
->hdce
;
133 dce
= (DCE
*) USER_HEAP_ADDR( hdce
);
134 dce
->hwndCurrent
= hwnd
;
140 if (!(dc
= (DC
*) GDI_GetObjPtr( hdc
, DC_MAGIC
))) return 0;
144 dc
->u
.x
.drawable
= wndPtr
->window
;
145 if (flags
& DCX_WINDOW
)
149 dc
->w
.DCSizeX
= wndPtr
->rectWindow
.right
- wndPtr
->rectWindow
.left
;
150 dc
->w
.DCSizeY
= wndPtr
->rectWindow
.bottom
- wndPtr
->rectWindow
.top
;
154 dc
->w
.DCOrgX
= wndPtr
->rectClient
.left
- wndPtr
->rectWindow
.left
;
155 dc
->w
.DCOrgY
= wndPtr
->rectClient
.top
- wndPtr
->rectWindow
.top
;
156 dc
->w
.DCSizeX
= wndPtr
->rectClient
.right
- wndPtr
->rectClient
.left
;
157 dc
->w
.DCSizeY
= wndPtr
->rectClient
.bottom
- wndPtr
->rectClient
.top
;
158 IntersectVisRect( hdc
, 0, 0, dc
->w
.DCSizeX
, dc
->w
.DCSizeY
);
161 else dc
->u
.x
.drawable
= DefaultRootWindow( display
);
163 if (flags
& DCX_CLIPCHILDREN
)
164 XSetSubwindowMode( display
, dc
->u
.x
.gc
, ClipByChildren
);
165 else XSetSubwindowMode( display
, dc
->u
.x
.gc
, IncludeInferiors
);
167 if ((flags
& DCX_INTERSECTRGN
) || (flags
& DCX_EXCLUDERGN
))
169 HRGN hrgn
= CreateRectRgn( 0, 0, 0, 0 );
172 if (CombineRgn( hrgn
, InquireVisRgn(hdc
), hrgnClip
,
173 (flags
& DCX_INTERSECTRGN
) ? RGN_AND
: RGN_DIFF
))
174 SelectVisRgn( hdc
, hrgn
);
175 DeleteObject( hrgn
);
180 printf( "GetDCEx(%d,%d,0x%x): returning %d\n", hwnd
, hrgnClip
, flags
, hdc
);
186 /***********************************************************************
189 HDC
GetDC( HWND hwnd
)
191 return GetDCEx( hwnd
, 0, DCX_USESTYLE
);
195 /***********************************************************************
196 * GetWindowDC (USER.67)
198 HDC
GetWindowDC( HWND hwnd
)
200 int flags
= DCX_CACHE
| DCX_WINDOW
;
204 if (!(wndPtr
= WIN_FindWndPtr( hwnd
))) return 0;
205 if (wndPtr
->dwStyle
& WS_CLIPCHILDREN
) flags
|= DCX_CLIPCHILDREN
;
206 if (wndPtr
->dwStyle
& WS_CLIPSIBLINGS
) flags
|= DCX_CLIPSIBLINGS
;
208 return GetDCEx( hwnd
, 0, flags
);
212 /***********************************************************************
213 * ReleaseDC (USER.68)
215 int ReleaseDC( HWND hwnd
, HDC hdc
)
221 printf( "ReleaseDC: %d %d\n", hwnd
, hdc
);
224 for (hdce
= firstDCE
; (hdce
); hdce
= dce
->hNext
)
226 if (!(dce
= (DCE
*) USER_HEAP_ADDR( hdce
))) return 0;
227 if (dce
->inUse
&& (dce
->hdc
== hdc
)) break;
231 if (dce
->type
== DCE_CACHE_DC
)
233 SetDCState( dce
->hdc
, defaultDCstate
);