2 * Copyright 1991 Massachusetts Institute of Technology
4 * Permission to use, copy, modify, distribute, and sell this software and its
5 * documentation for any purpose is hereby granted without fee, provided that
6 * the above copyright notice appear in all copies and that both that
7 * copyright notice and this permission notice appear in supporting
8 * documentation, and that the name of M.I.T. not be used in advertising or
9 * publicity pertaining to distribution of the software without specific,
10 * written prior permission. M.I.T. makes no representations about the
11 * suitability of this software for any purpose. It is provided "as is"
12 * without express or implied warranty.
14 * M.I.T. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL
15 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL M.I.T.
16 * BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
17 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
18 * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
19 * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
25 * Display ditroff output in an X window
30 static char rcsid
[] = "$XConsortium: xditview.c,v 1.17 89/12/10 17:05:08 rws Exp $";
34 #include <X11/Xatom.h>
37 #include <X11/Intrinsic.h>
38 #include <X11/StringDefs.h>
39 #include <X11/Shell.h>
40 #include <X11/Xaw/Paned.h>
41 #include <X11/Xaw/Viewport.h>
42 #include <X11/Xaw/Box.h>
43 #include <X11/Xaw/Command.h>
44 #include <X11/Xaw/Dialog.h>
45 #include <X11/Xaw/Label.h>
46 #include <X11/Xaw/SimpleMenu.h>
47 #include <X11/Xaw/SmeBSB.h>
54 #include "xdit_mask.bm"
60 static String fallback_resources
[] = {
61 #include "GXditview-ad.h"
65 static struct app_resources
{
70 #define offset(field) XtOffset(struct app_resources *, field)
72 /* Application resources. */
74 static XtResource resources
[] = {
75 {"printCommand", "PrintCommand", XtRString
, sizeof(char*),
76 offset(print_command
), XtRString
, NULL
},
77 {"filename", "Filename", XtRString
, sizeof(char*),
78 offset(filename
), XtRString
, NULL
},
83 /* Command line options table. Only resources are entered here...there is a
84 pass over the remaining options after XtParseCommand is let loose. */
86 static XrmOptionDescRec options
[] = {
87 {"-page", "*dvi.pageNumber", XrmoptionSepArg
, NULL
},
88 {"-backingStore", "*dvi.backingStore", XrmoptionSepArg
, NULL
},
89 {"-resolution", "*dvi.resolution", XrmoptionSepArg
, NULL
},
90 {"-printCommand", ".printCommand", XrmoptionSepArg
, NULL
},
91 {"-filename", ".filename", XrmoptionSepArg
, NULL
},
92 {"-noPolyText", "*dvi.noPolyText", XrmoptionNoArg
, "TRUE"},
95 static char current_print_command
[1024];
97 static char current_file_name
[1024];
98 static FILE *current_file
;
101 * Report the syntax for calling xditview.
108 (void) printf ("Usage: %s [-fg <color>] [-bg <color>]\n", call
);
109 (void) printf (" [-bd <color>] [-bw <pixels>] [-help]\n");
110 (void) printf (" [-display displayname] [-geometry geom]\n");
111 (void) printf (" [-page <page-number>] [-backing <backing-store>]\n");
112 (void) printf (" [-resolution <res>] [-print <command>]\n");
113 (void) printf (" [-filename <file>] [filename]\n\n");
117 static void NewFile (), SetPageNumber ();
118 static Widget toplevel
, paned
, viewport
, dvi
;
120 static Widget simpleMenu
;
122 static void NextPage(), PreviousPage(), SelectPage(), OpenFile(), Quit();
125 static struct menuEntry
{
129 "nextPage", NextPage
,
130 "previousPage", PreviousPage
,
131 "selectPage", SelectPage
,
133 "openFile", OpenFile
,
137 static void NextPageAction(), PreviousPageAction(), SelectPageAction();
138 static void OpenFileAction(), QuitAction();
139 static void AcceptAction(), CancelAction();
140 static void PrintAction();
141 static void RerasterizeAction();
143 XtActionsRec xditview_actions
[] = {
144 "NextPage", NextPageAction
,
145 "PreviousPage", PreviousPageAction
,
146 "SelectPage", SelectPageAction
,
147 "Print", PrintAction
,
148 "OpenFile", OpenFileAction
,
149 "Rerasterize", RerasterizeAction
,
151 "Accept", AcceptAction
,
152 "Cancel", CancelAction
,
155 #define MenuNextPage 0
156 #define MenuPreviousPage 1
157 #define MenuSelectPage 2
159 #define MenuOpenFile 4
162 static char pageLabel
[256] = "Page <none>";
170 static Arg labelArgs
[] = {
171 {XtNlabel
, (XtArgVal
) pageLabel
},
173 XtAppContext xtcontext
;
176 Arg pageNumberArgs
[1];
179 toplevel
= XtAppInitialize(&xtcontext
, "GXditview",
180 options
, XtNumber (options
),
181 &argc
, argv
, fallback_resources
, NULL
, 0);
183 || (argc
== 2 && (!strcmp(argv
[1], "-help")
184 || !strcmp(argv
[1], "--help"))))
187 XtGetApplicationResources(toplevel
, (XtPointer
)&app_resources
,
188 resources
, XtNumber(resources
),
190 if (app_resources
.print_command
)
191 strcpy(current_print_command
, app_resources
.print_command
);
193 XtAppAddActions(xtcontext
, xditview_actions
, XtNumber (xditview_actions
));
195 XtSetArg (topLevelArgs
[0], XtNiconPixmap
,
196 XCreateBitmapFromData (XtDisplay (toplevel
),
197 XtScreen(toplevel
)->root
,
198 xdit_bits
, xdit_width
, xdit_height
));
200 XtSetArg (topLevelArgs
[1], XtNiconMask
,
201 XCreateBitmapFromData (XtDisplay (toplevel
),
202 XtScreen(toplevel
)->root
,
204 xdit_mask_width
, xdit_mask_height
));
205 XtSetValues (toplevel
, topLevelArgs
, 2);
210 * create the menu and insert the entries
212 simpleMenu
= XtCreatePopupShell ("menu", simpleMenuWidgetClass
, toplevel
,
214 for (i
= 0; i
< XtNumber (menuEntries
); i
++) {
215 entry
= XtCreateManagedWidget(menuEntries
[i
].name
,
216 smeBSBObjectClass
, simpleMenu
,
218 XtAddCallback(entry
, XtNcallback
, menuEntries
[i
].function
, NULL
);
221 paned
= XtCreateManagedWidget("paned", panedWidgetClass
, toplevel
,
223 viewport
= XtCreateManagedWidget("viewport", viewportWidgetClass
, paned
,
225 dvi
= XtCreateManagedWidget ("dvi", dviWidgetClass
, viewport
, NULL
, 0);
226 page
= XtCreateManagedWidget ("label", labelWidgetClass
, paned
,
227 labelArgs
, XtNumber (labelArgs
));
228 XtSetArg (pageNumberArgs
[0], XtNpageNumber
, &page_number
);
229 XtGetValues (dvi
, pageNumberArgs
, 1);
232 /* NewFile modifies current_file_name, so do this here. */
233 if (app_resources
.filename
)
234 strcpy(current_file_name
, app_resources
.filename
);
235 XtRealizeWidget (toplevel
);
237 SetPageNumber (page_number
);
238 XtAppMainLoop(xtcontext
);
243 SetPageNumber (number
)
246 int actual_number
, last_page
;
248 XtSetArg (arg
[0], XtNpageNumber
, number
);
249 XtSetValues (dvi
, arg
, 1);
250 XtSetArg (arg
[0], XtNpageNumber
, &actual_number
);
251 XtSetArg (arg
[1], XtNlastPageNumber
, &last_page
);
252 XtGetValues (dvi
, arg
, 2);
253 if (actual_number
== 0)
254 sprintf (pageLabel
, "Page <none>");
255 else if (last_page
> 0)
256 sprintf (pageLabel
, "Page %d of %d", actual_number
, last_page
);
258 sprintf (pageLabel
, "Page %d", actual_number
);
259 XtSetArg (arg
[0], XtNlabel
, pageLabel
);
260 XtSetValues (page
, arg
, 1);
264 SelectPageNumber (number_string
)
267 SetPageNumber (atoi(number_string
));
270 static int hadFile
= 0;
282 if (!strcmp (current_file_name
, "-"))
284 else if (current_file_name
[0] == '|')
285 pclose (current_file
);
287 fclose (current_file
);
289 if (!strcmp (name
, "-"))
291 else if (name
[0] == '|')
292 new_file
= popen (name
+1, "r");
294 new_file
= fopen (name
, "r");
298 /* XXX display error message */
301 XtSetArg (arg
[0], XtNfile
, new_file
);
302 XtSetArg (arg
[1], XtNseek
, seek
);
303 XtSetValues (dvi
, arg
, 2);
304 if (hadFile
|| name
[0] != '-' || name
[1] != '\0') {
305 XtSetArg (arg
[0], XtNtitle
, name
);
306 if (name
[0] != '/' && (n
= strrchr (name
, '/')))
310 XtSetArg (arg
[1], XtNiconName
, n
);
311 XtSetValues (toplevel
, arg
, 2);
314 SelectPageNumber ("1");
315 strcpy (current_file_name
, name
);
316 current_file
= new_file
;
319 static char fileBuf
[1024];
321 ResetMenuEntry (entry
)
326 XtSetArg (arg
[0], XtNpopupOnEntry
, entry
);
327 XtSetValues (XtParent(entry
) , arg
, (Cardinal
) 1);
333 NextPage (entry
, name
, data
)
338 ResetMenuEntry (entry
);
347 XtSetArg (args
[0], XtNpageNumber
, &number
);
348 XtGetValues (dvi
, args
, 1);
349 SetPageNumber (number
+1);
355 PreviousPage (entry
, name
, data
)
359 PreviousPageAction ();
360 ResetMenuEntry (entry
);
364 PreviousPageAction ()
369 XtSetArg (args
[0], XtNpageNumber
, &number
);
370 XtGetValues (dvi
, args
, 1);
371 SetPageNumber (number
-1);
377 SelectPage (entry
, name
, data
)
382 ResetMenuEntry (entry
);
388 MakePrompt (toplevel
, "Page number", SelectPageNumber
, "");
397 #ifdef SIGNALRETURNSINT
402 /* Avoid dieing because of an invalid command. */
403 handler
= signal(SIGPIPE
, SIG_IGN
);
405 print_file
= popen(name
, "w");
407 /* XXX print error message */
409 DviSaveToFile(dvi
, print_file
);
411 signal(SIGPIPE
, handler
);
412 strcpy(current_print_command
, name
);
421 if (current_file_name
[0] == 0) {
422 /* XXX display an error message */
425 XtSetArg (args
[0], XtNpageNumber
, &number
);
426 XtGetValues (dvi
, args
, 1);
427 NewFile(current_file_name
);
428 SetPageNumber (number
);
434 Print (entry
, name
, data
)
439 ResetMenuEntry (entry
);
445 if (current_print_command
[0])
446 strcpy (fileBuf
, current_print_command
);
449 MakePrompt (toplevel
, "Print command:", DoPrint
, fileBuf
);
456 OpenFile (entry
, name
, data
)
461 ResetMenuEntry (entry
);
467 if (current_file_name
[0])
468 strcpy (fileBuf
, current_file_name
);
471 MakePrompt (toplevel
, "File to open:", NewFile
, fileBuf
);
477 Quit (entry
, closure
, data
)
479 caddr_t closure
, data
;
490 Widget promptShell
, promptDialog
;
491 void (*promptfunction
)();
495 void CancelAction (widget
, event
, params
, num_params
)
499 Cardinal
*num_params
;
502 XtSetKeyboardFocus(toplevel
, (Widget
) None
);
503 XtDestroyWidget(promptShell
);
504 promptShell
= (Widget
) 0;
509 void AcceptAction (widget
, event
, params
, num_params
)
513 Cardinal
*num_params
;
515 (*promptfunction
)(XawDialogGetValueString(promptDialog
));
516 CancelAction (widget
, event
, params
, num_params
);
519 MakePrompt(centerw
, prompt
, func
, def
)
525 static Arg dialogArgs
[] = {
531 Position source_x
, source_y
;
532 Position dest_x
, dest_y
;
533 Dimension center_width
, center_height
;
534 Dimension prompt_width
, prompt_height
;
537 CancelAction ((Widget
)NULL
, (XEvent
*) 0, (String
*) 0, (Cardinal
*) 0);
538 promptShell
= XtCreatePopupShell ("promptShell", transientShellWidgetClass
,
539 toplevel
, NULL
, (Cardinal
) 0);
540 dialogArgs
[0].value
= (XtArgVal
)prompt
;
541 dialogArgs
[1].value
= (XtArgVal
)def
;
542 promptDialog
= XtCreateManagedWidget( "promptDialog", dialogWidgetClass
,
543 promptShell
, dialogArgs
, XtNumber (dialogArgs
));
544 XawDialogAddButton(promptDialog
, "accept", NULL
, (caddr_t
) 0);
545 XawDialogAddButton(promptDialog
, "cancel", NULL
, (caddr_t
) 0);
546 valueWidget
= XtNameToWidget (promptDialog
, "value");
548 XtSetArg (valueArgs
[0], XtNresizable
, TRUE
);
549 XtSetValues (valueWidget
, valueArgs
, 1);
551 * as resizable isn't set until just above, the
552 * default value will be displayed incorrectly.
553 * rectify the situation by resetting the values
555 XtSetValues (promptDialog
, dialogArgs
, XtNumber (dialogArgs
));
557 XtSetKeyboardFocus (promptDialog
, valueWidget
);
558 XtSetKeyboardFocus (toplevel
, valueWidget
);
559 XtRealizeWidget (promptShell
);
561 * place the widget in the center of the "parent"
563 XtSetArg (centerArgs
[0], XtNwidth
, ¢er_width
);
564 XtSetArg (centerArgs
[1], XtNheight
, ¢er_height
);
565 XtGetValues (centerw
, centerArgs
, 2);
566 XtSetArg (centerArgs
[0], XtNwidth
, &prompt_width
);
567 XtSetArg (centerArgs
[1], XtNheight
, &prompt_height
);
568 XtGetValues (promptShell
, centerArgs
, 2);
569 source_x
= (center_width
- prompt_width
) / 2;
570 source_y
= (center_height
- prompt_height
) / 3;
571 XtTranslateCoords (centerw
, source_x
, source_y
, &dest_x
, &dest_y
);
572 XtSetArg (centerArgs
[0], XtNx
, dest_x
);
573 XtSetArg (centerArgs
[1], XtNy
, dest_y
);
574 XtSetValues (promptShell
, centerArgs
, 2);
575 XtMapWidget(promptShell
);
576 promptfunction
= func
;
590 c-continued-statement-offset: 4
594 c-tab-always-indent: nil