Back to index

tetex-bin  3.0
xm_prefs_page.c
Go to the documentation of this file.
00001 /*
00002  * Copyright (c) 2004 Stefan Ulrich
00003  *
00004  * Permission is hereby granted, free of charge, to any person obtaining a copy
00005  * of this software and associated documentation files (the "Software"), to
00006  * deal in the Software without restriction, including without limitation the
00007  * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
00008  * sell copies of the Software, and to permit persons to whom the Software is
00009  * furnished to do so, subject to the following conditions:
00010  *
00011  * The above copyright notice and this permission notice shall be included in
00012  * all copies or substantial portions of the Software.
00013  *
00014  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
00015  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
00016  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
00017  * PAUL VOJTA OR ANY OTHER AUTHOR OF THIS SOFTWARE BE LIABLE FOR ANY CLAIM,
00018  * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
00019  * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
00020  * OTHER DEALINGS IN THE SOFTWARE.
00021  *
00022  */
00023 
00024 /*
00025  * Panel 4 (Paper size) for xdvik preferences dialog.
00026  */
00027 
00028 #include "xdvi-config.h"
00029 #include "xdvi.h"
00030 
00031 #include "x_util.h"
00032 #include "xm_colorsel.h"
00033 #include "topic-window.h"
00034 #include "util.h"
00035 #include "events.h"
00036 #include "statusline.h"
00037 
00038 #include "xm_prefsP.h"
00039 #include "xm_prefs_page.h"
00040 #include "my-snprintf.h"
00041 
00042 #ifdef MOTIF /* entire file */
00043 
00044 #include <X11/Xatom.h>
00045 
00046 #include <Xm/Xm.h>
00047 #include <Xm/Protocols.h>
00048 #include <Xm/DialogS.h>
00049 #include <Xm/LabelG.h>
00050 #include <Xm/PushB.h>
00051 #include <Xm/PushBG.h>
00052 #include <Xm/Form.h>
00053 #include <Xm/Frame.h>
00054 #include <Xm/PanedW.h>
00055 #include <Xm/DrawnB.h>
00056 #include <Xm/RowColumn.h>
00057 #include <Xm/Scale.h>
00058 #include <Xm/ToggleBG.h>
00059 #include <Xm/Text.h>
00060 #include <Xm/TextF.h>
00061 #include <Xm/CascadeBG.h>
00062 
00063 #if XmVersion >= 2000 && !defined(LESSTIF_VERSION)
00064 /* spinbox only available with Motif 2.0; the lesstif version (as of 0.93) looks like shit */
00065 #include <Xm/SpinB.h>
00066 #define USE_SPINBOX 1
00067 #else
00068 #define USE_SPINBOX 0
00069 #endif
00070 
00071 /*
00072  * Handy defaults
00073  */
00074 static Arg one_of_many = { XmNindicatorType, XmONE_OF_MANY };
00075 static Arg n_of_many = { XmNindicatorType, XmN_OF_MANY };
00076 static Arg frame_title = { XmNchildType, XmFRAME_TITLE_CHILD };
00077 static Arg one_col[] = {
00078     { XmNpacking, XmPACK_TIGHT },
00079     { XmNnumColumns, 1 },
00080     { XmNorientation, XmVERTICAL }
00081 };
00082 
00083 
00084 /* this is a small selection from the paper types in xdvi.c
00085  * (only the more frequenlty used ones)
00086  */
00087 static struct paper_info {
00088     const char *format;
00089     const char *resource_format;
00090     const char *size;
00091     const char *landscape_size;
00092 } papersizes[] = {
00093     { "US (Letter)", "us",         "8.5x11in",   "11x8.5in"    },
00094     { "Tabloid",     "tabloid",    "11x17in",    "17x11in"     },     /* dvips compatibility */
00095     { "Legal",              "legal",      "8.5x14in",   "14x8.5in"    },
00096     { "A0",          "a0",         "841x1189mm", "1189x841mm"  },
00097     { "A1",          "a1",         "594x841mm",  "841x594mm"   },
00098     { "A2",          "a2",         "420x594mm",  "594x420mm"   },
00099     { "A3",          "a3",         "297x420mm",  "420x297mm"   },
00100     { "A4",          "a4",         "210x297mm",  "297x210mm"   },
00101     { "A5",          "a5",         "148x210mm",  "210x148mm"   },
00102     { "B5",          "b5",         "176x250mm",  "250x176mm"   },
00103     { "B6",          "b6",         "125x176mm",  "176x125mm"   },
00104     { "B7",          "b7",         "88x125mm",   "125x88mm"    },
00105     { NULL,          NULL,         NULL,         NULL          } /* terminate */
00106 };
00107 
00108 void update_preferences_windowsize(void)
00109 {
00110     Widget shell, button;
00111 
00112     /* it's not an error if the prefs dialog doesn't exist yet */
00113     if (get_widget_by_name(&shell, globals.widgets.top_level, Xdvi_PREFS_DIALOG_NAME, False)
00114        && get_widget_by_name(&button, shell, Xdvi_REMEMBER_WINDOWSIZE_STR, True)) {
00115        XmToggleButtonGadgetSetState(button, resource.remember_windowsize, False);
00116     }
00117 }
00118 
00119 void update_preferences_shrink(void)
00120 {
00121     Widget shell, text;
00122 
00123     if (get_widget_by_name(&shell, globals.widgets.top_level, Xdvi_PREFS_DIALOG_NAME, False)
00124        && get_widget_by_name(&text, shell, Xdvi_SHRINK_TEXT, True)) {
00125        char buf[LENGTH_OF_INT];
00126        SNPRINTF(buf, LENGTH_OF_INT, "%d", resource.shrinkfactor);
00127 #if USE_SPINBOX
00128        XmTextFieldSetString(text, buf);
00129        XtVaSetValues(text, XmNposition, resource.shrinkfactor, NULL);
00130 #else
00131        XtVaSetValues(text, XmNvalue, buf, NULL);
00132 #endif
00133     }
00134 }
00135 
00136 static void
00137 landscape_cb(Widget w, XtPointer client_data, XtPointer call_data)
00138 {
00139     struct topic_info *tinfo  = (struct topic_info *)client_data;
00140     struct prefs_choice *prefs = (struct prefs_choice *)tinfo->data;
00141     Widget portrait_b, landscape_b;
00142     Boolean landscape = False, is_set;
00143     static char *paper_option = NULL;
00144     Boolean match = False;
00145     int i;
00146 
00147     UNUSED(call_data);
00148     
00149     for (i = 0; papersizes[i].format != NULL; i++) {
00150        /* ignore final `r' when comparing */
00151        if (strncmp(resource.paper,
00152                   papersizes[i].resource_format,
00153                   strlen(papersizes[i].resource_format)) == 0) {
00154            const char *ptr;
00155            match = True;
00156            if (strcmp(resource.paper, "letter") == 0) /* special case */
00157               ptr = "us";
00158            else
00159               ptr = papersizes[i].resource_format;
00160            free(paper_option);
00161            paper_option = xstrdup(ptr);
00162            break;
00163        }
00164     }
00165 
00166     if (!match) {
00167        XDVI_ERROR((stderr, "paper resource `%s' not found in list!\n", resource.paper));
00168        return;
00169     }
00170 
00171     if (get_widget_by_name(&portrait_b, tinfo->shell, Xdvi_PAPER_PORTRAIT_STR, True)
00172        && get_widget_by_name(&landscape_b, tinfo->shell, Xdvi_PAPER_LANDSCAPE_STR, True)) {
00173 
00174        if (w == portrait_b) {
00175            XtVaGetValues(portrait_b, XmNset, &is_set, NULL);
00176            landscape = !is_set;
00177        }
00178        else {
00179            XtVaGetValues(landscape_b, XmNset, &is_set, NULL);
00180            landscape = is_set;
00181        }
00182 
00183 /*     fprintf(stderr, "++++++++ CALLBACK: setting portrait to %s, landscape to %s\n", */
00184 /*            landscape ? "False" : "True", */
00185 /*            landscape ? "True" : "False"); */
00186        
00187        XmToggleButtonGadgetSetState(portrait_b, !landscape, False);
00188        XmToggleButtonGadgetSetState(landscape_b, landscape, False);
00189     }
00190 
00191     if (landscape) {
00192        paper_option = xstrcat(paper_option, "r");
00193     }
00194 
00195     resource.paper = paper_option;
00196     store_preference(&(prefs->db), "paper", "%s", paper_option);
00197 }
00198 
00199 static void
00200 select_cb(Widget w, XtPointer client_data, XtPointer call_data)
00201 {
00202     struct topic_info *tinfo  = (struct topic_info *)client_data;
00203     struct prefs_choice *prefs = (struct prefs_choice *)tinfo->data;
00204 
00205     XmString str;
00206     char *choice;
00207     int i;
00208     static char *curr_choice= NULL;
00209     Boolean landscape = False;
00210     
00211     UNUSED(call_data);
00212     
00213     XtVaGetValues(w, XmNlabelString, &str, NULL);
00214     XmStringGetLtoR(str, G_charset, &choice);
00215 
00216     if (strlen(resource.paper) > 0 &&
00217        strcmp(resource.paper, "letter") != 0 &&
00218        resource.paper[strlen(resource.paper) - 1] == 'r')
00219        landscape = True;
00220     
00221     free(curr_choice);
00222     curr_choice = NULL;
00223     for (i = 0; papersizes[i].format != NULL; i++) {
00224        if (strcmp(choice, papersizes[i].format) == 0) {
00225            curr_choice = xstrdup(papersizes[i].resource_format);
00226        }
00227     }
00228     if (curr_choice == NULL) {
00229        XDVI_ERROR((stderr, "choice`%s' not found in list!\n", choice));
00230        return;
00231     }
00232 
00233     if (landscape) {
00234        curr_choice = xstrcat(curr_choice, "r");
00235     }
00236 
00237     resource.paper = curr_choice;
00238     store_preference(&(prefs->db), "paper", "%s", curr_choice);
00239 }
00240 
00241 void
00242 update_preferences_paper(void)
00243 {
00244     Widget shell, portrait_button, landscape_button, sizes_menu, sizes_cascade;
00245     Boolean landscape = False;
00246 
00247     /* it's not an error if the prefs dialog doesn't exist yet */
00248     if (get_widget_by_name(&shell, globals.widgets.top_level, Xdvi_PREFS_DIALOG_NAME, False)
00249        && get_widget_by_name(&portrait_button, shell, Xdvi_PAPER_PORTRAIT_STR, True)
00250        && get_widget_by_name(&landscape_button, shell, Xdvi_PAPER_LANDSCAPE_STR, True)
00251        && get_widget_by_name(&sizes_menu, shell, Xdvi_PAPER_MENU, True)
00252        && get_widget_by_name(&sizes_cascade, shell, Xdvi_PAPER_CASCADE, True)) {
00253 
00254        int i;
00255        Widget sizes_button;
00256        
00257        if (strlen(resource.paper) > 0 &&
00258            strcmp(resource.paper, "letter") != 0 &&
00259            resource.paper[strlen(resource.paper) - 1] == 'r') {
00260 
00261            landscape = True;
00262        }
00263 
00264 #if 0
00265        XtVaGetValues(portrait_button, XmNset, &test1, NULL);
00266        XtVaGetValues(landscape_button, XmNset, &test2, NULL);
00267        
00268        fprintf(stderr, "+++++++ old state of portrait: %d, landscape: %d\n",
00269               test1, test2);
00270        
00271        fprintf(stderr, "+++++++ setting portrait to %s, landscape to %s\n",
00272               landscape ? "False" : "True",
00273               landscape ? "True" : "False");
00274 #endif /* 0 */
00275 
00276        /*
00277           Apparently there's a bug in Motif (OpenMotif 2.1) in that the button
00278           is not properly updated in all cases.
00279 
00280           To reproduce:
00281 
00282           Open Preferences dialog, change `landscape' option, click
00283           `OK'.  Now open the dialog again, change the option again,
00284           but click `Cancel'.  This correctly reverts the visible
00285           state of the buttons, but when opening the dialog again,
00286           the button's internal state is not consistent with the
00287           visual appearance: when clicking on the unset button, its
00288           ValueChanged callback is not invoked, so nothing happens;
00289           but after clicking on another(!)  button in the preferences
00290           dialog, it works again.
00291 
00292           As a workaround, we destroy the buttons and re-create them from scratch - yuck!
00293        */
00294        {
00295            Widget form = XtParent(portrait_button);
00296            Widget cascade;
00297            struct topic_info *info;
00298            
00299            XtVaGetValues(portrait_button,
00300                        XmNleftWidget, &cascade,
00301                        XmNuserData, &info,
00302                        NULL);
00303            XtDestroyWidget(portrait_button);
00304            XtDestroyWidget(landscape_button);
00305 
00306            portrait_button = XmCreateToggleButtonGadget(form, Xdvi_PAPER_PORTRAIT_STR, &one_of_many, 1);
00307            XmToggleButtonGadgetSetState(portrait_button, !landscape, False);
00308            XtVaSetValues(portrait_button,
00309                        XmNtopAttachment, XmATTACH_FORM,
00310                        XmNbottomAttachment, XmATTACH_FORM,
00311                        XmNleftAttachment, XmATTACH_WIDGET,
00312                        XmNleftWidget, cascade,
00313                        XmNleftOffset, 10,
00314                        XmNuserData, (XtPointer)info,
00315                        NULL);
00316            landscape_button = XmCreateToggleButtonGadget(form, Xdvi_PAPER_LANDSCAPE_STR, &one_of_many, 1);
00317            XmToggleButtonGadgetSetState(landscape_button, landscape, False);
00318            XtVaSetValues(landscape_button,
00319                        XmNtopAttachment, XmATTACH_FORM,
00320                        XmNbottomAttachment, XmATTACH_FORM,
00321                        XmNleftAttachment, XmATTACH_WIDGET,
00322                        XmNleftWidget, portrait_button,
00323                        XmNleftOffset, 10,
00324                        XmNuserData, (XtPointer)info,
00325                        NULL);
00326            XtManageChild(portrait_button);
00327            XtManageChild(landscape_button);
00328            XtAddCallback(portrait_button, XmNvalueChangedCallback, landscape_cb, (XtPointer)info);
00329            XtAddCallback(landscape_button, XmNvalueChangedCallback, landscape_cb, (XtPointer)info);
00330        }
00331 #if 0
00332        XtVaGetValues(portrait_button, XmNset, &test1, NULL);
00333        XtVaGetValues(landscape_button, XmNset, &test2, NULL);
00334        
00335        fprintf(stderr, "+++++++ new state of portrait: %d, landscape: %d\n",
00336               test1, test2);
00337 #endif /* 0 */
00338        
00339        for (i = 0; papersizes[i].format != NULL; i++) {
00340            if (strncmp(resource.paper,
00341                      papersizes[i].resource_format,
00342                      strlen(papersizes[i].resource_format)) == 0
00343               && get_widget_by_name(&sizes_button, sizes_menu, papersizes[i].format, True)) {
00344 
00345               XtVaSetValues(sizes_cascade, XmNmenuHistory, sizes_button, NULL);
00346            }
00347        }
00348     }
00349 }
00350 
00351 #if 0 /* currently unused */
00352 static void
00353 shrinkfactor_spinbox_cb(Widget w, XtPointer client_data, XtPointer call_data)
00354 {
00355     int val;
00356 /*      static Boolean first_time = True; */
00357     struct topic_info *info = (struct topic_info *)client_data;
00358     struct prefs_choice *prefs = (struct prefs_choice *)(info->data);
00359     UNUSED(call_data);
00360     
00361     XtVaGetValues(w, XmNposition, &val, NULL);
00362 
00363     /* return if value not changed yet; else the first invocation of the
00364        window may actually reset the shrink factor to the default.
00365     */
00366 /*      if (val != resource.shrinkfactor) { */
00367 /*     first_time = False; */
00368 /*      } */
00369 
00370     if (XtIsRealized(w)) {
00371        /* don't set the resource.shrinkfactor here so that we can revert it from there if needed */
00372        do_set_shrinkfactor(val, False);
00373        store_preference(&(prefs->db), "shrinkFactor", "%d", val);
00374     }
00375 }
00376 #endif /* currently unused */
00377 
00378 static void
00379 set_shrinkfactor_cb(Widget w, XtPointer client_data, XtPointer call_data)
00380 {
00381     char *text;
00382     int val;
00383     struct topic_info *info = (struct topic_info *)client_data;
00384     struct prefs_choice *prefs = (struct prefs_choice *)(info->data);
00385 
00386 #if USE_SPINBOX
00387     XmTextPosition pos;
00388     UNUSED(call_data);
00389     text = XmTextFieldGetString(w);
00390     val = strtol(text, (char **)NULL, 10);
00391 #else
00392     Widget text_field;
00393     UNUSED(call_data);
00394     XtVaGetValues(w, XmNuserData, &text_field, NULL);
00395     ASSERT(text_field != 0, "Expected text field in XmNuserData, set_shrinkfactor_cb()");
00396     XtVaGetValues(text_field, XmNvalue, &text, NULL);
00397     val = strtol(text, (char **)NULL, 10);
00398 /*     fprintf(stderr, "spinbox value: |%s|\n", text); */
00399 #endif
00400 
00401     if (!XtIsRealized(w))
00402        return;
00403     
00404     /* verify values in case of direct text input */
00405     if (val > 100 || val <= 0) {
00406        if (val > 100)
00407            statusline_print(STATUS_MEDIUM, "Shrink factor larger than maximum 100");
00408        else if (val <= 0)
00409            statusline_print(STATUS_MEDIUM, "Shrink factor smaller than minimum 1");
00410        return;
00411     }
00412 #if USE_SPINBOX
00413     /* synchronize internal spinbox value */
00414     pos = XmTextFieldGetInsertionPosition(w);
00415     XtVaSetValues(w, XmNposition, val, NULL);
00416     XmTextFieldSetInsertionPosition(w, pos);
00417 #endif
00418     /* don't set the resource.shrinkfactor here so that we can revert it from there if needed */
00419     do_set_shrinkfactor(val, False);
00420     store_preference(&(prefs->db), "shrinkFactor", "%d", val);
00421     
00422     XtFree(text);
00423 }
00424 
00425 static Widget
00426 h_create_shrink_frame(Widget top, struct topic_info *info)
00427 {
00428     Widget shrink_form, shrink_label;
00429 
00430     UNUSED(info);
00431     
00432     shrink_form = XmCreateForm(top, "shrink_form", NULL, 0);
00433     XtVaSetValues(shrink_form,
00434 /*              XmNverticalSpacing, 10, */
00435 /*              XmNhorizontalSpacing, 10, */
00436                 NULL);
00437 
00438     
00439     shrink_label = XmCreateLabelGadget(shrink_form, "Default Shrink Factor: ", NULL, 0);
00440     XtVaSetValues(shrink_label,
00441                 XmNtopAttachment, XmATTACH_FORM,
00442                 XmNleftAttachment, XmATTACH_FORM,
00443                 XmNbottomAttachment, XmATTACH_FORM,
00444                 /* TODO  XmNleftOffset, 10, */
00445                 NULL);
00446     XtManageChild(shrink_label);
00447     {
00448        Widget shrink_text;
00449 #if USE_SPINBOX
00450        Widget shrink_spinbox =
00451            XtVaCreateManagedWidget(Xdvi_SHRINK_SPINBOX, xmSpinBoxWidgetClass, shrink_form,
00452                                 XmNtopAttachment, XmATTACH_FORM,
00453                                 XmNleftAttachment, XmATTACH_WIDGET,
00454                                 XmNleftWidget, shrink_label,
00455                                 XmNinitialDelay, 200,
00456                                 XmNrepeatDelay, 50,
00457                                 NULL);
00458        shrink_text =
00459            XtVaCreateManagedWidget(Xdvi_SHRINK_TEXT, xmTextFieldWidgetClass, shrink_spinbox,
00460                                 XmNspinBoxChildType, XmNUMERIC,
00461                                 XmNminimumValue, 1,
00462                                 XmNmaximumValue, 100,
00463                                 XmNeditable, True,
00464                                 XmNcolumns, 3,
00465                                 XmNincrementValue, 1,
00466                                 XmNwrap, False, /* too confusing */
00467                                 /* NOTE: use resource.shrinkfactor here, not current setting,
00468                                    otherwise the current setting will sneak into ~/.xdvirc */
00469                                 XmNposition, (int)(resource.shrinkfactor),
00470                                 NULL);
00471 
00472        XtAddCallback(shrink_text, XmNactivateCallback, set_shrinkfactor_cb, (XtPointer)info);
00473        XtAddCallback(shrink_text, XmNvalueChangedCallback, set_shrinkfactor_cb, (XtPointer)info);
00474 
00475        adjust_heights(shrink_spinbox, shrink_text, shrink_label, NULL);
00476        
00477 #else
00478        char buf[LENGTH_OF_INT];
00479        Widget shrink_button;
00480        shrink_text = XmCreateTextField(shrink_form, Xdvi_SHRINK_TEXT, NULL, 0);
00481        SNPRINTF(buf, LENGTH_OF_INT, "%d", resource.shrinkfactor);
00482        XtVaSetValues(shrink_text,
00483                     XmNtopAttachment, XmATTACH_FORM,
00484                     XmNleftAttachment, XmATTACH_WIDGET,
00485                     XmNleftWidget, shrink_label,
00486                     XmNcolumns, 4,
00487                     XmNvalue, buf,
00488                     XmNuserData, shrink_text,
00489                     NULL);
00490        XtOverrideTranslations(shrink_text, XtParseTranslationTable("<Key>Return:activate()"));
00491        XtAddCallback(shrink_text, XmNactivateCallback, set_shrinkfactor_cb, (XtPointer)info);
00492 
00493        shrink_button = XmCreatePushButton(shrink_form, Xdvi_APPLY_STR, NULL, 0);
00494        XtVaSetValues(shrink_button,
00495                     XmNtopAttachment, XmATTACH_FORM,
00496                     XmNleftAttachment, XmATTACH_WIDGET,
00497                     XmNleftOffset, 10,
00498                     XmNleftWidget, shrink_text,
00499                     XmNuserData, shrink_text,
00500                     NULL);
00501        XtAddCallback(shrink_button, XmNactivateCallback, set_shrinkfactor_cb, (XtPointer)info);
00502        
00503        adjust_heights(shrink_label, shrink_text, shrink_button, NULL);
00504        XtManageChild(shrink_text);
00505        XtManageChild(shrink_button);
00506 #endif
00507     }
00508     
00509 /*     XtManageChild(shrink_form); */
00510 
00511     return shrink_form;
00512 }
00513 
00514 static void
00515 remember_windowsize_cb(Widget w, XtPointer client_data, XtPointer call_data)
00516 {
00517     struct topic_info *info = (struct topic_info *)client_data;
00518     struct prefs_choice *prefs = (struct prefs_choice *)(info->data);
00519 
00520     UNUSED(w);
00521     UNUSED(call_data);
00522     
00523     resource.remember_windowsize = !resource.remember_windowsize;
00524     
00525     store_preference(&(prefs->db), "rememberWindowSize", "%s", resource.remember_windowsize ? "True" : "False");
00526 }
00527 
00528 
00529 
00530 static Widget
00531 h_create_papersize_form(Widget parent, struct topic_info *info)
00532 {
00533     Widget form, menu, cascade, portrait_option, landscape_option;
00534     XmString str;
00535     Arg args[8];
00536     int n;
00537     size_t i;
00538     Boolean landscape = False;
00539     
00540     form = XmCreateForm(parent, "paper_form", NULL, 0);
00541     
00542     menu = XmCreatePulldownMenu(form, Xdvi_PAPER_MENU, NULL, 0);
00543 
00544     if (strcmp(resource.paper, "letter") != 0 && /* exceptions: these have no landscape format */
00545        strcmp(resource.paper, "ledger") != 0 &&
00546        strlen(resource.paper) > 0 &&
00547        resource.paper[strlen(resource.paper) - 1] == 'r') { /* landscape format */
00548        landscape = True;
00549     }
00550 
00551     str = XmStringCreateLocalized("Paper Size:");
00552 
00553     n = 0;
00554     XtSetArg(args[n], XmNsubMenuId, menu); n++;
00555     XtSetArg(args[n], XmNlabelString, str); n++;
00556     XtSetArg(args[n], XmNtopAttachment, XmATTACH_FORM); n++;
00557     XtSetArg(args[n], XmNleftAttachment, XmATTACH_FORM); n++;
00558     XtSetArg(args[n], XmNbottomAttachment, XmATTACH_FORM); n++;
00559 
00560     cascade = XmCreateOptionMenu(form, Xdvi_PAPER_CASCADE, args, n);
00561     XmStringFree(str);
00562 
00563     portrait_option = XmCreateToggleButtonGadget(form, Xdvi_PAPER_PORTRAIT_STR, &one_of_many, 1);
00564     XmToggleButtonGadgetSetState(portrait_option, !landscape, False);
00565     XtVaSetValues(portrait_option,
00566                 XmNtopAttachment, XmATTACH_FORM,
00567                 XmNbottomAttachment, XmATTACH_FORM,
00568                 XmNleftAttachment, XmATTACH_WIDGET,
00569                 XmNleftWidget, cascade,
00570                 XmNleftOffset, 10,
00571                 XmNuserData, (XtPointer)info,
00572                 NULL);
00573     
00574     landscape_option = XmCreateToggleButtonGadget(form, Xdvi_PAPER_LANDSCAPE_STR, &one_of_many, 1);
00575     XmToggleButtonGadgetSetState(landscape_option, landscape, False);
00576     XtVaSetValues(landscape_option,
00577                 XmNtopAttachment, XmATTACH_FORM,
00578                 XmNbottomAttachment, XmATTACH_FORM,
00579                 XmNleftAttachment, XmATTACH_WIDGET,
00580                 XmNleftWidget, portrait_option,
00581                 XmNleftOffset, 10,
00582                 XmNuserData, (XtPointer)info,
00583                 NULL);
00584 /*     adjust_heights(landscape_option, menu, cascade, NULL); */
00585     XtAddCallback(portrait_option, XmNvalueChangedCallback, landscape_cb, (XtPointer)info);
00586     XtAddCallback(landscape_option, XmNvalueChangedCallback, landscape_cb, (XtPointer)info);
00587 /*      XtAddCallback(portrait_option, XmNarmCallback, test_cb, (XtPointer)info); */
00588 /*      XtAddCallback(landscape_option, XmNarmCallback, test_cb, (XtPointer)info); */
00589     
00590     XtManageChild(portrait_option);
00591     XtManageChild(landscape_option);
00592     
00593     for (i = 0; papersizes[i].format != NULL; i++) {
00594        Widget w = XtVaCreateManagedWidget(papersizes[i].format, xmPushButtonGadgetClass, menu,
00595                                       XmNuserData, landscape_option,
00596                                       NULL);
00597 /*     fprintf(stderr, "Created button: %p for %s\n", w, papersizes[i].format); */
00598 
00599        /* select default value */
00600        if (strncmp(resource.paper,
00601                   papersizes[i].resource_format,
00602                   strlen(papersizes[i].resource_format)) == 0) {
00603            XtVaSetValues(cascade, XmNmenuHistory, w, NULL);
00604        }
00605        XtAddCallback(w, XmNactivateCallback, select_cb, (XtPointer)info);
00606     }
00607     XtManageChild(cascade);
00608 
00609     return form;
00610 }
00611 
00612 Widget
00613 prefs_paper(struct topic_info *info)
00614 {
00615     Widget form;
00616     Widget geometry_frame, geometry_label, geometry_rowcol, shrink_frame, geometry_button;
00617     Widget paper_frame, paper_label;
00618     Arg args[10];
00619     int n = 0;
00620     Widget rowcol;
00621 #if !defined(LESSTIF_VERSION)
00622     Widget paper_text;
00623 #endif
00624     Widget paper_size_form;
00625     
00626     form = XtVaCreateWidget("form", xmFormWidgetClass,
00627                          info->right_form,
00628                          XmNtopAttachment, XmATTACH_FORM,
00629                          XmNleftAttachment, XmATTACH_FORM,
00630                          XmNrightAttachment, XmATTACH_FORM,
00631                          XmNbottomAttachment, XmATTACH_FORM,
00632                          NULL);
00633 
00634     n = 0;
00635     XtSetArg(args[n], XmNmarginWidth, 8); n++;
00636     XtSetArg(args[n], XmNmarginHeight, 4); n++;
00637     geometry_frame = XmCreateFrame(form, "geometry_frame", args, n);
00638     h_attach_below(geometry_frame,  NULL);
00639 
00640     geometry_label = XmCreateLabelGadget(geometry_frame, "Window Size and Shrink Factor", &frame_title, 1);
00641     XtManageChild(geometry_label);
00642     
00643     geometry_rowcol = XmCreateRowColumn(geometry_frame, "geometry_rowcol", one_col, XtNumber(one_col));
00644     
00645     geometry_button = XmCreateToggleButtonGadget(geometry_rowcol, Xdvi_REMEMBER_WINDOWSIZE_STR, &n_of_many, 1);
00646     XmToggleButtonGadgetSetState(geometry_button, resource.remember_windowsize, False);
00647     XtAddCallback(geometry_button, XmNvalueChangedCallback, remember_windowsize_cb, (XtPointer)info);
00648     XtManageChild(geometry_button);
00649     
00650     shrink_frame = h_create_shrink_frame(geometry_rowcol, info);
00651     XtManageChild(shrink_frame);
00652 
00653     XtManageChild(geometry_rowcol);
00654 
00655     n = 0;
00656     XtSetArg(args[n], XmNmarginWidth, 8); n++;
00657     XtSetArg(args[n], XmNmarginHeight, 4); n++;
00658     XtSetArg(args[n], XmNtopOffset, 10); n++;
00659     paper_frame = XmCreateFrame(form, "paper_frame", args, n);
00660     h_attach_below(paper_frame, geometry_frame);
00661 
00662     paper_label = XmCreateLabelGadget(paper_frame, "Default Paper Size", &frame_title, 1);
00663     XtManageChild(paper_label);
00664     
00665     rowcol = XmCreateRowColumn(paper_frame, "papersize_rowcol", NULL, 0);
00666 
00667 #if !defined(LESSTIF_VERSION) /* stupid LessTif doesn't wrap Labels at '\n' */
00668     paper_text = XmCreateLabelGadget(rowcol,
00669                                  "Used if the DVI file does not specify the paper size, e.g. via\n"
00670                                  "\\usepackage[dvips]{geometry}.  This setting will only take effect\n"
00671                                  "after restarting xdvi.", NULL, 0);
00672     XtVaSetValues(paper_text,
00673                 XmNalignment, XmALIGNMENT_BEGINNING,
00674                 NULL);
00675     XtManageChild(paper_text);
00676 #endif
00677     
00678     paper_size_form = h_create_papersize_form(rowcol, info);
00679     XtManageChild(paper_size_form);
00680 
00681     XtManageChild(rowcol);
00682     
00683     XtManageChild(geometry_frame);
00684     XtManageChild(paper_frame);
00685     
00686     XtManageChild(form);
00687 
00688     return form;
00689 }
00690 
00691 #else
00692 /* silence `empty compilation unit' warnings */
00693 static void bar(void); static void foo() { bar(); } static void bar(void) { foo(); }
00694 #endif /* MOTIF */
00695