Uses Xrender extension to allow client side font rendering.
[wine] / graphics / escape.c
1 /*
2  * Escape() function.
3  *
4  * Copyright 1994  Bob Amstadt
5  * Copyright 2001  Alexandre Julliard
6  */
7
8 #include <string.h>
9 #include "windef.h"
10 #include "wingdi.h"
11 #include "gdi.h"
12 #include "debugtools.h"
13
14 DEFAULT_DEBUG_CHANNEL(driver);
15
16 /***********************************************************************
17  *            Escape  [GDI.38]
18  */
19 INT16 WINAPI Escape16( HDC16 hdc, INT16 escape, INT16 in_count,
20                        SEGPTR in_data, LPVOID out_data )
21 {
22     INT ret;
23
24     switch(escape)
25     {
26     /* Escape(hdc,CLIP_TO_PATH,LPINT16,NULL) */
27     /* Escape(hdc,DRAFTMODE,LPINT16,NULL) */
28     /* Escape(hdc,ENUMPAPERBINS,LPINT16,LPSTR); */
29     /* Escape(hdc,EPSPRINTING,LPINT16,NULL) */
30     /* Escape(hdc,EXT_DEVICE_CAPS,LPINT16,LPDWORD) */
31     /* Escape(hdc,GETCOLORTABLE,LPINT16,LPDWORD) */
32     /* Escape(hdc,MOUSETRAILS,LPINT16,NULL) */
33     /* Escape(hdc,POSTSCRIPT_IGNORE,LPINT16,NULL) */
34     /* Escape(hdc,QUERYESCSUPPORT,LPINT16,NULL) */
35     /* Escape(hdc,SET_ARC_DIRECTION,LPINT16,NULL) */
36     /* Escape(hdc,SET_POLY_MODE,LPINT16,NULL) */
37     /* Escape(hdc,SET_SCREEN_ANGLE,LPINT16,NULL) */
38     /* Escape(hdc,SET_SPREAD,LPINT16,NULL) */
39     case CLIP_TO_PATH:
40     case DRAFTMODE:
41     case ENUMPAPERBINS:
42     case EPSPRINTING:
43     case EXT_DEVICE_CAPS:
44     case GETCOLORTABLE:
45     case MOUSETRAILS:
46     case POSTSCRIPT_IGNORE:
47     case QUERYESCSUPPORT:
48     case SET_ARC_DIRECTION:
49     case SET_POLY_MODE:
50     case SET_SCREEN_ANGLE:
51     case SET_SPREAD:
52     {
53         INT16 *ptr = MapSL(in_data);
54         INT data = *ptr;
55         return Escape( hdc, escape, sizeof(data), (LPCSTR)&data, out_data );
56     }
57
58     /* Escape(hdc,ENABLEDUPLEX,LPUINT16,NULL) */
59     case ENABLEDUPLEX:
60     {
61         UINT16 *ptr = MapSL(in_data);
62         UINT data = *ptr;
63         return Escape( hdc, escape, sizeof(data), (LPCSTR)&data, NULL );
64     }
65
66     /* Escape(hdc,GETPHYSPAGESIZE,NULL,LPPOINT16) */
67     /* Escape(hdc,GETPRINTINGOFFSET,NULL,LPPOINT16) */
68     /* Escape(hdc,GETSCALINGFACTOR,NULL,LPPOINT16) */
69     case GETPHYSPAGESIZE:
70     case GETPRINTINGOFFSET:
71     case GETSCALINGFACTOR:
72     {
73         POINT16 *ptr = out_data;
74         POINT pt32;
75         ret = Escape( hdc, escape, 0, NULL, &pt32 );
76         ptr->x = pt32.x;
77         ptr->y = pt32.y;
78         return ret;
79     }
80
81     /* Escape(hdc,ENABLEPAIRKERNING,LPINT16,LPINT16); */
82     /* Escape(hdc,ENABLERELATIVEWIDTHS,LPINT16,LPINT16); */
83     /* Escape(hdc,SETCOPYCOUNT,LPINT16,LPINT16) */
84     /* Escape(hdc,SETKERNTRACK,LPINT16,LPINT16) */
85     /* Escape(hdc,SETLINECAP,LPINT16,LPINT16) */
86     /* Escape(hdc,SETLINEJOIN,LPINT16,LPINT16) */
87     /* Escape(hdc,SETMITERLIMIT,LPINT16,LPINT16) */
88     case ENABLEPAIRKERNING:
89     case ENABLERELATIVEWIDTHS:
90     case SETCOPYCOUNT:
91     case SETKERNTRACK:
92     case SETLINECAP:
93     case SETLINEJOIN:
94     case SETMITERLIMIT:
95     {
96         INT16 *new = MapSL(in_data);
97         INT16 *old = out_data;
98         INT out, in = *new;
99         ret = Escape( hdc, escape, sizeof(in), (LPCSTR)&in, &out );
100         *old = out;
101         return ret;
102     }
103
104     /* Escape(hdc,SETABORTPROC,ABORTPROC,NULL); */
105     case SETABORTPROC:
106         return SetAbortProc16( hdc, (ABORTPROC16)in_data );
107
108     /* Escape(hdc,STARTDOC,LPSTR,LPDOCINFO16);
109      * lpvOutData is actually a pointer to the DocInfo structure and used as
110      * a second input parameter */
111     case STARTDOC:
112         if (out_data)
113         {
114             ret = StartDoc16( hdc, out_data );
115             if (ret > 0) ret = StartPage( hdc );
116             return ret;
117         }
118         return Escape( hdc, escape, in_count, MapSL(in_data), NULL );
119
120     /* Escape(hdc,SET_BOUNDS,LPRECT16,NULL); */
121     /* Escape(hdc,SET_CLIP_BOX,LPRECT16,NULL); */
122     case SET_BOUNDS:
123     case SET_CLIP_BOX:
124     {
125         RECT16 *rc16 = MapSL(in_data);
126         RECT rc;
127         rc.left   = rc16->left;
128         rc.top    = rc16->top;
129         rc.right  = rc16->right;
130         rc.bottom = rc16->bottom;
131         return Escape( hdc, escape, sizeof(rc), (LPCSTR)&rc, NULL );
132     }
133
134     /* Escape(hdc,NEXTBAND,NULL,LPRECT16); */
135     case NEXTBAND:
136     {
137         RECT rc;
138         RECT16 *rc16 = out_data;
139         ret = Escape( hdc, escape, 0, NULL, &rc );
140         rc16->left   = rc.left;
141         rc16->top    = rc.top;
142         rc16->right  = rc.right;
143         rc16->bottom = rc.bottom;
144         return ret;
145     }
146
147     /* Escape(hdc,ABORTDOC,NULL,NULL); */
148     /* Escape(hdc,BANDINFO,BANDINFOSTRUCT*,BANDINFOSTRUCT*); */
149     /* Escape(hdc,BEGIN_PATH,NULL,NULL); */
150     /* Escape(hdc,DRAWPATTERNRECT,PRECT_STRUCT*,NULL); */
151     /* Escape(hdc,ENDDOC,NULL,NULL); */
152     /* Escape(hdc,END_PATH,PATHINFO,NULL); */
153     /* Escape(hdc,EXTTEXTOUT,EXTTEXT_STRUCT*,NULL); */
154     /* Escape(hdc,FLUSHOUTPUT,NULL,NULL); */
155     /* Escape(hdc,GETFACENAME,NULL,LPSTR); */
156     /* Escape(hdc,GETPAIRKERNTABLE,NULL,KERNPAIR*); */
157     /* Escape(hdc,GETSETPAPERBINS,BinInfo*,BinInfo*); */
158     /* Escape(hdc,GETSETPRINTORIENT,ORIENT*,NULL); */
159     /* Escape(hdc,GETSETSCREENPARAMS,SCREENPARAMS*,SCREENPARAMS*); */
160     /* Escape(hdc,GETTECHNOLOGY,NULL,LPSTR); */
161     /* Escape(hdc,GETTRACKKERNTABLE,NULL,KERNTRACK*); */
162     /* Escape(hdc,MFCOMMENT,LPSTR,NULL); */
163     /* Escape(hdc,NEWFRAME,NULL,NULL); */
164     /* Escape(hdc,PASSTHROUGH,LPSTR,NULL); */
165     /* Escape(hdc,RESTORE_CTM,NULL,NULL); */
166     /* Escape(hdc,SAVE_CTM,NULL,NULL); */
167     /* Escape(hdc,SETALLJUSTVALUES,EXTTEXTDATA*,NULL); */
168     /* Escape(hdc,SETCOLORTABLE,COLORTABLE_STRUCT*,LPDWORD); */
169     /* Escape(hdc,SET_BACKGROUND_COLOR,LPDWORD,LPDWORD); */
170     /* Escape(hdc,TRANSFORM_CTM,LPSTR,NULL); */
171     case ABORTDOC:
172     case BANDINFO:
173     case BEGIN_PATH:
174     case DRAWPATTERNRECT:
175     case ENDDOC:
176     case END_PATH:
177     case EXTTEXTOUT:
178     case FLUSHOUTPUT:
179     case GETFACENAME:
180     case GETPAIRKERNTABLE:
181     case GETSETPAPERBINS:
182     case GETSETPRINTORIENT:
183     case GETSETSCREENPARAMS:
184     case GETTECHNOLOGY:
185     case GETTRACKKERNTABLE:
186     case MFCOMMENT:
187     case NEWFRAME:
188     case PASSTHROUGH:
189     case RESTORE_CTM:
190     case SAVE_CTM:
191     case SETALLJUSTVALUES:
192     case SETCOLORTABLE:
193     case SET_BACKGROUND_COLOR:
194     case TRANSFORM_CTM:
195         /* pass it unmodified to the 32-bit function */
196         return Escape( hdc, escape, in_count, MapSL(in_data), out_data );
197
198     /* Escape(hdc,ENUMPAPERMETRICS,LPINT16,LPRECT16); */
199     /* Escape(hdc,GETEXTENDEDTEXTMETRICS,LPUINT16,EXTTEXTMETRIC*); */
200     /* Escape(hdc,GETEXTENTTABLE,LPSTR,LPINT16); */
201     /* Escape(hdc,GETSETPAPERMETRICS,LPRECT16,LPRECT16); */
202     /* Escape(hdc,GETVECTORBRUSHSIZE,LPLOGBRUSH16,LPPOINT16); */
203     /* Escape(hdc,GETVECTORPENSIZE,LPLOGPEN16,LPPOINT16); */
204     case ENUMPAPERMETRICS:
205     case GETEXTENDEDTEXTMETRICS:
206     case GETEXTENTTABLE:
207     case GETSETPAPERMETRICS:
208     case GETVECTORBRUSHSIZE:
209     case GETVECTORPENSIZE:
210     default:
211         FIXME("unknown/unsupported 16-bit escape %x (%d,%p,%p\n",
212               escape, in_count, MapSL(in_data), out_data );
213         return Escape( hdc, escape, in_count, MapSL(in_data), out_data );
214     }
215 }
216
217
218 /************************************************************************
219  *             Escape  [GDI32.@]
220  */
221 INT WINAPI Escape( HDC hdc, INT escape, INT in_count, LPCSTR in_data, LPVOID out_data )
222 {
223     INT ret;
224     POINT *pt;
225
226     switch (escape)
227     {
228     case ABORTDOC:
229         return AbortDoc( hdc );
230
231     case ENDDOC:
232         return EndDoc( hdc );
233
234     case GETPHYSPAGESIZE:
235         pt = out_data;
236         pt->x = GetDeviceCaps( hdc, PHYSICALWIDTH );
237         pt->y = GetDeviceCaps( hdc, PHYSICALHEIGHT );
238         return 1;
239
240     case GETPRINTINGOFFSET:
241         pt = out_data;
242         pt->x = GetDeviceCaps( hdc, PHYSICALOFFSETX );
243         pt->y = GetDeviceCaps( hdc, PHYSICALOFFSETY );
244         return 1;
245
246     case GETSCALINGFACTOR:
247         pt = out_data;
248         pt->x = GetDeviceCaps( hdc, SCALINGFACTORX );
249         pt->y = GetDeviceCaps( hdc, SCALINGFACTORY );
250         return 1;
251
252     case NEWFRAME:
253         return EndPage( hdc );
254
255     case SETABORTPROC:
256         return SetAbortProc( hdc, (ABORTPROC)in_data );
257
258     case STARTDOC:
259         {
260             DOCINFOA doc;
261             char *name = NULL;
262
263             /* in_data may not be 0 terminated so we must copy it */
264             if (in_data)
265             {
266                 name = HeapAlloc( GetProcessHeap(), 0, in_count+1 );
267                 memcpy( name, in_data, in_count );
268                 name[in_count] = 0;
269             }
270             /* out_data is actually a pointer to the DocInfo structure and used as
271              * a second input parameter */
272             if (out_data) doc = *(DOCINFOA *)out_data;
273             else
274             {
275                 doc.cbSize = sizeof(doc);
276                 doc.lpszOutput = NULL;
277                 doc.lpszDatatype = NULL;
278                 doc.fwType = 0;
279             }
280             doc.lpszDocName = name;
281             ret = StartDocA( hdc, &doc );
282             if (name) HeapFree( GetProcessHeap(), 0, name );
283             if (ret > 0) ret = StartPage( hdc );
284             return ret;
285         }
286
287     case QUERYESCSUPPORT:
288         {
289             INT *ptr = (INT *)in_data;
290             if (in_count < sizeof(INT)) return 0;
291             switch(*ptr)
292             {
293             case ABORTDOC:
294             case ENDDOC:
295             case GETPHYSPAGESIZE:
296             case GETPRINTINGOFFSET:
297             case GETSCALINGFACTOR:
298             case NEWFRAME:
299             case QUERYESCSUPPORT:
300             case SETABORTPROC:
301             case STARTDOC:
302                 return TRUE;
303             }
304             break;
305         }
306     }
307
308     /* if not handled internally, pass it to the driver */
309     return ExtEscape( hdc, escape, in_count, in_data, 0, out_data );
310 }
311
312
313 /******************************************************************************
314  *              ExtEscape       [GDI32.@]
315  *
316  * PARAMS
317  *    hdc         [I] Handle to device context
318  *    nEscape     [I] Escape function
319  *    cbInput     [I] Number of bytes in input structure
320  *    lpszInData  [I] Pointer to input structure
321  *    cbOutput    [I] Number of bytes in output structure
322  *    lpszOutData [O] Pointer to output structure
323  *
324  * RETURNS
325  *    Success: >0
326  *    Not implemented: 0
327  *    Failure: <0
328  */
329 INT WINAPI ExtEscape( HDC hdc, INT nEscape, INT cbInput, LPCSTR lpszInData,
330                       INT cbOutput, LPSTR lpszOutData )
331 {
332     INT ret = 0;
333     DC * dc = DC_GetDCPtr( hdc );
334     if (dc)
335     {
336         if (dc->funcs->pExtEscape)
337             ret = dc->funcs->pExtEscape( dc, nEscape, cbInput, lpszInData, cbOutput, lpszOutData );
338         GDI_ReleaseObj( hdc );
339     }
340     return ret;
341 }
342
343
344 /*******************************************************************
345  *      DrawEscape [GDI32.@]
346  *
347  *
348  */
349 INT WINAPI DrawEscape(HDC hdc, INT nEscape, INT cbInput, LPCSTR lpszInData)
350 {
351     FIXME("DrawEscape, stub\n");
352     return 0;
353 }