1 /* mview.c -- File viewer -*- coding: euc-jp; -*-
2 Copyright (C) 2003, 2004
3 National Institute of Advanced Industrial Science and Technology (AIST)
4 Registration Number H15PRO112
6 This file is part of the m17n library.
8 The m17n library is free software; you can redistribute it and/or
9 modify it under the terms of the GNU Lesser General Public License
10 as published by the Free Software Foundation; either version 2.1 of
11 the License, or (at your option) any later version.
13 The m17n library is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 Lesser General Public License for more details.
18 You should have received a copy of the GNU Lesser General Public
19 License along with the m17n library; if not, write to the Free
20 Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
24 @enpage m17n-view view file
26 @section m17n-view-synopsis SYNOPSIS
28 m17n-view [ XT-OPTION ...] [ OPTION ... ] [ FILE ]
30 @section m17n-view-description DESCRIPTION
32 Display FILE on a window.
34 If FILE is omitted, the input is taken from standard input.
36 XT-OPTIONs are standard Xt arguments (e.g. -fn, -fg).
38 The following OPTIONs are available.
44 ENCODING is the encoding of FILE (defaults to UTF-8).
48 FONTSIZE is the fontsize in point. If omitted, it defaults to the
49 size of the default font defined in X resource.
62 @japage m17n-view ¥Õ¥¡¥¤¥ë¤ò¸«¤ë
64 @section m17n-view-synopsis SYNOPSIS
66 m17n-view [ XT-OPTION ...] [ OPTION ... ] [ FILE ]
68 @section m17n-view-description DESCRIPTION
70 FILE ¤ò¥¦¥£¥ó¥É¥¦¤Ëɽ¼¨¤¹¤ë¡£
72 FILE ¤¬¾Êά¤µ¤ì¤¿¾ì¹ç¤Ï¡¢É¸½àÆþÎϤ«¤é¤È¤ë¡£
74 XT-OPTIONs ¤Ï Xt ¤Îɸ½à¤Î°ú¿ô¤Ç¤¢¤ë¡£ (e.g. -fn, -fg).
76 °Ê²¼¤Î¥ª¥×¥·¥ç¥ó¤¬ÍøÍѤǤ¤ë¡£
82 ENCODING ¤Ï FILE ¤Î¥³¡¼¥É·Ï¤Ç¤¢¤ë¡£(¥Ç¥Õ¥©¥ë¥È¤Ï UTF-8)
86 FONTSIZE ¤Ï¥Õ¥©¥ó¥È¤ÎÂ礤µ¤ò¥Ý¥¤¥ó¥Èñ°Ì¤Ç¼¨¤·¤¿¤â¤Î¤Ç¤¢¤ë¡£¾Êά
87 ¤µ¤ì¤¿¾ì¹ç¤Ï¡¢X ¤Î¥ê¥½¡¼¥¹¤ÇÄêµÁ¤µ¤ì¤¿¥Ç¥Õ¥©¥ë¥È¥Õ¥©¥ó¥È¤ÎÂ礤µ¤È
92 ¥Ð¡¼¥¸¥ç¥óÈÖ¹æ¤òɽ¼¨¤¹¤ë¡£
96 ¤³¤Î¥á¥Ã¥»¡¼¥¸¤òɽ¼¨¤¹¤ë¡£
104 #ifdef HAVE_X11_XAW_COMMAND_H
106 #include <X11/Intrinsic.h>
107 #include <X11/StringDefs.h>
108 #include <X11/Shell.h>
110 #include <m17n-gui.h>
111 #include <m17n-misc.h>
114 #include <X11/Xaw/Form.h>
115 #include <X11/Xaw/Command.h>
116 #include <X11/Xaw/Viewport.h>
118 #define VERSION "1.3.4"
120 /* Global m17n variables. */
124 MDrawControl control;
127 /* Callback procedure for "quit". */
130 QuitProc (Widget w, XtPointer client_data, XtPointer call_data)
132 XtAppSetExitFlag (XtWidgetToApplicationContext (w));
136 /* Move POS to the next line head in M-text MT whose length is LEN.
137 If POS is already on the last line, set POS to LEN. */
139 #define NEXTLINE(pos, len) \
141 pos = mtext_character (mt, pos, len, '\n'); \
149 /* Action procedure for expose event. Redraw partial area of the
150 widget W. The area is specified in EVENT. */
153 ExposeProc (Widget w, XEvent *event, String *str, Cardinal *num)
155 XExposeEvent *expose = (XExposeEvent *) event;
156 int len = mtext_len (mt);
161 /* We must update the area between the Y-positions expose->y and
162 (expose->y + expose->height). We ignore X-positions. */
164 /* At first, find the line that occupies the Y-position expose->y.
165 That is the first line to draw. */
171 mdraw_text_extents (frame, mt, from, to, &control, NULL, NULL, &rect);
172 if (to == len || y + rect.height > expose->y)
176 /* The first character to draw is at position FROM. Remeber the
177 Y-position to start drawing. */
180 /* Next, find the line that occupies the Y-position (expose->y +
181 expose->height). That is the last line to draw. This time, we
182 enable caching to utilize it in the later drawing. */
184 control.disable_caching = 0;
185 while (to < len && y < expose->y + expose->height)
189 mdraw_text_extents (frame, mt, pos, to, &control, NULL, NULL, &rect);
193 /* It is decided that we must draw from FROM to the previous
195 mdraw_text_with_control (frame, (MDrawWindow) XtWindow (w),
196 0, yoff, mt, from, to, &control);
198 /* Disable caching again. */
199 control.disable_caching = 1;
201 /* If the widget was vertically enlarged too much, shrink it. */
202 if (metric.height < expose->y + expose->height)
206 XtSetArg (arg, XtNheight, metric.height);
207 XtSetValues (w, &arg, 0);
212 /* Print the usage of this program (the name is PROG), and exit with
216 help_exit (char *prog, int exit_code)
224 printf ("Usage: %s [ XT-OPTION ...] [ OPTION ...] [ FILE ]\n", prog);
225 printf ("Display FILE on a window.\n");
226 printf (" If FILE is omitted, the input is taken from standard input.\n");
227 printf (" XT-OPTIONs are standard Xt arguments (e.g. -fn, -fg).\n");
228 printf ("The following OPTIONs are available.\n");
229 printf (" %-13s %s", "-e ENCODING",
230 "ENCODING is the encoding of FILE (defaults to UTF-8).\n");
231 printf (" %-13s %s", "-s FONTSIZE",
232 "FONTSIZE is the fontsize in point.\n");
233 printf ("\t\tIf omitted, it defaults to the size\n");
234 printf ("\t\tof the default font defined in X resource.\n");
235 printf (" %-13s %s", "--version", "print version number\n");
236 printf (" %-13s %s", "-h, --help", "print this message\n");
241 /* Format MSG by FMT and print the result to the stderr, and exit. */
243 #define FATAL_ERROR(fmt, arg) \
245 fprintf (stderr, fmt, arg); \
250 /* Adjust FONTSIZE for the resolution of the screen of widget W. */
253 adjust_fontsize (Widget w, int fontsize)
255 Display *display = XtDisplay (w);
256 int screen_number = XScreenNumberOfScreen (XtScreen (w));
257 double pixels = DisplayHeight (display, screen_number);
258 double mm = DisplayHeightMM (display, screen_number);
260 return (fontsize * pixels * 25.4 / mm / 100);
265 main (int argc, char **argv)
267 XtAppContext context;
268 Widget shell, form, quit, viewport, text;
269 String quit_action = "<KeyPress>q: set() notify() unset()";
270 XtActionsRec actions[] = { {"Expose", ExposeProc} };
273 int viewport_width, viewport_height;
274 char *coding_name = NULL;
279 /* Open an application context. */
280 XtSetLanguageProc (NULL, NULL, NULL);
281 shell = XtOpenApplication (&context, "M17NView", NULL, 0, &argc, argv, NULL,
282 sessionShellWidgetClass, NULL, 0);
283 XtAppAddActions (context, actions, XtNumber (actions));
285 /* Parse the remaining command line arguments. */
286 for (i = 1; i < argc; i++)
288 if (! strcmp (argv[i], "--help")
289 || ! strcmp (argv[i], "-h"))
290 help_exit (argv[0], 0);
291 else if (! strcmp (argv[i], "--version"))
293 printf ("m17n-view (m17n library) %s\n", VERSION);
294 printf ("Copyright (C) 2003 AIST, JAPAN\n");
297 else if (! strcmp (argv[i], "-e"))
300 coding_name = argv[i];
302 else if (! strcmp (argv[i], "-s"))
308 FATAL_ERROR ("Invalid fontsize %s!\n", argv[i]);
309 fontsize = adjust_fontsize (shell, (int) (n * 10));
311 else if (argv[i][0] != '-')
313 fp = fopen (argv[i], "r");
315 FATAL_ERROR ("Fail to open the file %s!\n", argv[i]);
319 printf ("Unknown option: %s", argv[i]);
320 help_exit (argv[0], 1);
324 /* Initialize the m17n library. */
326 if (merror_code != MERROR_NONE)
327 FATAL_ERROR ("%s\n", "Fail to initialize the m17n library.");
329 /* Decide how to decode the input stream. */
332 coding = mconv_resolve_coding (msymbol (coding_name));
334 FATAL_ERROR ("Invalid coding: %s\n", coding_name);
337 coding = Mcoding_utf_8;
339 mt = mconv_decode_stream (coding, fp);
342 FATAL_ERROR ("%s\n", "Fail to decode the input file or stream!");
345 MPlist *param = mplist ();
346 MFace *face = mface ();
349 mface_put_prop (face, Msize, (void *) fontsize);
350 mplist_put (param, Mwidget, shell);
351 mplist_put (param, Mface, face);
352 frame = mframe (param);
353 m17n_object_unref (param);
354 m17n_object_unref (face);
357 /* Create this widget hierarchy.
358 Shell - form -+- quit
360 +- viewport - text */
362 form = XtCreateManagedWidget ("form", formWidgetClass, shell, NULL, 0);
363 XtSetArg (arg[0], XtNleft, XawChainLeft);
364 XtSetArg (arg[1], XtNright, XawChainLeft);
365 XtSetArg (arg[2], XtNtop, XawChainTop);
366 XtSetArg (arg[3], XtNbottom, XawChainTop);
367 XtSetArg (arg[4], XtNaccelerators, XtParseAcceleratorTable (quit_action));
368 quit = XtCreateManagedWidget ("quit", commandWidgetClass, form, arg, 5);
369 XtAddCallback (quit, XtNcallback, QuitProc, NULL);
371 viewport_width = (int) mframe_get_prop (frame, Mfont_width) * 80;
373 = ((int) mframe_get_prop (frame, Mfont_ascent)
374 + (int) mframe_get_prop (frame, Mfont_descent)) * 24;
375 XtSetArg (arg[0], XtNallowVert, True);
376 XtSetArg (arg[1], XtNforceBars, False);
377 XtSetArg (arg[2], XtNfromVert, quit);
378 XtSetArg (arg[3], XtNtop, XawChainTop);
379 XtSetArg (arg[4], XtNbottom, XawChainBottom);
380 XtSetArg (arg[5], XtNright, XawChainRight);
381 XtSetArg (arg[6], XtNwidth, viewport_width);
382 XtSetArg (arg[7], XtNheight, viewport_height);
383 viewport = XtCreateManagedWidget ("viewport", viewportWidgetClass, form,
386 /* Before creating the text widget, we must calculate the height of
387 the M-text to draw. */
388 control.two_dimensional = 1;
389 control.enable_bidi = 1;
390 control.disable_caching = 1;
391 control.max_line_width = viewport_width;
392 mdraw_text_extents (frame, mt, 0, mtext_len (mt), &control,
393 NULL, NULL, &metric);
396 /* Decide the size of the text widget. */
397 XtSetArg (arg[0], XtNwidth, viewport_width);
398 if (viewport_height > metric.height)
399 /* The outer viewport is tall enough. */
400 XtSetArg (arg[1], XtNheight, viewport_height);
401 else if (metric.height < 0x8000)
402 /* The M-text height is within the limit of X. */
403 XtSetArg (arg[1], XtNheight, metric.height);
405 /* We can't make such a tall widget. Truncate it. */
406 XtSetArg (arg[1], XtNheight, 0x7FFF);
408 /* We must provide our own expose event handler. */
409 XtSetArg (arg[2], XtNtranslations,
410 XtParseTranslationTable ((String) "<Expose>: Expose()"));
411 text = XtCreateManagedWidget ("text", simpleWidgetClass, viewport, arg, 3);
414 /* Realize the top widget, and dive into an even loop. */
415 XtInstallAllAccelerators (form, form);
416 XtRealizeWidget (shell);
417 XtAppMainLoop (context);
420 m17n_object_unref (mt);
421 m17n_object_unref (frame);
427 #else /* not HAVE_X11_XAW_COMMAND_H */
430 main (int argc, char **argv)
433 "Building of this program failed (lack of some header files)\n");
437 #endif /* not HAVE_X11_XAW_COMMAND_H */
439 #endif /* not FOR_DOXYGEN */