1 /**
2 *
3 * $Header: /cvsroot/lesstif/lesstif/lib/Xm-2.1/PrintShell.c,v 1.24 2002/04/13 11:08:48 amai Exp $
4 *
5 * Copyright � 2000,2001,2002 LessTif Development Team
6 *
7 * This file is part of the GNU LessTif Library.
8 *
9 * This library is free software; you can redistribute it and/or
10 * modify it under the terms of the GNU Library General Public
11 * License as published by the Free Software Foundation; either
12 * version 2 of the License, or (at your option) any later version.
13 *
14 * This library is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17 * Library General Public License for more details.
18 *
19 * You should have received a copy of the GNU Library General Public
20 * License along with this library; if not, write to the Free
21 * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
22 *
23 **/
24
25 static const char rcsid[] = "$Header: /cvsroot/lesstif/lesstif/lib/Xm-2.1/PrintShell.c,v 1.24 2002/04/13 11:08:48 amai Exp $";
26
27 #include <LTconfig.h>
28
29 /*
30 * Lots of stuff in this file is only compiled if we have the Xp library.
31 *
32 #ifdef HAVE_LIB_XP
33 */
34
35 #include <stdio.h>
36
37 #include <XmI/XmI.h>
38
39 #include <Xm/XmP.h>
40
41 #include <Xm/PrintSP.h> /* required in any case */
42 #ifdef HAVE_LIB_XP
43 #include <Xm/Print.h>
44 #endif
45
46 #include <XmI/DebugUtil.h>
47
48
49 /* Forward Declarations */
50 static void class_initialize(void);
51 static void class_part_initialize(WidgetClass w_class);
52 static void initialize(Widget request, Widget new_w,
53 ArgList args, Cardinal *num_args);
54 static void destroy(Widget w);
55 static void realize(Widget w, XtValueMask *value_mask,
56 XSetWindowAttributes *attributes);
57 static void resize(Widget w);
58 static Boolean set_values(Widget current, Widget request, Widget new_w,
59 ArgList args, Cardinal *num_args);
60 static void _XmPrintNotify(Widget w, XtPointer client, XEvent *evp, Boolean *cont);
61
62 #define Offset(field) XtOffsetOf(XmPrintShellRec, print.field)
63
64
65 /* Resources for the PrintShell class */
66 static XtResource resources[] =
67 {
68 {
69 XmNstartJobCallback, XmCCallback, XmRCallback,
70 sizeof(XtCallbackList), Offset(start_job_callback),
71 XmRImmediate, (XtPointer)NULL
72 },
73 {
74 XmNendJobCallback, XmCCallback, XmRCallback,
75 sizeof(XtCallbackList), Offset(end_job_callback),
76 XmRImmediate, (XtPointer)NULL
77 },
78 {
79 XmNpageSetupCallback, XmCCallback, XmRCallback,
80 sizeof(XtCallbackList), Offset(page_setup_callback),
81 XmRImmediate, (XtPointer)NULL
82 },
83 {
84 XmNpdmNotificationCallback, XmCCallback, XmRCallback,
85 sizeof(XtCallbackList), Offset(pdm_notification_callback),
86 XmRImmediate, (XtPointer)NULL
87 },
88 {
89 XmNminX, XmCMinX, XmRDimension,
90 sizeof(Dimension), Offset(min_x),
91 XmRImmediate, (XtPointer)NULL /* dynamic */
92 },
93 {
94 XmNminY, XmCMinY, XmRDimension,
95 sizeof(Dimension), Offset(min_y),
96 XmRImmediate, (XtPointer)NULL /* dynamic */
97 },
98 {
99 XmNmaxX, XmCMaxX, XmRDimension,
100 sizeof(Dimension), Offset(max_x),
101 XmRImmediate, (XtPointer)NULL /* dynamic */
102 },
103 {
104 XmNmaxY, XmCMaxY, XmRDimension,
105 sizeof(Dimension), Offset(max_y),
106 XmRImmediate, (XtPointer)NULL /* dynamic */
107 },
108 {
109 XmNdefaultPixmapResolution, XmCDefaultPixmapResolution, XmRShort,
110 sizeof(unsigned short), Offset(default_pixmap_resolution),
111 XmRImmediate, (XtPointer)100
112 },
113 };
114
115 static XtActionsRec actions[] =
116 {
117 #if 0
118 {"MenuShellPopdownOne", MenuShellPopdownOne},
119 #endif
120 {NULL, NULL}
121 };
122
123
124 static XmBaseClassExtRec _XmPrintShellCoreClassExtRec = {
125 /* next_extension */ NULL,
126 /* record_type */ NULLQUARK,
127 /* version */ XmBaseClassExtVersion,
128 /* size */ sizeof(XmBaseClassExtRec),
129 /* initialize_prehook */ NULL,
130 /* set_values_prehook */ NULL,
131 /* initialize_posthook */ NULL,
132 /* set_values_posthook */ NULL,
133 /* secondary_object_class */ NULL,
134 /* secondary_object_create */ NULL,
135 /* get_secondary_resources */ NULL,
136 /* fast_subclass */ { 0 },
137 /* get_values_prehook */ NULL,
138 /* get_values_posthook */ NULL,
139 /* class_part_init_prehook */ NULL,
140 /* class_part_init_posthook */ NULL,
141 /* ext_resources */ NULL,
142 /* compiled_ext_resources */ NULL,
143 /* num_ext_resources */ 0,
144 /* use_sub_resources */ False,
145 /* widget_navigable */ NULL,
146 /* focus_change */ NULL,
147 /* wrapper_data */ NULL
148 };
149
150 XmPrintShellClassRec xmPrintShellClassRec = {
151 /* Core class part */
152 {
153 /* superclass */ (WidgetClass) &applicationShellClassRec,
154 /* class_name */ "XmPrintShell",
155 /* widget_size */ sizeof(XmPrintShellRec),
156 /* class_initialize */ class_initialize,
157 /* class_part_initialize */ class_part_initialize,
158 /* class_inited */ False,
159 /* initialize */ initialize,
160 /* initialize_hook */ NULL,
161 /* realize */ realize,
162 /* actions */ actions,
163 /* num_actions */ XtNumber(actions),
164 /* resources */ resources,
165 /* num_resources */ XtNumber(resources),
166 /* xrm_class */ NULLQUARK,
167 /* compress_motion */ True,
168 /* compress_exposure */ XtExposeCompressMaximal,
169 /* compress_enterleave */ True,
170 /* visible_interest */ False,
171 /* destroy */ destroy,
172 /* resize */ resize,
173 /* expose */ XtInheritExpose,
174 /* set_values */ set_values,
175 /* set_values_hook */ NULL,
176 /* set_values_almost */ XtInheritSetValuesAlmost,
177 /* get_values_hook */ NULL,
178 /* accept_focus */ NULL,
179 /* version */ XtVersion,
180 /* callback offsets */ NULL,
181 /* tm_table */ NULL,
182 /* query_geometry */ NULL,
183 /* display_accelerator */ NULL,
184 /* extension */ (XtPointer)&_XmPrintShellCoreClassExtRec
185 },
186 /* Composite class part */
187 {
188 /* geometry manager */ XtInheritGeometryManager,
189 /* change_managed */ XtInheritChangeManaged,
190 /* insert_child */ XtInheritInsertChild,
191 /* delete_child */ XtInheritDeleteChild,
192 /* extension */ NULL,
193 },
194 /* Shell class part */
195 {
196 /* extension */ NULL,
197 },
198 /* WM Shell class part */
199 {
200 /* extension */ NULL,
201 },
202 /* VendorShell class part */
203 {
204 /* extension */ NULL,
205 },
206 /* TopLevelShell class part */
207 {
208 /* extension */ NULL,
209 },
210 /* ApplicationShell class part */
211 {
212 /* extension */ NULL,
213 },
214 {
215 /* ?? */ NULL,
216 },
217 };
218
219 WidgetClass xmPrintShellWidgetClass = (WidgetClass)&xmPrintShellClassRec;
220
221
222 static void
class_initialize(void)223 class_initialize(void)
224 {
225 _XmInitializeExtensions();
226
227 _XmPrintShellCoreClassExtRec.record_type = XmQmotif;
228 }
229
230
231 static void
class_part_initialize(WidgetClass widget_class)232 class_part_initialize(WidgetClass widget_class)
233 {
234 #if 0
235 _XmFastSubclassInit(widget_class, XmMENU_SHELL_BIT);
236 #endif
237 }
238
239 #ifdef HAVE_LIB_XP
240 /*
241 * This is a static table to keep the link between widgets and XPContexts.
242 * Yeah - this is probably not a very bright idea. Maybe it should also
243 * contain the Display.
244 */
245 static int nfields = 0;
246 typedef struct {
247 Widget w;
248 XPContext c;
249 } WidgetContext;
250 static WidgetContext *wctxt = NULL;
251
252
253 static void
_XmStoreWidgetContext(Widget w,XPContext c)254 _XmStoreWidgetContext(Widget w, XPContext c)
255 {
256 nfields++;
257 wctxt = (WidgetContext *)XtRealloc((XtPointer)wctxt, sizeof(WidgetContext) * nfields);
258 wctxt[nfields-1].w = w;
259 wctxt[nfields-1].c = c;
260 }
261
262 static Widget
_XmPrintContextToWidget(XPContext c)263 _XmPrintContextToWidget(XPContext c)
264 {
265 int i;
266
267 for (i=0; i<nfields; i++)
268 if (wctxt[i].c == c) {
269 return wctxt[i].w;
270 }
271 return NULL;
272 }
273
274 static XPContext
_XmPrintWidgetToContext(Widget w)275 _XmPrintWidgetToContext(Widget w)
276 {
277 int i;
278
279 for (i=0; i<nfields; i++)
280 if (wctxt[i].w == w) {
281 return wctxt[i].c;
282 }
283 return (XPContext)0;
284 }
285
286 static void
SelectNotify(Widget w,int * e,XtPointer * s,int n,XtPointer client)287 SelectNotify(Widget w, int *e, XtPointer *s, int n, XtPointer client)
288 {
289 XPContext c = XpGetContext(XtDisplay(w));
290
291 if (! c) {
292 _XmWarning(w, "XmPrintShell SelectNotify: no print context\n");
293 return;
294 }
295
296 XpSelectInput(XtDisplay(w), c, XPPrintMask | XPAttributeMask);
297
298 _XmStoreWidgetContext(w, c); /* Here ? */
299 }
300
301
302 static Boolean
DispatchEvent(XEvent * evp)303 DispatchEvent(XEvent *evp)
304 {
305 XPPrintEvent *e = (XPPrintEvent*)evp;
306
307 Widget w = _XmPrintContextToWidget(e->context);
308
309 #if 1 /* Only for debugging */
310 {
311 int error_base, event_base;
312
313 if (!XpQueryExtension(XtDisplay(w), &event_base, &error_base)) {
314 return False;
315 }
316
317 if (e->type == event_base + XPPrintNotify) {
318 switch (e->detail) {
319 case XPStartJobNotify:
320 DEBUGOUT(_LtDebug(__FILE__, w, "XmPrintShell-DispatchEvent XPStartJobNotify\n"));
321 break;
322 case XPEndJobNotify:
323 DEBUGOUT(_LtDebug(__FILE__, w, "XmPrintShell-DispatchEvent XPEndJobNotify\n"));
324 break;
325 case XPStartDocNotify:
326 DEBUGOUT(_LtDebug(__FILE__, w, "XmPrintShell-DispatchEvent XPStartDocNotify\n"));
327 break;
328 case XPStartPageNotify:
329 DEBUGOUT(_LtDebug(__FILE__, w, "XmPrintShell-DispatchEvent XPStartPageNotify\n"));
330 break;
331 case XPEndPageNotify:
332 DEBUGOUT(_LtDebug(__FILE__, w, "XmPrintShell-DispatchEvent XPEndPageNotify\n"));
333 break;
334 case XPEndDocNotify:
335 DEBUGOUT(_LtDebug(__FILE__, w, "XmPrintShell-DispatchEvent XPEndDocNotify\n"));
336 break;
337 default:
338 DEBUGOUT(_LtDebug(__FILE__, w, "XmPrintShell DispatchEvent\n"));
339 }
340 }
341 }
342 #endif
343
344 return XtDispatchEventToWidget(w, evp);
345 }
346 #endif /* HAVE_LIB_XP */
347
348
349 static void
initialize(Widget request,Widget new_w,ArgList args,Cardinal * num_args)350 initialize(Widget request, Widget new_w, ArgList args, Cardinal *num_args)
351 {
352 #ifdef HAVE_LIB_XP
353 int error_base, event_base;
354
355 DEBUGOUT(_LtDebug(__FILE__, new_w, "XmPrintShell Initialize\n"));
356
357 if (new_w->core.width == 0 || new_w->core.height == 0) {
358 new_w->core.width = 1000;
359 new_w->core.height = 1000; /* FIX ME */
360 }
361
362 if (!XpQueryExtension(XtDisplay(new_w), &event_base, &error_base)) {
363 DEBUGOUT(_LtDebug(__FILE__, new_w, "XmPrintShell initialize: fail !!\n"));
364 return;
365 }
366
367 DEBUGOUT(_LtDebug(__FILE__, new_w, "XmPrintShell Initialize event_base %d error_base %d\n",
368 event_base, error_base));
369
370 XtInsertEventTypeHandler(new_w,
371 event_base + XPPrintNotify,
372 (XtPointer)XPPrintMask,
373 _XmPrintNotify, NULL,
374 XtListTail);
375
376 XtRegisterExtensionSelector(XtDisplay(new_w),
377 event_base + XPPrintNotify,
378 event_base + XPAttributeNotify,
379 SelectNotify,
380 NULL);
381
382 (void) XtSetEventDispatcher(XtDisplay(new_w),
383 event_base + XPPrintNotify,
384 DispatchEvent);
385
386 PS_LastPage(new_w) = False;
387 #endif
388 }
389
390
391 static void
destroy(Widget w)392 destroy(Widget w)
393 {
394 DEBUGOUT(_LtDebug(__FILE__, w, "XmPrintShell Destroy\n"));
395 }
396
397
398 static void
resize(Widget w)399 resize(Widget w)
400 {
401 DEBUGOUT(_LtDebug(__FILE__, w, "XmPrintShell Resize\n"));
402 }
403
404
405 static void
realize(Widget w,XtValueMask * value_mask,XSetWindowAttributes * attributes)406 realize(Widget w, XtValueMask *value_mask, XSetWindowAttributes *attributes)
407 {
408 DEBUGOUT(_LtDebug(__FILE__, w, "XmPrintShell Realize\n"));
409 #if 1
410
411 #define superclass (&applicationShellClassRec)
412 (*superclass->core_class.realize) (w, value_mask, attributes);
413 #undef superclass
414
415 #endif
416 }
417
418
419 static Boolean
set_values(Widget current,Widget request,Widget new_w,ArgList args,Cardinal * num_args)420 set_values(Widget current, Widget request, Widget new_w,
421 ArgList args, Cardinal *num_args)
422 {
423 DEBUGOUT(_LtDebug(__FILE__, new_w, "XmPrintShell SetValues\n"));
424 return True;
425 }
426
427 #if 0
428 /*
429 * This isn't a Motif API.
430 */
431 extern Widget
432 XmCreatePrintShell(Widget parent, char *name, ArgList arglist, Cardinal argcount)
433 {
434 while (parent && !XtIsComposite(parent))
435 parent = XtParent(parent);
436
437 return XtCreatePopupShell(name, xmPrintShellWidgetClass, parent,
438 arglist, argcount);
439 }
440 #endif
441
442 #ifdef HAVE_LIB_XP
443 static void
_XmPrintNotify(Widget w,XtPointer client,XEvent * evp,Boolean * cont)444 _XmPrintNotify(Widget w, XtPointer client, XEvent *evp, Boolean *cont)
445 {
446 XPPrintEvent *e = (XPPrintEvent *)evp;
447 XmPrintShellCallbackStruct cbs;
448
449 switch (e->detail) {
450 case XPStartPageNotify:
451 DEBUGOUT(_LtDebug(__FILE__, w, "XPStartPageNotify\n"));
452
453 DEBUGOUT(_LtDebug(__FILE__, w, "XpEndPage\n"));
454 XpEndPage(XtDisplay(w));
455
456 if (PS_LastPage(w)) {
457 DEBUGOUT(_LtDebug(__FILE__, w, "XpEndJob\n"));
458 XpEndJob(XtDisplay(w));
459 }
460 break;
461 case XPEndPageNotify:
462 DEBUGOUT(_LtDebug(__FILE__, w, "XPEndPageNotify\n"));
463
464 if (! PS_LastPage(w)) {
465 DEBUGOUT(_LtDebug(__FILE__, w, "XpStartPage\n"));
466 XpStartPage(XtDisplay(w), XtWindow(w));
467
468 cbs.reason = XmCR_PAGE_SETUP;
469 cbs.event = evp;
470 cbs.detail = NULL;
471 cbs.context = 0;
472 cbs.last_page = False;
473 if (PS_PageSetupCallback(w))
474 XtCallCallbackList(w, PS_PageSetupCallback(w), &cbs);
475 PS_LastPage(w) = cbs.last_page;
476 }
477 break;
478 case XPStartDocNotify:
479 DEBUGOUT(_LtDebug(__FILE__, w, "XPStartDocNotify\n"));
480 break;
481 case XPEndDocNotify:
482 DEBUGOUT(_LtDebug(__FILE__, w, "XPEndDocNotify\n"));
483 break;
484 case XPStartJobNotify:
485 DEBUGOUT(_LtDebug(__FILE__, w, "XPStartJobNotify\n"));
486 PS_LastPage(w) = False;
487
488 cbs.reason = XmCR_START_JOB;
489 cbs.event = evp;
490 cbs.detail = NULL;
491 cbs.context = _XmPrintWidgetToContext(w);
492 cbs.last_page = False;
493
494 if (PS_StartJobCallback(w))
495 XtCallCallbackList(w, PS_StartJobCallback(w), &cbs);
496
497 #if 0
498 DEBUGOUT(_LtDebug(__FILE__, w, "XpStartDoc\n"));
499 XpStartDoc(XtDisplay(w), XPDocNormal);
500 #endif
501
502 /* Copied from EndPage section */
503 if (! cbs.last_page) {
504 DEBUGOUT(_LtDebug(__FILE__, w, "XpStartPage\n"));
505 XpStartPage(XtDisplay(w), XtWindow(w));
506
507 cbs.reason = XmCR_PAGE_SETUP;
508 cbs.event = evp;
509 cbs.detail = NULL;
510 cbs.context = _XmPrintWidgetToContext(w);
511 cbs.last_page = False;
512 if (PS_PageSetupCallback(w))
513 XtCallCallbackList(w, PS_PageSetupCallback(w), &cbs);
514
515 PS_LastPage(w) = cbs.last_page;
516 #if 0
517 if (cbs.last_page) {
518 DEBUGOUT(_LtDebug(__FILE__, w, "XpEndPage\n"));
519 XpEndPage(XtDisplay(w));
520 }
521 #endif
522 }
523 break;
524 case XPEndJobNotify:
525 DEBUGOUT(_LtDebug(__FILE__, w, "XPEndJobNotify\n"));
526 cbs.reason = XmCR_END_JOB;
527 cbs.event = evp;
528 cbs.detail = NULL;
529 cbs.context = 0;
530 cbs.last_page = False;
531
532 if (PS_EndJobCallback(w))
533 XtCallCallbackList(w, PS_EndJobCallback(w), &cbs);
534 break;
535 default:
536 DEBUGOUT(_LtDebug(__FILE__, w, "_XmPrintNotify(default)\n"));
537 break;
538 }
539 }
540 #endif /* HAVE_LIB_XP */
541