Xft support under OpenMotif 2.3.3 - I've been using this for quite a while on
[nedit.git] / source / menu.c
blob7b34396da2de5de886f51284a9e2c192d281502d
1 static const char CVSID[] = "$Id: menu.c,v 1.143 2008/01/04 22:11:03 yooden Exp $";
2 /*******************************************************************************
3 * *
4 * menu.c -- Nirvana Editor menus *
5 * *
6 * Copyright (C) 1999 Mark Edel *
7 * *
8 * This is free software; you can redistribute it and/or modify it under the *
9 * terms of the GNU General Public License as published by the Free Software *
10 * Foundation; either version 2 of the License, or (at your option) any later *
11 * version. In addition, you may distribute versions of this program linked to *
12 * Motif or Open Motif. See README for details. *
13 * *
14 * This software is distributed in the hope that it will be useful, but WITHOUT *
15 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or *
16 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License *
17 * for more details. *
18 * *
19 * You should have received a copy of the GNU General Public License along with *
20 * software; if not, write to the Free Software Foundation, Inc., 59 Temple *
21 * Place, Suite 330, Boston, MA 02111-1307 USA *
22 * *
23 * Nirvana Text Editor *
24 * May 10, 1991 *
25 * *
26 * Written by Mark Edel *
27 * *
28 *******************************************************************************/
30 #ifdef HAVE_CONFIG_H
31 #include "../config.h"
32 #endif
34 #include "menu.h"
35 #include "textBuf.h"
36 #include "text.h"
37 #include "nedit.h"
38 #include "file.h"
39 #include "window.h"
40 #include "search.h"
41 #include "selection.h"
42 #include "undo.h"
43 #include "shift.h"
44 #include "help.h"
45 #include "preferences.h"
46 #include "tags.h"
47 #include "userCmds.h"
48 #include "shell.h"
49 #include "macro.h"
50 #include "highlight.h"
51 #include "highlightData.h"
52 #include "interpret.h"
53 #include "smartIndent.h"
54 #include "windowTitle.h"
55 #include "../util/getfiles.h"
56 #include "../util/DialogF.h"
57 #include "../util/misc.h"
58 #include "../util/fileUtils.h"
59 #include "../util/utils.h"
60 #include "../Xlt/BubbleButton.h"
62 #include <ctype.h>
63 #include <errno.h>
64 #include <stdio.h>
65 #include <stdlib.h>
66 #include <string.h>
67 #include <unistd.h>
68 #include <sys/stat.h>
69 #include <sys/types.h>
71 #ifdef VMS
72 #include "../util/VMSparam.h"
73 #else
74 #ifndef __MVS__
75 #include <sys/param.h>
76 #endif
77 #endif /*VMS*/
79 #include <X11/X.h>
80 #include <Xm/Xm.h>
81 #include <Xm/CascadeB.h>
82 #include <Xm/PushB.h>
83 #include <Xm/ToggleB.h>
84 #include <Xm/Separator.h>
85 #include <Xm/RowColumn.h>
86 #include <Xm/MenuShell.h>
88 #ifdef HAVE_DEBUG_H
89 #include "../debug.h"
90 #endif
92 #if XmVersion >= 1002
93 #define MENU_WIDGET(w) (XmGetPostedFromWidget(XtParent(w)))
94 #else
95 #define MENU_WIDGET(w) (w)
96 #endif
98 /* Menu modes for SGI_CUSTOM short-menus feature */
99 enum menuModes {FULL, SHORT};
101 typedef void (*menuCallbackProc)();
103 extern void _XmDismissTearOff(Widget, XtPointer, XtPointer);
105 static void doActionCB(Widget w, XtPointer clientData, XtPointer callData);
106 static void doTabActionCB(Widget w, XtPointer clientData, XtPointer callData);
107 static void pasteColCB(Widget w, XtPointer clientData, XtPointer callData);
108 static void shiftLeftCB(Widget w, XtPointer clientData, XtPointer callData);
109 static void shiftRightCB(Widget w, XtPointer clientData, XtPointer callData);
110 static void findCB(Widget w, XtPointer clientData, XtPointer callData);
111 static void findSameCB(Widget w, XtPointer clientData, XtPointer callData);
112 static void findSelCB(Widget w, XtPointer clientData, XtPointer callData);
113 static void findIncrCB(Widget w, XtPointer clientData, XtPointer callData);
114 static void replaceCB(Widget w, XtPointer clientData, XtPointer callData);
115 static void replaceSameCB(Widget w, XtPointer clientData, XtPointer callData);
116 static void replaceFindSameCB(Widget w, XtPointer clientData, XtPointer callData);
117 static void markCB(Widget w, XtPointer clientData, XtPointer callData);
118 static void gotoMarkCB(Widget w, XtPointer clientData, XtPointer callData);
119 static void gotoMatchingCB(Widget w, XtPointer clientData, XtPointer callData);
120 static void autoIndentOffCB(Widget w, WindowInfo *window, caddr_t callData);
121 static void autoIndentCB(Widget w, WindowInfo *window, caddr_t callData);
122 static void smartIndentCB(Widget w, WindowInfo *window, caddr_t callData);
123 static void preserveCB(Widget w, WindowInfo *window, caddr_t callData);
124 static void autoSaveCB(Widget w, WindowInfo *window, caddr_t callData);
125 static void newlineWrapCB(Widget w, WindowInfo *window, caddr_t callData);
126 static void noWrapCB(Widget w, WindowInfo *window, caddr_t callData);
127 static void continuousWrapCB(Widget w, WindowInfo *window, caddr_t callData);
128 static void wrapMarginCB(Widget w, WindowInfo *window, caddr_t callData);
129 static void fontCB(Widget w, WindowInfo *window, caddr_t callData);
130 static void tabsCB(Widget w, WindowInfo *window, caddr_t callData);
131 static void backlightCharsCB(Widget w, WindowInfo *window, caddr_t callData);
132 static void showMatchingOffCB(Widget w, WindowInfo *window, caddr_t callData);
133 static void showMatchingDelimitCB(Widget w, WindowInfo *window, caddr_t callData);
134 static void showMatchingRangeCB(Widget w, WindowInfo *window, caddr_t callData);
135 static void matchSyntaxBasedCB(Widget w, WindowInfo *window, caddr_t callData);
136 static void statsCB(Widget w, WindowInfo *window, caddr_t callData);
137 static void autoIndentOffDefCB(Widget w, WindowInfo *window, caddr_t callData);
138 static void autoIndentDefCB(Widget w, WindowInfo *window, caddr_t callData);
139 static void smartIndentDefCB(Widget w, WindowInfo *window, caddr_t callData);
140 static void autoSaveDefCB(Widget w, WindowInfo *window, caddr_t callData);
141 static void preserveDefCB(Widget w, WindowInfo *window, caddr_t callData);
142 static void noWrapDefCB(Widget w, WindowInfo *window, caddr_t callData);
143 static void newlineWrapDefCB(Widget w, WindowInfo *window, caddr_t callData);
144 static void contWrapDefCB(Widget w, WindowInfo *window, caddr_t callData);
145 static void wrapMarginDefCB(Widget w, WindowInfo *window, caddr_t callData);
146 static void shellSelDefCB(Widget widget, WindowInfo* window, caddr_t callData);
147 static void openInTabDefCB(Widget w, WindowInfo *window, caddr_t callData);
148 static void tabBarDefCB(Widget w, WindowInfo *window, caddr_t callData);
149 static void tabBarHideDefCB(Widget w, WindowInfo *window, caddr_t callData);
150 static void tabSortDefCB(Widget w, WindowInfo *window, caddr_t callData);
151 static void toolTipsDefCB(Widget w, WindowInfo *window, caddr_t callData);
152 static void tabNavigateDefCB(Widget w, WindowInfo *window, caddr_t callData);
153 static void statsLineDefCB(Widget w, WindowInfo *window, caddr_t callData);
154 static void iSearchLineDefCB(Widget w, WindowInfo *window, caddr_t callData);
155 static void lineNumsDefCB(Widget w, WindowInfo *window, caddr_t callData);
156 static void pathInWindowsMenuDefCB(Widget w, WindowInfo *window, caddr_t callData);
157 static void customizeTitleDefCB(Widget w, WindowInfo *window, caddr_t callData);
158 static void tabsDefCB(Widget w, WindowInfo *window, caddr_t callData);
159 static void showMatchingOffDefCB(Widget w, WindowInfo *window, caddr_t callData);
160 static void showMatchingDelimitDefCB(Widget w, WindowInfo *window, caddr_t callData);
161 static void showMatchingRangeDefCB(Widget w, WindowInfo *window, caddr_t callData);
162 static void matchSyntaxBasedDefCB(Widget w, WindowInfo *window, caddr_t callData);
163 static void highlightOffDefCB(Widget w, WindowInfo *window, caddr_t callData);
164 static void highlightDefCB(Widget w, WindowInfo *window, caddr_t callData);
165 static void backlightCharsDefCB(Widget w, WindowInfo *window, caddr_t callData);
166 static void fontDefCB(Widget w, WindowInfo *window, caddr_t callData);
167 static void colorDefCB(Widget w, WindowInfo *window, caddr_t callData);
168 static void smartTagsDefCB(Widget parent, XtPointer client_data, XtPointer call_data);
169 static void showAllTagsDefCB(Widget parent, XtPointer client_data, XtPointer call_data);
170 static void languageDefCB(Widget w, WindowInfo *window, caddr_t callData);
171 static void highlightingDefCB(Widget w, WindowInfo *window, caddr_t callData);
172 static void smartMacrosDefCB(Widget w, WindowInfo *window, caddr_t callData);
173 static void stylesDefCB(Widget w, WindowInfo *window, caddr_t callData);
174 static void shellDefCB(Widget w, WindowInfo *window, caddr_t callData);
175 static void macroDefCB(Widget w, WindowInfo *window, caddr_t callData);
176 static void bgMenuDefCB(Widget w, WindowInfo *window, caddr_t callData);
177 static void searchDlogsDefCB(Widget w, WindowInfo *window, caddr_t callData);
178 static void beepOnSearchWrapDefCB(Widget w, WindowInfo *window, caddr_t callData);
179 static void keepSearchDlogsDefCB(Widget w, WindowInfo *window,
180 caddr_t callData);
181 static void searchWrapsDefCB(Widget w, WindowInfo *window, caddr_t callData);
182 static void appendLFCB(Widget w, WindowInfo* window, caddr_t callData);
183 static void sortOpenPrevDefCB(Widget w, WindowInfo *window, caddr_t callData);
184 static void reposDlogsDefCB(Widget w, WindowInfo *window, caddr_t callData);
185 static void autoScrollDefCB(Widget w, WindowInfo *window, caddr_t callData);
186 static void modWarnDefCB(Widget w, WindowInfo *window, caddr_t callData);
187 static void modWarnRealDefCB(Widget w, WindowInfo *window, caddr_t callData);
188 static void exitWarnDefCB(Widget w, WindowInfo *window, caddr_t callData);
189 static void searchLiteralCB(Widget w, WindowInfo *window, caddr_t callData);
190 static void searchCaseSenseCB(Widget w, WindowInfo *window, caddr_t callData);
191 static void searchLiteralWordCB(Widget w, WindowInfo *window, caddr_t callData);
192 static void searchCaseSenseWordCB(Widget w, WindowInfo *window, caddr_t callData);
193 static void searchRegexNoCaseCB(Widget w, WindowInfo *window, caddr_t callData);
194 static void searchRegexCB(Widget w, WindowInfo *window, caddr_t callData);
195 #ifdef REPLACE_SCOPE
196 static void replaceScopeWindowCB(Widget w, WindowInfo *window, caddr_t callData);
197 static void replaceScopeSelectionCB(Widget w, WindowInfo *window, caddr_t callData);
198 static void replaceScopeSmartCB(Widget w, WindowInfo *window, caddr_t callData);
199 #endif
200 static void size24x80CB(Widget w, WindowInfo *window, caddr_t callData);
201 static void size40x80CB(Widget w, WindowInfo *window, caddr_t callData);
202 static void size60x80CB(Widget w, WindowInfo *window, caddr_t callData);
203 static void size80x80CB(Widget w, WindowInfo *window, caddr_t callData);
204 static void sizeCustomCB(Widget w, WindowInfo *window, caddr_t callData);
205 static void savePrefCB(Widget w, WindowInfo *window, caddr_t callData);
206 static void formFeedCB(Widget w, XtPointer clientData, XtPointer callData);
207 static void cancelShellCB(Widget w, WindowInfo *window, XtPointer callData);
208 static void learnCB(Widget w, WindowInfo *window, caddr_t callData);
209 static void finishLearnCB(Widget w, WindowInfo *window, caddr_t callData);
210 static void cancelLearnCB(Widget w, WindowInfo *window, caddr_t callData);
211 static void replayCB(Widget w, WindowInfo *window, caddr_t callData);
212 static void windowMenuCB(Widget w, WindowInfo *window, caddr_t callData);
213 static void prevOpenMenuCB(Widget w, WindowInfo *window, caddr_t callData);
214 static void unloadTagsFileMenuCB(Widget w, WindowInfo *window,
215 caddr_t callData);
216 static void unloadTipsFileMenuCB(Widget w, WindowInfo *window,
217 caddr_t callData);
218 static void newAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
219 static void newOppositeAP(Widget w, XEvent *event, String *args,
220 Cardinal *nArgs);
221 static void newTabAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
222 static void openDialogAP(Widget w, XEvent *event, String *args,
223 Cardinal *nArgs);
224 static void openAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
225 static void openSelectedAP(Widget w, XEvent *event, String *args,
226 Cardinal *nArgs);
227 static void closeAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
228 static void saveAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
229 static void saveAsDialogAP(Widget w, XEvent *event, String *args,
230 Cardinal *nArgs);
231 static void saveAsAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
232 static void revertDialogAP(Widget w, XEvent *event, String *args,
233 Cardinal *nArgs);
234 static void revertAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
235 static void includeDialogAP(Widget w, XEvent *event, String *args,
236 Cardinal *nArgs);
237 static void includeAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
238 static void loadMacroDialogAP(Widget w, XEvent *event, String *args,
239 Cardinal *nArgs) ;
240 static void loadMacroAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
241 static void loadTagsDialogAP(Widget w, XEvent *event, String *args,
242 Cardinal *nArgs);
243 static void loadTagsAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
244 static void unloadTagsAP(Widget w, XEvent *event, String *args,
245 Cardinal *nArgs);
246 static void loadTipsDialogAP(Widget w, XEvent *event, String *args,
247 Cardinal *nArgs);
248 static void loadTipsAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
249 static void unloadTipsAP(Widget w, XEvent *event, String *args,
250 Cardinal *nArgs);
251 static void printAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
252 static void printSelAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
253 static void exitAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
254 static void undoAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
255 static void redoAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
256 static void clearAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
257 static void selAllAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
258 static void shiftLeftAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
259 static void shiftLeftTabAP(Widget w, XEvent *event, String *args,
260 Cardinal *nArgs);
261 static void shiftRightAP(Widget w, XEvent *event, String *args,
262 Cardinal *nArgs);
263 static void shiftRightTabAP(Widget w, XEvent *event, String *args,
264 Cardinal *nArgs);
265 static void findDialogAP(Widget w, XEvent *event, String *args,
266 Cardinal *nArgs);
267 static void findAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
268 static void findSameAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
269 static void findSelAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
270 static void findIncrAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
271 static void startIncrFindAP(Widget w, XEvent *event, String *args,
272 Cardinal *nArgs);
273 static void replaceDialogAP(Widget w, XEvent *event, String *args,
274 Cardinal *nArgs);
275 static void replaceAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
276 static void replaceAllAP(Widget w, XEvent *event, String *args,
277 Cardinal *nArgs);
278 static void replaceInSelAP(Widget w, XEvent *event, String *args,
279 Cardinal *nArgs);
280 static void replaceSameAP(Widget w, XEvent *event, String *args,
281 Cardinal *nArgs);
282 static void replaceFindAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
283 static void replaceFindSameAP(Widget w, XEvent *event, String *args,
284 Cardinal *nArgs);
285 static void gotoAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
286 static void gotoDialogAP(Widget w, XEvent *event, String *args,
287 Cardinal *nArgs);
288 static void gotoSelectedAP(Widget w, XEvent *event, String *args,
289 Cardinal *nArgs);
290 static void repeatDialogAP(Widget w, XEvent *event, String *args,
291 Cardinal *nArgs);
292 static void repeatMacroAP(Widget w, XEvent *event, String *args,
293 Cardinal *nArgs);
294 static void markAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
295 static void markDialogAP(Widget w, XEvent *event, String *args,
296 Cardinal *nArgs);
297 static void gotoMarkAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
298 static void gotoMarkDialogAP(Widget w, XEvent *event, String *args,
299 Cardinal *nArgs);
300 static void selectToMatchingAP(Widget w, XEvent *event, String *args,
301 Cardinal *nArgs);
302 static void gotoMatchingAP(Widget w, XEvent *event, String *args,
303 Cardinal *nArgs);
304 static void findDefAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
305 static void showTipAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
306 static void splitPaneAP(Widget w, XEvent *event, String *args,
307 Cardinal *nArgs);
308 static void detachDocumentDialogAP(Widget w, XEvent *event, String *args,
309 Cardinal *nArgs);
310 static void detachDocumentAP(Widget w, XEvent *event, String *args,
311 Cardinal *nArgs);
312 static void moveDocumentDialogAP(Widget w, XEvent *event, String *args,
313 Cardinal *nArgs);
314 static void nextDocumentAP(Widget w, XEvent *event, String *args,
315 Cardinal *nArgs);
316 static void prevDocumentAP(Widget w, XEvent *event, String *args,
317 Cardinal *nArgs);
318 static void lastDocumentAP(Widget w, XEvent *event, String *args,
319 Cardinal *nArgs);
320 static void closePaneAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
321 static void capitalizeAP(Widget w, XEvent *event, String *args,
322 Cardinal *nArgs);
323 static void lowercaseAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
324 static void fillAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
325 static void controlDialogAP(Widget w, XEvent *event, String *args,
326 Cardinal *nArgs);
327 #ifndef VMS
328 static void filterDialogAP(Widget w, XEvent *event, String *args,
329 Cardinal *nArgs);
330 static void shellFilterAP(Widget w, XEvent *event, String *args,
331 Cardinal *nArgs);
332 static void execDialogAP(Widget w, XEvent *event, String *args,
333 Cardinal *nArgs);
334 static void execAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
335 static void execLineAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
336 static void shellMenuAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
337 #endif
338 static void macroMenuAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
339 static void bgMenuAP(Widget w, XEvent *event, String *args, Cardinal *nArgs);
340 static void beginningOfSelectionAP(Widget w, XEvent *event, String *args,
341 Cardinal *nArgs);
342 static void endOfSelectionAP(Widget w, XEvent *event, String *args,
343 Cardinal *nArgs);
344 static Widget createMenu(Widget parent, char *name, char *label,
345 char mnemonic, Widget *cascadeBtn, int mode);
346 static Widget createMenuItem(Widget parent, char *name, char *label,
347 char mnemonic, menuCallbackProc callback, void *cbArg, int mode);
348 static Widget createFakeMenuItem(Widget parent, char *name,
349 menuCallbackProc callback, void *cbArg);
350 static Widget createMenuToggle(Widget parent, char *name, char *label,
351 char mnemonic, menuCallbackProc callback, void *cbArg, int set,
352 int mode);
353 static Widget createMenuRadioToggle(Widget parent, char *name, char *label,
354 char mnemonic, menuCallbackProc callback, void *cbArg, int set,
355 int mode);
356 static Widget createMenuSeparator(Widget parent, char *name, int mode);
357 static void invalidatePrevOpenMenus(void);
358 static void updateWindowMenu(const WindowInfo *window);
359 static void updatePrevOpenMenu(WindowInfo *window);
360 static void updateTagsFileMenu(WindowInfo *window);
361 static void updateTipsFileMenu(WindowInfo *window);
362 static int searchDirection(int ignoreArgs, String *args, Cardinal *nArgs);
363 static int searchWrap(int ignoreArgs, String *args, Cardinal *nArgs);
364 static int searchKeepDialogs(int ignoreArgs, String *args, Cardinal *nArgs);
365 static int searchType(int ignoreArgs, String *args, Cardinal *nArgs);
366 static char **shiftKeyToDir(XtPointer callData);
367 static void raiseCB(Widget w, WindowInfo *window, caddr_t callData);
368 static void openPrevCB(Widget w, char *name, caddr_t callData);
369 static void unloadTagsFileCB(Widget w, char *name, caddr_t callData);
370 static void unloadTipsFileCB(Widget w, char *name, caddr_t callData);
371 static int cmpStrPtr(const void *strA, const void *strB);
372 static void setWindowSizeDefault(int rows, int cols);
373 static void updateWindowSizeMenus(void);
374 static void updateWindowSizeMenu(WindowInfo *win);
375 static int strCaseCmp(const char *str1, const char *str2);
376 static int compareWindowNames(const void *windowA, const void *windowB);
377 static void bgMenuPostAP(Widget w, XEvent *event, String *args,
378 Cardinal *nArgs);
379 static void tabMenuPostAP(Widget w, XEvent *event, String *args,
380 Cardinal *nArgs);
381 static void raiseWindowAP(Widget w, XEvent *event, String *args,
382 Cardinal *nArgs);
383 static void focusPaneAP(Widget w, XEvent *event, String *args,
384 Cardinal *nArgs);
385 static void setStatisticsLineAP(Widget w, XEvent *event, String *args,
386 Cardinal *nArgs);
387 static void setIncrementalSearchLineAP(Widget w, XEvent *event, String *args,
388 Cardinal *nArgs);
389 static void setShowLineNumbersAP(Widget w, XEvent *event, String *args,
390 Cardinal *nArgs);
391 static void setAutoIndentAP(Widget w, XEvent *event, String *args,
392 Cardinal *nArgs);
393 static void setWrapTextAP(Widget w, XEvent *event, String *args,
394 Cardinal *nArgs);
395 static void setWrapMarginAP(Widget w, XEvent *event, String *args,
396 Cardinal *nArgs);
397 static void setHighlightSyntaxAP(Widget w, XEvent *event, String *args,
398 Cardinal *nArgs);
399 static void setMakeBackupCopyAP(Widget w, XEvent *event, String *args,
400 Cardinal *nArgs);
401 static void setIncrementalBackupAP(Widget w, XEvent *event, String *args,
402 Cardinal *nArgs);
403 static void setShowMatchingAP(Widget w, XEvent *event, String *args,
404 Cardinal *nArgs);
405 static void setMatchSyntaxBasedAP(Widget w, XEvent *event, String *args,
406 Cardinal *nArgs);
407 static void setOvertypeModeAP(Widget w, XEvent *event, String *args,
408 Cardinal *nArgs);
409 static void setLockedAP(Widget w, XEvent *event, String *args,
410 Cardinal *nArgs);
411 static void setUseTabsAP(Widget w, XEvent *event, String *args,
412 Cardinal *nArgs);
413 static void setEmTabDistAP(Widget w, XEvent *event, String *args,
414 Cardinal *nArgs);
415 static void setTabDistAP(Widget w, XEvent *event, String *args,
416 Cardinal *nArgs);
417 static void setFontsAP(Widget w, XEvent *event, String *args,
418 Cardinal *nArgs);
419 static void setLanguageModeAP(Widget w, XEvent *event, String *args,
420 Cardinal *nArgs);
421 #ifdef SGI_CUSTOM
422 static void shortMenusCB(Widget w, WindowInfo *window, caddr_t callData);
423 static void addToToggleShortList(Widget w);
424 static int shortPrefAskDefault(Widget parent, Widget w, const char *settingName);
425 #endif
427 static HelpMenu * buildHelpMenu( Widget pane, HelpMenu * menu,
428 WindowInfo * window);
430 /* Application action table */
431 static XtActionsRec Actions[] = {
432 {"new", newAP},
433 {"new_opposite", newOppositeAP},
434 {"new_tab", newTabAP},
435 {"open", openAP},
436 {"open-dialog", openDialogAP},
437 {"open_dialog", openDialogAP},
438 {"open-selected", openSelectedAP},
439 {"open_selected", openSelectedAP},
440 {"close", closeAP},
441 {"save", saveAP},
442 {"save-as", saveAsAP},
443 {"save_as", saveAsAP},
444 {"save-as-dialog", saveAsDialogAP},
445 {"save_as_dialog", saveAsDialogAP},
446 {"revert-to-saved", revertAP},
447 {"revert_to_saved", revertAP},
448 {"revert_to_saved_dialog", revertDialogAP},
449 {"include-file", includeAP},
450 {"include_file", includeAP},
451 {"include-file-dialog", includeDialogAP},
452 {"include_file_dialog", includeDialogAP},
453 {"load-macro-file", loadMacroAP},
454 {"load_macro_file", loadMacroAP},
455 {"load-macro-file-dialog", loadMacroDialogAP},
456 {"load_macro_file_dialog", loadMacroDialogAP},
457 {"load-tags-file", loadTagsAP},
458 {"load_tags_file", loadTagsAP},
459 {"load-tags-file-dialog", loadTagsDialogAP},
460 {"load_tags_file_dialog", loadTagsDialogAP},
461 {"unload_tags_file", unloadTagsAP},
462 {"load_tips_file", loadTipsAP},
463 {"load_tips_file_dialog", loadTipsDialogAP},
464 {"unload_tips_file", unloadTipsAP},
465 {"print", printAP},
466 {"print-selection", printSelAP},
467 {"print_selection", printSelAP},
468 {"exit", exitAP},
469 {"undo", undoAP},
470 {"redo", redoAP},
471 {"delete", clearAP},
472 {"select-all", selAllAP},
473 {"select_all", selAllAP},
474 {"shift-left", shiftLeftAP},
475 {"shift_left", shiftLeftAP},
476 {"shift-left-by-tab", shiftLeftTabAP},
477 {"shift_left_by_tab", shiftLeftTabAP},
478 {"shift-right", shiftRightAP},
479 {"shift_right", shiftRightAP},
480 {"shift-right-by-tab", shiftRightTabAP},
481 {"shift_right_by_tab", shiftRightTabAP},
482 {"find", findAP},
483 {"find-dialog", findDialogAP},
484 {"find_dialog", findDialogAP},
485 {"find-again", findSameAP},
486 {"find_again", findSameAP},
487 {"find-selection", findSelAP},
488 {"find_selection", findSelAP},
489 {"find_incremental", findIncrAP},
490 {"start_incremental_find", startIncrFindAP},
491 {"replace", replaceAP},
492 {"replace-dialog", replaceDialogAP},
493 {"replace_dialog", replaceDialogAP},
494 {"replace-all", replaceAllAP},
495 {"replace_all", replaceAllAP},
496 {"replace-in-selection", replaceInSelAP},
497 {"replace_in_selection", replaceInSelAP},
498 {"replace-again", replaceSameAP},
499 {"replace_again", replaceSameAP},
500 {"replace_find", replaceFindAP},
501 {"replace_find_same", replaceFindSameAP},
502 {"replace_find_again", replaceFindSameAP},
503 {"goto-line-number", gotoAP},
504 {"goto_line_number", gotoAP},
505 {"goto-line-number-dialog", gotoDialogAP},
506 {"goto_line_number_dialog", gotoDialogAP},
507 {"goto-selected", gotoSelectedAP},
508 {"goto_selected", gotoSelectedAP},
509 {"mark", markAP},
510 {"mark-dialog", markDialogAP},
511 {"mark_dialog", markDialogAP},
512 {"goto-mark", gotoMarkAP},
513 {"goto_mark", gotoMarkAP},
514 {"goto-mark-dialog", gotoMarkDialogAP},
515 {"goto_mark_dialog", gotoMarkDialogAP},
516 {"match", selectToMatchingAP},
517 {"select_to_matching", selectToMatchingAP},
518 {"goto_matching", gotoMatchingAP},
519 {"find-definition", findDefAP},
520 {"find_definition", findDefAP},
521 {"show_tip", showTipAP},
522 {"split-pane", splitPaneAP},
523 {"split_pane", splitPaneAP},
524 {"close-pane", closePaneAP},
525 {"close_pane", closePaneAP},
526 {"detach_document", detachDocumentAP},
527 {"detach_document_dialog", detachDocumentDialogAP},
528 {"move_document_dialog", moveDocumentDialogAP},
529 {"next_document", nextDocumentAP},
530 {"previous_document", prevDocumentAP},
531 {"last_document", lastDocumentAP},
532 {"uppercase", capitalizeAP},
533 {"lowercase", lowercaseAP},
534 {"fill-paragraph", fillAP},
535 {"fill_paragraph", fillAP},
536 {"control-code-dialog", controlDialogAP},
537 {"control_code_dialog", controlDialogAP},
538 #ifndef VMS
539 {"filter-selection-dialog", filterDialogAP},
540 {"filter_selection_dialog", filterDialogAP},
541 {"filter-selection", shellFilterAP},
542 {"filter_selection", shellFilterAP},
543 {"execute-command", execAP},
544 {"execute_command", execAP},
545 {"execute-command-dialog", execDialogAP},
546 {"execute_command_dialog", execDialogAP},
547 {"execute-command-line", execLineAP},
548 {"execute_command_line", execLineAP},
549 {"shell-menu-command", shellMenuAP},
550 {"shell_menu_command", shellMenuAP},
551 #endif /*VMS*/
552 {"macro-menu-command", macroMenuAP},
553 {"macro_menu_command", macroMenuAP},
554 {"bg_menu_command", bgMenuAP},
555 {"post_window_bg_menu", bgMenuPostAP},
556 {"post_tab_context_menu", tabMenuPostAP},
557 {"beginning-of-selection", beginningOfSelectionAP},
558 {"beginning_of_selection", beginningOfSelectionAP},
559 {"end-of-selection", endOfSelectionAP},
560 {"end_of_selection", endOfSelectionAP},
561 {"repeat_macro", repeatMacroAP},
562 {"repeat_dialog", repeatDialogAP},
563 {"raise_window", raiseWindowAP},
564 {"focus_pane", focusPaneAP},
565 {"set_statistics_line", setStatisticsLineAP},
566 {"set_incremental_search_line", setIncrementalSearchLineAP},
567 {"set_show_line_numbers", setShowLineNumbersAP},
568 {"set_auto_indent", setAutoIndentAP},
569 {"set_wrap_text", setWrapTextAP},
570 {"set_wrap_margin", setWrapMarginAP},
571 {"set_highlight_syntax", setHighlightSyntaxAP},
572 #ifndef VMS
573 {"set_make_backup_copy", setMakeBackupCopyAP},
574 #endif
575 {"set_incremental_backup", setIncrementalBackupAP},
576 {"set_show_matching", setShowMatchingAP},
577 {"set_match_syntax_based", setMatchSyntaxBasedAP},
578 {"set_overtype_mode", setOvertypeModeAP},
579 {"set_locked", setLockedAP},
580 {"set_tab_dist", setTabDistAP},
581 {"set_em_tab_dist", setEmTabDistAP},
582 {"set_use_tabs", setUseTabsAP},
583 {"set_fonts", setFontsAP},
584 {"set_language_mode", setLanguageModeAP}
587 /* List of previously opened files for File menu */
588 static int NPrevOpen = 0;
589 static char** PrevOpen = NULL;
591 #ifdef SGI_CUSTOM
592 /* Window to receive items to be toggled on and off in short menus mode */
593 static WindowInfo *ShortMenuWindow;
594 #endif
596 void HidePointerOnKeyedEvent(Widget w, XEvent *event)
598 if (event && (event->type == KeyPress || event->type == KeyRelease)) {
599 ShowHidePointer((TextWidget)w, True);
604 ** Install actions for use in translation tables and macro recording, relating
605 ** to menu item commands
607 void InstallMenuActions(XtAppContext context)
609 XtAppAddActions(context, Actions, XtNumber(Actions));
613 ** Return the (statically allocated) action table for menu item actions.
615 XtActionsRec *GetMenuActions(int *nActions)
617 *nActions = XtNumber(Actions);
618 return Actions;
622 ** Create the menu bar
624 Widget CreateMenuBar(Widget parent, WindowInfo *window)
626 Widget menuBar, menuPane, btn, subPane, subSubPane, subSubSubPane, cascade;
629 ** cache user menus:
630 ** allocate user menu cache
632 window->userMenuCache = CreateUserMenuCache();
635 ** Create the menu bar (row column) widget
637 menuBar = XmCreateMenuBar(parent, "menuBar", NULL, 0);
639 #ifdef SGI_CUSTOM
641 ** Short menu mode is a special feature for the SGI system distribution
642 ** version of NEdit.
644 ** To make toggling short-menus mode faster (re-creating the menus was
645 ** too slow), a list is kept in the window data structure of items to
646 ** be turned on and off. Initialize that list and give the menu creation
647 ** routines a pointer to the window on which this list is kept. This is
648 ** (unfortunately) a global variable to keep the interface simple for
649 ** the mainstream case.
651 ShortMenuWindow = window;
652 window->nToggleShortItems = 0;
653 #endif
656 ** "File" pull down menu.
658 menuPane = createMenu(menuBar, "fileMenu", "File", 0, NULL, SHORT);
659 createMenuItem(menuPane, "new", "New", 'N', doActionCB, "new", SHORT);
660 if ( GetPrefOpenInTab() )
661 window->newOppositeItem = createMenuItem(menuPane, "newOpposite",
662 "New Window", 'W', doActionCB, "new_opposite", SHORT);
663 else
664 window->newOppositeItem = createMenuItem(menuPane, "newOpposite",
665 "New Tab", 'T', doActionCB, "new_opposite", SHORT);
666 createMenuItem(menuPane, "open", "Open...", 'O', doActionCB, "open_dialog",
667 SHORT);
668 window->openSelItem=createMenuItem(menuPane, "openSelected", "Open Selected", 'd',
669 doActionCB, "open_selected", FULL);
670 if (GetPrefMaxPrevOpenFiles() > 0) {
671 window->prevOpenMenuPane = createMenu(menuPane, "openPrevious",
672 "Open Previous", 'v', &window->prevOpenMenuItem, SHORT);
673 XtSetSensitive(window->prevOpenMenuItem, NPrevOpen != 0);
674 XtAddCallback(window->prevOpenMenuItem, XmNcascadingCallback,
675 (XtCallbackProc)prevOpenMenuCB, window);
677 createMenuSeparator(menuPane, "sep1", SHORT);
678 window->closeItem = createMenuItem(menuPane, "close", "Close", 'C',
679 doActionCB, "close", SHORT);
680 createMenuItem(menuPane, "save", "Save", 'S', doActionCB, "save", SHORT);
681 createMenuItem(menuPane, "saveAs", "Save As...", 'A', doActionCB,
682 "save_as_dialog", SHORT);
683 createMenuItem(menuPane, "revertToSaved", "Revert to Saved", 'R',
684 doActionCB, "revert_to_saved_dialog", SHORT);
685 createMenuSeparator(menuPane, "sep2", SHORT);
686 createMenuItem(menuPane, "includeFile", "Include File...", 'I',
687 doActionCB, "include_file_dialog", SHORT);
688 createMenuItem(menuPane, "loadMacroFile", "Load Macro File...", 'M',
689 doActionCB, "load_macro_file_dialog", FULL);
690 createMenuItem(menuPane, "loadTagsFile", "Load Tags File...", 'g',
691 doActionCB, "load_tags_file_dialog", FULL);
692 window->unloadTagsMenuPane = createMenu(menuPane, "unloadTagsFiles",
693 "Unload Tags File", 'U', &window->unloadTagsMenuItem, FULL);
694 XtSetSensitive(window->unloadTagsMenuItem, TagsFileList != NULL);
695 XtAddCallback(window->unloadTagsMenuItem, XmNcascadingCallback,
696 (XtCallbackProc)unloadTagsFileMenuCB, window);
697 createMenuItem(menuPane, "loadTipsFile", "Load Calltips File...", 'F',
698 doActionCB, "load_tips_file_dialog", FULL);
699 window->unloadTipsMenuPane = createMenu(menuPane, "unloadTipsFiles",
700 "Unload Calltips File", 'e', &window->unloadTipsMenuItem, FULL);
701 XtSetSensitive(window->unloadTipsMenuItem, TipsFileList != NULL);
702 XtAddCallback(window->unloadTipsMenuItem, XmNcascadingCallback,
703 (XtCallbackProc)unloadTipsFileMenuCB, window);
704 createMenuSeparator(menuPane, "sep3", SHORT);
705 createMenuItem(menuPane, "print", "Print...", 'P', doActionCB, "print",
706 SHORT);
707 window->printSelItem = createMenuItem(menuPane, "printSelection",
708 "Print Selection...", 'l', doActionCB, "print_selection",
709 SHORT);
710 XtSetSensitive(window->printSelItem, window->wasSelected);
711 createMenuSeparator(menuPane, "sep4", SHORT);
712 createMenuItem(menuPane, "exit", "Exit", 'x', doActionCB, "exit", SHORT);
713 CheckCloseDim();
716 ** "Edit" pull down menu.
718 menuPane = createMenu(menuBar, "editMenu", "Edit", 0, NULL, SHORT);
719 window->undoItem = createMenuItem(menuPane, "undo", "Undo", 'U',
720 doActionCB, "undo", SHORT);
721 XtSetSensitive(window->undoItem, False);
722 window->redoItem = createMenuItem(menuPane, "redo", "Redo", 'R',
723 doActionCB, "redo", SHORT);
724 XtSetSensitive(window->redoItem, False);
725 createMenuSeparator(menuPane, "sep1", SHORT);
726 window->cutItem = createMenuItem(menuPane, "cut", "Cut", 't', doActionCB,
727 "cut_clipboard", SHORT);
728 XtSetSensitive(window->cutItem, window->wasSelected);
729 window->copyItem = createMenuItem(menuPane, "copy", "Copy", 'C', doActionCB,
730 "copy_clipboard", SHORT);
731 XtSetSensitive(window->copyItem, window->wasSelected);
732 createMenuItem(menuPane, "paste", "Paste", 'P', doActionCB,
733 "paste_clipboard", SHORT);
734 createMenuItem(menuPane, "pasteColumn", "Paste Column", 's', pasteColCB,
735 window, SHORT);
736 window->delItem=createMenuItem(menuPane, "delete", "Delete", 'D', doActionCB, "delete_selection",
737 SHORT);
738 XtSetSensitive(window->delItem, window->wasSelected);
739 createMenuItem(menuPane, "selectAll", "Select All", 'A', doActionCB,
740 "select_all", SHORT);
741 createMenuSeparator(menuPane, "sep2", SHORT);
742 createMenuItem(menuPane, "shiftLeft", "Shift Left", 'L',
743 shiftLeftCB, window, SHORT);
744 createFakeMenuItem(menuPane, "shiftLeftShift", shiftLeftCB, window);
745 createMenuItem(menuPane, "shiftRight", "Shift Right", 'g',
746 shiftRightCB, window, SHORT);
747 createFakeMenuItem(menuPane, "shiftRightShift", shiftRightCB, window);
748 window->lowerItem=createMenuItem(menuPane, "lowerCase", "Lower-case", 'w',
749 doActionCB, "lowercase", SHORT);
750 window->upperItem=createMenuItem(menuPane, "upperCase", "Upper-case", 'e',
751 doActionCB, "uppercase", SHORT);
752 createMenuItem(menuPane, "fillParagraph", "Fill Paragraph", 'F',
753 doActionCB, "fill_paragraph", SHORT);
754 createMenuSeparator(menuPane, "sep3", FULL);
755 createMenuItem(menuPane, "insertFormFeed", "Insert Form Feed", 'I',
756 formFeedCB, window, FULL);
757 createMenuItem(menuPane, "insertCtrlCode", "Insert Ctrl Code...", 'n',
758 doActionCB, "control_code_dialog", FULL);
759 #ifdef SGI_CUSTOM
760 createMenuSeparator(menuPane, "sep4", SHORT);
761 window->overtypeModeItem = createMenuToggle(menuPane, "overtype", "Overtype", 'O',
762 doActionCB, "set_overtype_mode", False, SHORT);
763 window->readOnlyItem = createMenuToggle(menuPane, "readOnly", "Read Only",
764 'y', doActionCB, "set_locked", IS_USER_LOCKED(window->lockReasons), FULL);
765 #endif
768 ** "Search" pull down menu.
770 menuPane = createMenu(menuBar, "searchMenu", "Search", 0, NULL, SHORT);
771 createMenuItem(menuPane, "find", "Find...", 'F', findCB, window, SHORT);
772 createFakeMenuItem(menuPane, "findShift", findCB, window);
773 window->findAgainItem=createMenuItem(menuPane, "findAgain", "Find Again", 'i', findSameCB, window,
774 SHORT);
775 XtSetSensitive(window->findAgainItem, NHist);
776 createFakeMenuItem(menuPane, "findAgainShift", findSameCB, window);
777 window->findSelItem=createMenuItem(menuPane, "findSelection", "Find Selection", 'S',
778 findSelCB, window, SHORT);
779 createFakeMenuItem(menuPane, "findSelectionShift", findSelCB, window);
780 createMenuItem(menuPane, "findIncremental", "Find Incremental", 'n',
781 findIncrCB, window, SHORT);
782 createFakeMenuItem(menuPane, "findIncrementalShift", findIncrCB, window);
783 createMenuItem(menuPane, "replace", "Replace...", 'R', replaceCB, window,
784 SHORT);
785 createFakeMenuItem(menuPane, "replaceShift", replaceCB, window);
786 window->replaceFindAgainItem=createMenuItem(menuPane, "replaceFindAgain", "Replace Find Again", 'A',
787 replaceFindSameCB, window, SHORT);
788 XtSetSensitive(window->replaceFindAgainItem, NHist);
789 createFakeMenuItem(menuPane, "replaceFindAgainShift", replaceFindSameCB, window);
790 window->replaceAgainItem=createMenuItem(menuPane, "replaceAgain", "Replace Again", 'p',
791 replaceSameCB, window, SHORT);
792 XtSetSensitive(window->replaceAgainItem, NHist);
793 createFakeMenuItem(menuPane, "replaceAgainShift", replaceSameCB, window);
794 createMenuSeparator(menuPane, "sep1", FULL);
795 createMenuItem(menuPane, "gotoLineNumber", "Goto Line Number...", 'L',
796 doActionCB, "goto_line_number_dialog", FULL);
797 window->gotoSelItem=createMenuItem(menuPane, "gotoSelected", "Goto Selected", 'G',
798 doActionCB, "goto_selected", FULL);
799 createMenuSeparator(menuPane, "sep2", FULL);
800 createMenuItem(menuPane, "mark", "Mark", 'k', markCB, window, FULL);
801 createMenuItem(menuPane, "gotoMark", "Goto Mark", 'o', gotoMarkCB, window,
802 FULL);
803 createFakeMenuItem(menuPane, "gotoMarkShift", gotoMarkCB, window);
804 createMenuSeparator(menuPane, "sep3", FULL);
805 createMenuItem(menuPane, "gotoMatching", "Goto Matching (..)", 'M',
806 gotoMatchingCB, window, FULL);
807 createFakeMenuItem(menuPane, "gotoMatchingShift", gotoMatchingCB, window);
808 window->findDefItem = createMenuItem(menuPane, "findDefinition",
809 "Find Definition", 'D', doActionCB, "find_definition", FULL);
810 XtSetSensitive(window->findDefItem, TagsFileList != NULL);
811 window->showTipItem = createMenuItem(menuPane, "showCalltip",
812 "Show Calltip", 'C', doActionCB, "show_tip", FULL);
813 XtSetSensitive(window->showTipItem, (TagsFileList != NULL ||
814 TipsFileList != NULL) );
817 ** Preferences menu, Default Settings sub menu
819 menuPane = createMenu(menuBar, "preferencesMenu", "Preferences", 0, NULL,
820 SHORT);
821 subPane = createMenu(menuPane, "defaultSettings", "Default Settings", 'D',
822 NULL, FULL);
823 createMenuItem(subPane, "languageModes", "Language Modes...", 'L',
824 languageDefCB, window, FULL);
826 /* Auto Indent sub menu */
827 subSubPane = createMenu(subPane, "autoIndent", "Auto Indent", 'A',
828 NULL, FULL);
829 window->autoIndentOffDefItem = createMenuRadioToggle(subSubPane, "off",
830 "Off", 'O', autoIndentOffDefCB, window,
831 GetPrefAutoIndent(PLAIN_LANGUAGE_MODE) == NO_AUTO_INDENT, SHORT);
832 window->autoIndentDefItem = createMenuRadioToggle(subSubPane, "on",
833 "On", 'n', autoIndentDefCB, window,
834 GetPrefAutoIndent(PLAIN_LANGUAGE_MODE) == AUTO_INDENT, SHORT);
835 window->smartIndentDefItem = createMenuRadioToggle(subSubPane, "smart",
836 "Smart", 'S', smartIndentDefCB, window,
837 GetPrefAutoIndent(PLAIN_LANGUAGE_MODE) == SMART_INDENT, SHORT);
838 createMenuSeparator(subSubPane, "sep1", SHORT);
839 createMenuItem(subSubPane, "ProgramSmartIndent", "Program Smart Indent...",
840 'P', smartMacrosDefCB, window, FULL);
842 /* Wrap sub menu */
843 subSubPane = createMenu(subPane, "wrap", "Wrap", 'W', NULL, FULL);
844 window->noWrapDefItem = createMenuRadioToggle(subSubPane,
845 "none", "None", 'N', noWrapDefCB,
846 window, GetPrefWrap(PLAIN_LANGUAGE_MODE) == NO_WRAP, SHORT);
847 window->newlineWrapDefItem = createMenuRadioToggle(subSubPane,
848 "autoNewline", "Auto Newline", 'A', newlineWrapDefCB,
849 window, GetPrefWrap(PLAIN_LANGUAGE_MODE) == NEWLINE_WRAP, SHORT);
850 window->contWrapDefItem = createMenuRadioToggle(subSubPane, "continuous",
851 "Continuous", 'C', contWrapDefCB, window,
852 GetPrefWrap(PLAIN_LANGUAGE_MODE) == CONTINUOUS_WRAP, SHORT);
853 createMenuSeparator(subSubPane, "sep1", SHORT);
854 createMenuItem(subSubPane, "wrapMargin", "Wrap Margin...", 'W',
855 wrapMarginDefCB, window, SHORT);
857 /* Smart Tags sub menu */
858 subSubPane = createMenu(subPane, "smartTags", "Tag Collisions", 'l',
859 NULL, FULL);
860 window->allTagsDefItem = createMenuRadioToggle(subSubPane, "showall",
861 "Show All", 'A', showAllTagsDefCB, window, !GetPrefSmartTags(),
862 FULL);
863 window->smartTagsDefItem = createMenuRadioToggle(subSubPane, "smart",
864 "Smart", 'S', smartTagsDefCB, window, GetPrefSmartTags(), FULL);
866 createMenuItem(subPane, "shellSel", "Command Shell...", 's', shellSelDefCB,
867 window, SHORT);
868 createMenuItem(subPane, "tabDistance", "Tab Stops...", 'T', tabsDefCB, window,
869 SHORT);
870 createMenuItem(subPane, "textFont", "Text Fonts...", 'F', fontDefCB, window,
871 FULL);
872 createMenuItem(subPane, "colors", "Colors...", 'C', colorDefCB, window,
873 FULL);
875 /* Customize Menus sub menu */
876 subSubPane = createMenu(subPane, "customizeMenus", "Customize Menus",
877 'u', NULL, FULL);
878 #ifndef VMS
879 createMenuItem(subSubPane, "shellMenu", "Shell Menu...", 'S',
880 shellDefCB, window, FULL);
881 #endif
882 createMenuItem(subSubPane, "macroMenu", "Macro Menu...", 'M',
883 macroDefCB, window, FULL);
884 createMenuItem(subSubPane, "windowBackgroundMenu",
885 "Window Background Menu...", 'W', bgMenuDefCB, window, FULL);
886 createMenuSeparator(subSubPane, "sep1", SHORT);
887 window->sortOpenPrevDefItem = createMenuToggle(subSubPane, "sortOpenPrevMenu",
888 "Sort Open Prev. Menu", 'o', sortOpenPrevDefCB, window,
889 GetPrefSortOpenPrevMenu(), FULL);
890 window->pathInWindowsMenuDefItem = createMenuToggle(subSubPane, "pathInWindowsMenu",
891 "Show Path In Windows Menu", 'P', pathInWindowsMenuDefCB, window, GetPrefShowPathInWindowsMenu(),
892 SHORT);
894 createMenuItem(subPane, "custimizeTitle", "Customize Window Title...", 'd',
895 customizeTitleDefCB, window, FULL);
897 /* Search sub menu */
898 subSubPane = createMenu(subPane, "searching", "Searching",
899 'g', NULL, FULL);
900 window->searchDlogsDefItem = createMenuToggle(subSubPane, "verbose",
901 "Verbose", 'V', searchDlogsDefCB, window,
902 GetPrefSearchDlogs(), SHORT);
903 window->searchWrapsDefItem = createMenuToggle(subSubPane, "wrapAround",
904 "Wrap Around", 'W', searchWrapsDefCB, window,
905 GetPrefSearchWraps(), SHORT);
906 window->beepOnSearchWrapDefItem = createMenuToggle(subSubPane,
907 "beepOnSearchWrap", "Beep On Search Wrap", 'B',
908 beepOnSearchWrapDefCB, window, GetPrefBeepOnSearchWrap(), SHORT);
909 window->keepSearchDlogsDefItem = createMenuToggle(subSubPane,
910 "keepDialogsUp", "Keep Dialogs Up", 'K',
911 keepSearchDlogsDefCB, window, GetPrefKeepSearchDlogs(), SHORT);
912 subSubSubPane = createMenu(subSubPane, "defaultSearchStyle",
913 "Default Search Style", 'D', NULL, FULL);
914 XtVaSetValues(subSubSubPane, XmNradioBehavior, True, NULL);
915 window->searchLiteralDefItem = createMenuToggle(subSubSubPane, "literal",
916 "Literal", 'L', searchLiteralCB, window,
917 GetPrefSearch() == SEARCH_LITERAL, FULL);
918 window->searchCaseSenseDefItem = createMenuToggle(subSubSubPane,
919 "caseSensitive", "Literal, Case Sensitive", 'C', searchCaseSenseCB, window,
920 GetPrefSearch() == SEARCH_CASE_SENSE, FULL);
921 window->searchLiteralWordDefItem = createMenuToggle(subSubSubPane, "literalWord",
922 "Literal, Whole Word", 'W', searchLiteralWordCB, window,
923 GetPrefSearch() == SEARCH_LITERAL_WORD, FULL);
924 window->searchCaseSenseWordDefItem = createMenuToggle(subSubSubPane,
925 "caseSensitiveWord", "Literal, Case Sensitive, Whole Word", 't', searchCaseSenseWordCB, window,
926 GetPrefSearch() == SEARCH_CASE_SENSE_WORD, FULL);
927 window->searchRegexDefItem = createMenuToggle(subSubSubPane,
928 "regularExpression", "Regular Expression", 'R', searchRegexCB,
929 window, GetPrefSearch() == SEARCH_REGEX, FULL);
930 window->searchRegexNoCaseDefItem = createMenuToggle(subSubSubPane,
931 "regularExpressionNoCase", "Regular Expression, Case Insensitive", 'I', searchRegexNoCaseCB, window,
932 GetPrefSearch() == SEARCH_REGEX_NOCASE, FULL);
933 #ifdef REPLACE_SCOPE
934 subSubSubPane = createMenu(subSubPane, "defaultReplaceScope",
935 "Default Replace Scope", 'R', NULL, FULL);
936 XtVaSetValues(subSubSubPane, XmNradioBehavior, True, NULL);
937 window->replScopeWinDefItem = createMenuToggle(subSubSubPane, "window",
938 "In Window", 'W', replaceScopeWindowCB, window,
939 GetPrefReplaceDefScope() == REPL_DEF_SCOPE_WINDOW, FULL);
940 window->replScopeSelDefItem = createMenuToggle(subSubSubPane, "selection",
941 "In Selection", 'S', replaceScopeSelectionCB, window,
942 GetPrefReplaceDefScope() == REPL_DEF_SCOPE_SELECTION, FULL);
943 window->replScopeSmartDefItem = createMenuToggle(subSubSubPane, "window",
944 "Smart", 'm', replaceScopeSmartCB, window,
945 GetPrefReplaceDefScope() == REPL_DEF_SCOPE_SMART, FULL);
946 #endif
948 /* Syntax Highlighting sub menu */
949 subSubPane = createMenu(subPane, "syntaxHighlighting","Syntax Highlighting",
950 'H', NULL, FULL);
951 window->highlightOffDefItem = createMenuRadioToggle(subSubPane, "off","Off",
952 'O', highlightOffDefCB, window, !GetPrefHighlightSyntax(), FULL);
953 window->highlightDefItem = createMenuRadioToggle(subSubPane, "on",
954 "On", 'n', highlightDefCB, window, GetPrefHighlightSyntax(), FULL);
955 createMenuSeparator(subSubPane, "sep1", SHORT);
956 createMenuItem(subSubPane, "recognitionPatterns", "Recognition Patterns...",
957 'R', highlightingDefCB, window, FULL);
958 createMenuItem(subSubPane, "textDrawingStyles", "Text Drawing Styles...", 'T',
959 stylesDefCB, window, FULL);
960 window->backlightCharsDefItem = createMenuToggle(subPane,
961 "backlightChars", "Apply Backlighting", 'g', backlightCharsDefCB,
962 window, GetPrefBacklightChars(), FULL);
964 /* tabbed editing sub menu */
965 subSubPane = createMenu(subPane, "tabbedEditMenu", "Tabbed Editing", 0,
966 &cascade, SHORT);
967 window->openInTabDefItem = createMenuToggle(subSubPane, "openAsTab",
968 "Open File In New Tab", 'T', openInTabDefCB, window,
969 GetPrefOpenInTab(), FULL);
970 window->tabBarDefItem = createMenuToggle(subSubPane, "showTabBar",
971 "Show Tab Bar", 'B', tabBarDefCB, window,
972 GetPrefTabBar(), FULL);
973 window->tabBarHideDefItem = createMenuToggle(subSubPane,
974 "hideTabBar", "Hide Tab Bar When Only One Document is Open", 'H',
975 tabBarHideDefCB, window, GetPrefTabBarHideOne(), FULL);
976 window->tabNavigateDefItem = createMenuToggle(subSubPane, "tabNavigateDef",
977 "Next/Prev Tabs Across Windows", 'W', tabNavigateDefCB, window,
978 GetPrefGlobalTabNavigate(), FULL);
979 window->tabSortDefItem = createMenuToggle(subSubPane, "tabSortDef",
980 "Sort Tabs Alphabetically", 'S', tabSortDefCB, window,
981 GetPrefSortTabs(), FULL);
983 window->toolTipsDefItem = createMenuToggle(subPane, "showTooltips",
984 "Show Tooltips", 0, toolTipsDefCB, window, GetPrefToolTips(),
985 FULL);
986 window->statsLineDefItem = createMenuToggle(subPane, "statisticsLine",
987 "Statistics Line", 'S', statsLineDefCB, window, GetPrefStatsLine(),
988 SHORT);
989 window->iSearchLineDefItem = createMenuToggle(subPane,
990 "incrementalSearchLine", "Incremental Search Line", 'i',
991 iSearchLineDefCB, window, GetPrefISearchLine(), FULL);
992 window->lineNumsDefItem = createMenuToggle(subPane, "showLineNumbers",
993 "Show Line Numbers", 'N', lineNumsDefCB, window, GetPrefLineNums(),
994 SHORT);
995 window->saveLastDefItem = createMenuToggle(subPane, "preserveLastVersion",
996 "Make Backup Copy (*.bck)", 'e', preserveDefCB, window,
997 GetPrefSaveOldVersion(), SHORT);
998 window->autoSaveDefItem = createMenuToggle(subPane, "incrementalBackup",
999 "Incremental Backup", 'B', autoSaveDefCB, window, GetPrefAutoSave(),
1000 SHORT);
1003 /* Show Matching sub menu */
1004 subSubPane = createMenu(subPane, "showMatching", "Show Matching (..)", 'M',
1005 NULL, FULL);
1006 window->showMatchingOffDefItem = createMenuRadioToggle(subSubPane, "off",
1007 "Off", 'O', showMatchingOffDefCB, window,
1008 GetPrefShowMatching() == NO_FLASH, SHORT);
1009 window->showMatchingDelimitDefItem = createMenuRadioToggle(subSubPane,
1010 "delimiter", "Delimiter", 'D', showMatchingDelimitDefCB, window,
1011 GetPrefShowMatching() == FLASH_DELIMIT, SHORT);
1012 window->showMatchingRangeDefItem = createMenuRadioToggle(subSubPane,
1013 "range", "Range", 'R', showMatchingRangeDefCB, window,
1014 GetPrefShowMatching() == FLASH_RANGE, SHORT);
1015 createMenuSeparator(subSubPane, "sep", SHORT);
1016 window->matchSyntaxBasedDefItem = createMenuToggle(subSubPane,
1017 "matchSyntax", "Syntax Based", 'S', matchSyntaxBasedDefCB, window,
1018 GetPrefMatchSyntaxBased(), SHORT);
1020 /* Append LF at end of files on save */
1021 window->appendLFItem = createMenuToggle(subPane, "appendLFItem",
1022 "Terminate with Line Break on Save", 'v', appendLFCB, NULL,
1023 GetPrefAppendLF(), FULL);
1025 window->reposDlogsDefItem = createMenuToggle(subPane, "popupsUnderPointer",
1026 "Popups Under Pointer", 'P', reposDlogsDefCB, window,
1027 GetPrefRepositionDialogs(), FULL);
1028 window->autoScrollDefItem = createMenuToggle(subPane, "autoScroll",
1029 "Auto Scroll Near Window Top/Bottom", 0, autoScrollDefCB, window,
1030 GetPrefAutoScroll(), FULL);
1031 subSubPane = createMenu(subPane, "warnings", "Warnings", 'r', NULL, FULL);
1032 window->modWarnDefItem = createMenuToggle(subSubPane,
1033 "filesModifiedExternally", "Files Modified Externally", 'F',
1034 modWarnDefCB, window, GetPrefWarnFileMods(), FULL);
1035 window->modWarnRealDefItem = createMenuToggle(subSubPane,
1036 "checkModifiedFileContents", "Check Modified File Contents", 'C',
1037 modWarnRealDefCB, window, GetPrefWarnRealFileMods(), FULL);
1038 XtSetSensitive(window->modWarnRealDefItem, GetPrefWarnFileMods());
1039 window->exitWarnDefItem = createMenuToggle(subSubPane, "onExit", "On Exit", 'O',
1040 exitWarnDefCB, window, GetPrefWarnExit(), FULL);
1042 /* Initial Window Size sub menu (simulates radioBehavior) */
1043 subSubPane = createMenu(subPane, "initialwindowSize",
1044 "Initial Window Size", 'z', NULL, FULL);
1045 /* XtVaSetValues(subSubPane, XmNradioBehavior, True, NULL); */
1046 window->size24x80DefItem = btn = createMenuToggle(subSubPane, "24X80",
1047 "24 x 80", '2', size24x80CB, window, False, SHORT);
1048 XtVaSetValues(btn, XmNindicatorType, XmONE_OF_MANY, NULL);
1049 window->size40x80DefItem = btn = createMenuToggle(subSubPane, "40X80",
1050 "40 x 80", '4', size40x80CB, window, False, SHORT);
1051 XtVaSetValues(btn, XmNindicatorType, XmONE_OF_MANY, NULL);
1052 window->size60x80DefItem = btn = createMenuToggle(subSubPane, "60X80",
1053 "60 x 80", '6', size60x80CB, window, False, SHORT);
1054 XtVaSetValues(btn, XmNindicatorType, XmONE_OF_MANY, NULL);
1055 window->size80x80DefItem = btn = createMenuToggle(subSubPane, "80X80",
1056 "80 x 80", '8', size80x80CB, window, False, SHORT);
1057 XtVaSetValues(btn, XmNindicatorType, XmONE_OF_MANY, NULL);
1058 window->sizeCustomDefItem = btn = createMenuToggle(subSubPane, "custom",
1059 "Custom...", 'C', sizeCustomCB, window, False, SHORT);
1060 XtVaSetValues(btn, XmNindicatorType, XmONE_OF_MANY, NULL);
1061 updateWindowSizeMenu(window);
1064 ** Remainder of Preferences menu
1066 createMenuItem(menuPane, "saveDefaults", "Save Defaults...", 'v',
1067 savePrefCB, window, FULL);
1068 #ifdef SGI_CUSTOM
1069 window->shortMenusDefItem = createMenuToggle(menuPane,
1070 "shortMenus", "Short Menus", 'h', shortMenusCB, window,
1071 GetPrefShortMenus(), SHORT);
1072 #endif
1073 createMenuSeparator(menuPane, "sep1", SHORT);
1074 window->statsLineItem = createMenuToggle(menuPane, "statisticsLine", "Statistics Line", 'S',
1075 statsCB, window, GetPrefStatsLine(), SHORT);
1076 window->iSearchLineItem = createMenuToggle(menuPane, "incrementalSearchLine","Incremental Search Line",
1077 'I', doActionCB, "set_incremental_search_line", GetPrefISearchLine(), FULL);
1078 window->lineNumsItem = createMenuToggle(menuPane, "lineNumbers", "Show Line Numbers", 'N',
1079 doActionCB, "set_show_line_numbers", GetPrefLineNums(), SHORT);
1080 CreateLanguageModeSubMenu(window, menuPane, "languageMode",
1081 "Language Mode", 'L');
1082 subPane = createMenu(menuPane, "autoIndent", "Auto Indent",
1083 'A', NULL, FULL);
1084 window->autoIndentOffItem = createMenuRadioToggle(subPane, "off", "Off",
1085 'O', autoIndentOffCB, window, window->indentStyle == NO_AUTO_INDENT,
1086 SHORT);
1087 window->autoIndentItem = createMenuRadioToggle(subPane, "on", "On", 'n',
1088 autoIndentCB, window, window->indentStyle == AUTO_INDENT, SHORT);
1089 window->smartIndentItem = createMenuRadioToggle(subPane, "smart", "Smart",
1090 'S', smartIndentCB, window, window->indentStyle == SMART_INDENT,
1091 SHORT);
1092 subPane = createMenu(menuPane, "wrap", "Wrap",
1093 'W', NULL, FULL);
1094 window->noWrapItem = createMenuRadioToggle(subPane, "none",
1095 "None", 'N', noWrapCB, window,
1096 window->wrapMode==NO_WRAP, SHORT);
1097 window->newlineWrapItem = createMenuRadioToggle(subPane, "autoNewlineWrap",
1098 "Auto Newline", 'A', newlineWrapCB, window,
1099 window->wrapMode==NEWLINE_WRAP, SHORT);
1100 window->continuousWrapItem = createMenuRadioToggle(subPane,
1101 "continuousWrap", "Continuous", 'C', continuousWrapCB, window,
1102 window->wrapMode==CONTINUOUS_WRAP, SHORT);
1103 createMenuSeparator(subPane, "sep1", SHORT);
1104 createMenuItem(subPane, "wrapMargin", "Wrap Margin...", 'W',
1105 wrapMarginCB, window, SHORT);
1106 createMenuItem(menuPane, "tabs", "Tab Stops...", 'T', tabsCB, window, SHORT);
1107 createMenuItem(menuPane, "textFont", "Text Fonts...", 'F', fontCB, window,
1108 FULL);
1109 window->highlightItem = createMenuToggle(menuPane, "highlightSyntax",
1110 "Highlight Syntax", 'H', doActionCB, "set_highlight_syntax",
1111 GetPrefHighlightSyntax(), SHORT);
1112 window->backlightCharsItem = createMenuToggle(menuPane, "backlightChars",
1113 "Apply Backlighting", 'g', backlightCharsCB, window,
1114 window->backlightChars, FULL);
1115 #ifndef VMS
1116 window->saveLastItem = createMenuToggle(menuPane, "makeBackupCopy",
1117 "Make Backup Copy (*.bck)", 'e', preserveCB, window,
1118 window->saveOldVersion, SHORT);
1119 #endif
1120 window->autoSaveItem = createMenuToggle(menuPane, "incrementalBackup",
1121 "Incremental Backup", 'B', autoSaveCB, window, window->autoSave,
1122 SHORT);
1124 subPane = createMenu(menuPane, "showMatching", "Show Matching (..)",
1125 'M', NULL, FULL);
1126 window->showMatchingOffItem = createMenuRadioToggle(subPane, "off", "Off",
1127 'O', showMatchingOffCB, window, window->showMatchingStyle == NO_FLASH,
1128 SHORT);
1129 window->showMatchingDelimitItem = createMenuRadioToggle(subPane,
1130 "delimiter", "Delimiter", 'D', showMatchingDelimitCB, window,
1131 window->showMatchingStyle == FLASH_DELIMIT, SHORT);
1132 window->showMatchingRangeItem = createMenuRadioToggle(subPane, "range",
1133 "Range", 'R', showMatchingRangeCB, window,
1134 window->showMatchingStyle == FLASH_RANGE, SHORT);
1135 createMenuSeparator(subPane, "sep", SHORT);
1136 window->matchSyntaxBasedItem = createMenuToggle(subPane, "matchSyntax",
1137 "Syntax Based", 'S', matchSyntaxBasedCB, window,
1138 window->matchSyntaxBased, SHORT);
1140 #ifndef SGI_CUSTOM
1141 createMenuSeparator(menuPane, "sep2", SHORT);
1142 window->overtypeModeItem = createMenuToggle(menuPane, "overtype", "Overtype", 'O',
1143 doActionCB, "set_overtype_mode", False, SHORT);
1144 window->readOnlyItem = createMenuToggle(menuPane, "readOnly", "Read Only",
1145 'y', doActionCB, "set_locked", IS_USER_LOCKED(window->lockReasons), FULL);
1146 #endif
1148 #ifndef VMS
1150 ** Create the Shell menu
1152 menuPane = window->shellMenuPane =
1153 createMenu(menuBar, "shellMenu", "Shell", 0, &cascade, FULL);
1154 btn = createMenuItem(menuPane, "executeCommand", "Execute Command...",
1155 'E', doActionCB, "execute_command_dialog", SHORT);
1156 XtVaSetValues(btn, XmNuserData, PERMANENT_MENU_ITEM, NULL);
1157 btn = createMenuItem(menuPane, "executeCommandLine", "Execute Command Line",
1158 'x', doActionCB, "execute_command_line", SHORT);
1159 XtVaSetValues(btn, XmNuserData, PERMANENT_MENU_ITEM, NULL);
1160 window->filterItem = createMenuItem(menuPane, "filterSelection",
1161 "Filter Selection...", 'F', doActionCB, "filter_selection_dialog",
1162 SHORT);
1163 XtVaSetValues(window->filterItem, XmNuserData, PERMANENT_MENU_ITEM,
1164 XmNsensitive, window->wasSelected, NULL);
1165 window->cancelShellItem = createMenuItem(menuPane, "cancelShellCommand",
1166 "Cancel Shell Command", 'C', cancelShellCB, window, SHORT);
1167 XtVaSetValues(window->cancelShellItem, XmNuserData, PERMANENT_MENU_ITEM,
1168 XmNsensitive, False, NULL);
1169 btn = createMenuSeparator(menuPane, "sep1", SHORT);
1170 XtVaSetValues(btn, XmNuserData, PERMANENT_MENU_ITEM, NULL);
1171 #endif
1174 ** Create the Macro menu
1176 menuPane = window->macroMenuPane =
1177 createMenu(menuBar, "macroMenu", "Macro", 0, &cascade, FULL);
1178 window->learnItem = createMenuItem(menuPane, "learnKeystrokes",
1179 "Learn Keystrokes", 'L', learnCB, window, SHORT);
1180 XtVaSetValues(window->learnItem , XmNuserData, PERMANENT_MENU_ITEM, NULL);
1181 window->finishLearnItem = createMenuItem(menuPane, "finishLearn",
1182 "Finish Learn", 'F', finishLearnCB, window, SHORT);
1183 XtVaSetValues(window->finishLearnItem , XmNuserData, PERMANENT_MENU_ITEM,
1184 XmNsensitive, False, NULL);
1185 window->cancelMacroItem = createMenuItem(menuPane, "cancelLearn",
1186 "Cancel Learn", 'C', cancelLearnCB, window, SHORT);
1187 XtVaSetValues(window->cancelMacroItem, XmNuserData, PERMANENT_MENU_ITEM,
1188 XmNsensitive, False, NULL);
1189 window->replayItem = createMenuItem(menuPane, "replayKeystrokes",
1190 "Replay Keystrokes", 'K', replayCB, window, SHORT);
1191 XtVaSetValues(window->replayItem, XmNuserData, PERMANENT_MENU_ITEM,
1192 XmNsensitive, GetReplayMacro() != NULL, NULL);
1193 window->repeatItem = createMenuItem(menuPane, "repeat",
1194 "Repeat...", 'R', doActionCB, "repeat_dialog", SHORT);
1195 XtVaSetValues(window->repeatItem, XmNuserData, PERMANENT_MENU_ITEM, NULL);
1196 btn = createMenuSeparator(menuPane, "sep1", SHORT);
1197 XtVaSetValues(btn, XmNuserData, PERMANENT_MENU_ITEM, NULL);
1200 ** Create the Windows menu
1202 menuPane = window->windowMenuPane = createMenu(menuBar, "windowsMenu",
1203 "Windows", 0, &cascade, FULL);
1204 XtAddCallback(cascade, XmNcascadingCallback, (XtCallbackProc)windowMenuCB,
1205 window);
1206 window->splitPaneItem = createMenuItem(menuPane, "splitPane",
1207 "Split Pane", 'S', doActionCB, "split_pane", SHORT);
1208 XtVaSetValues(window->splitPaneItem, XmNuserData, PERMANENT_MENU_ITEM,
1209 NULL);
1210 window->closePaneItem = createMenuItem(menuPane, "closePane",
1211 "Close Pane", 'C', doActionCB, "close_pane", SHORT);
1212 XtVaSetValues(window->closePaneItem, XmNuserData, PERMANENT_MENU_ITEM,NULL);
1213 XtSetSensitive(window->closePaneItem, False);
1215 btn = createMenuSeparator(menuPane, "sep01", SHORT);
1216 XtVaSetValues(btn, XmNuserData, PERMANENT_MENU_ITEM, NULL);
1217 window->detachDocumentItem = createMenuItem(menuPane, "detachBuffer",
1218 "Detach Tab", 'D', doActionCB, "detach_document", SHORT);
1219 XtSetSensitive(window->detachDocumentItem, False);
1221 window->moveDocumentItem = createMenuItem(menuPane, "moveDocument",
1222 "Move Tab To...", 'M', doActionCB, "move_document_dialog", SHORT);
1223 XtSetSensitive(window->moveDocumentItem, False);
1224 btn = createMenuSeparator(menuPane, "sep1", SHORT);
1225 XtVaSetValues(btn, XmNuserData, PERMANENT_MENU_ITEM, NULL);
1228 ** Create "Help" pull down menu.
1230 menuPane = createMenu(menuBar, "helpMenu", "Help", 0, &cascade, SHORT);
1231 XtVaSetValues(menuBar, XmNmenuHelpWidget, cascade, NULL);
1232 buildHelpMenu( menuPane, &H_M[0], window );
1234 return menuBar;
1237 /*----------------------------------------------------------------------------*/
1239 static Widget makeHelpMenuItem(
1241 Widget parent,
1242 char *name, /* to be assigned to the child widget */
1243 char *label, /* text to be displayed in menu */
1244 char mnemonic, /* letter in label to be underlined */
1245 menuCallbackProc callback, /* activated when menu item selected */
1246 void *cbArg, /* passed to activated call back */
1247 int mode, /* SGI_CUSTOM menu option */
1248 enum HelpTopic topic /* associated with this menu item */
1251 Widget menuItem =
1252 createMenuItem( parent, name, label, mnemonic, callback, cbArg, mode );
1254 XtVaSetValues( menuItem, XmNuserData, (XtPointer)topic, NULL );
1255 return menuItem;
1258 /*----------------------------------------------------------------------------*/
1260 static void helpCB( Widget menuItem, XtPointer clientData, XtPointer callData )
1262 enum HelpTopic topic;
1263 XtPointer userData;
1265 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(menuItem))->lastFocus,
1266 ((XmAnyCallbackStruct *)callData)->event);
1267 XtVaGetValues( menuItem, XmNuserData, &userData, NULL );
1268 topic = (enum HelpTopic)userData;
1270 Help(topic);
1273 /*----------------------------------------------------------------------------*/
1275 #define NON_MENU_HELP 9
1277 static HelpMenu * buildHelpMenu(
1279 Widget pane, /* Menu pane on which to place new menu items */
1280 HelpMenu * menu, /* Data to drive building the help menu */
1281 WindowInfo * window /* Main NEdit window information */
1284 #ifdef VMS
1285 int hideIt = 1; /* All menu items matching this will be inaccessible */
1286 #else
1287 int hideIt = -1; /* This value should make all menu items accessible */
1288 #endif
1290 if( menu != NULL )
1292 int crntLevel = menu->level;
1294 /*-------------------------
1295 * For each menu element ...
1296 *-------------------------*/
1297 while( menu != NULL && menu->level == crntLevel )
1299 /*----------------------------------------------
1300 * ... see if dealing with a separator or submenu
1301 *----------------------------------------------*/
1302 if( menu->topic == HELP_none )
1304 if( menu->mnemonic == '-' )
1306 createMenuSeparator(pane, menu->wgtName, SHORT);
1307 menu = menu->next;
1309 else
1311 /*-------------------------------------------------------
1312 * Do not show any of the submenu when it is to be hidden.
1313 *-------------------------------------------------------*/
1314 if( menu->hideIt == hideIt || menu->hideIt == NON_MENU_HELP )
1316 do { menu = menu->next;
1317 } while( menu != NULL && menu->level > crntLevel );
1320 else
1322 Widget subPane =
1323 createMenu( pane, menu->wgtName, menu->subTitle,
1324 menu->mnemonic, NULL, FULL);
1326 menu = buildHelpMenu( subPane, menu->next, window );
1331 else
1333 /*---------------------------------------
1334 * Show menu item if not going to hide it.
1335 * This is the easy way out of hiding
1336 * menu items. When entire submenus want
1337 * to be hidden, either the entire branch
1338 * will have to be marked, or this algorithm
1339 * will have to become a lot smarter.
1340 *---------------------------------------*/
1341 if( menu->hideIt != hideIt && menu->hideIt != NON_MENU_HELP )
1342 makeHelpMenuItem(
1343 pane, menu->wgtName, HelpTitles[menu->topic],
1344 menu->mnemonic, helpCB, window, SHORT, menu->topic );
1346 menu = menu->next;
1351 return menu;
1354 /*----------------------------------------------------------------------------*/
1357 ** handle actions called from the context menus of tabs.
1359 static void doTabActionCB(Widget w, XtPointer clientData, XtPointer callData)
1361 Widget menu = MENU_WIDGET(w);
1362 WindowInfo *win, *window = WidgetToWindow(menu);
1364 /* extract the window to be acted upon, see comment in
1365 tabMenuPostAP() for detail */
1366 XtVaGetValues(window->tabMenuPane, XmNuserData, &win, NULL);
1368 HidePointerOnKeyedEvent(win->lastFocus,
1369 ((XmAnyCallbackStruct *)callData)->event);
1370 XtCallActionProc(win->lastFocus, (char *)clientData,
1371 ((XmAnyCallbackStruct *)callData)->event, NULL, 0);
1374 static void doActionCB(Widget w, XtPointer clientData, XtPointer callData)
1376 Widget menu = MENU_WIDGET(w);
1377 Widget widget = WidgetToWindow(menu)->lastFocus;
1378 String action = (String) clientData;
1379 XEvent* event = ((XmAnyCallbackStruct*) callData)->event;
1381 HidePointerOnKeyedEvent(widget, event);
1383 XtCallActionProc(widget, action, event, NULL, 0);
1386 static void pasteColCB(Widget w, XtPointer clientData, XtPointer callData)
1388 static char *params[1] = {"rect"};
1390 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1391 ((XmAnyCallbackStruct *)callData)->event);
1392 XtCallActionProc(WidgetToWindow(MENU_WIDGET(w))->lastFocus, "paste_clipboard",
1393 ((XmAnyCallbackStruct *)callData)->event, params, 1);
1396 static void shiftLeftCB(Widget w, XtPointer clientData, XtPointer callData)
1398 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1399 ((XmAnyCallbackStruct *)callData)->event);
1400 XtCallActionProc(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1401 ((XmAnyCallbackStruct *)callData)->event->xbutton.state & ShiftMask
1402 ? "shift_left_by_tab" : "shift_left",
1403 ((XmAnyCallbackStruct *)callData)->event, NULL, 0);
1406 static void shiftRightCB(Widget w, XtPointer clientData, XtPointer callData)
1408 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1409 ((XmAnyCallbackStruct *)callData)->event);
1410 XtCallActionProc(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1411 ((XmAnyCallbackStruct *)callData)->event->xbutton.state & ShiftMask
1412 ? "shift_right_by_tab" : "shift_right",
1413 ((XmAnyCallbackStruct *)callData)->event, NULL, 0);
1416 static void findCB(Widget w, XtPointer clientData, XtPointer callData)
1418 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1419 ((XmAnyCallbackStruct *)callData)->event);
1420 XtCallActionProc(WidgetToWindow(MENU_WIDGET(w))->lastFocus, "find_dialog",
1421 ((XmAnyCallbackStruct *)callData)->event,
1422 shiftKeyToDir(callData), 1);
1425 static void findSameCB(Widget w, XtPointer clientData, XtPointer callData)
1427 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1428 ((XmAnyCallbackStruct *)callData)->event);
1429 XtCallActionProc(WidgetToWindow(MENU_WIDGET(w))->lastFocus, "find_again",
1430 ((XmAnyCallbackStruct *)callData)->event,
1431 shiftKeyToDir(callData), 1);
1434 static void findSelCB(Widget w, XtPointer clientData, XtPointer callData)
1436 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1437 ((XmAnyCallbackStruct *)callData)->event);
1438 XtCallActionProc(WidgetToWindow(MENU_WIDGET(w))->lastFocus, "find_selection",
1439 ((XmAnyCallbackStruct *)callData)->event,
1440 shiftKeyToDir(callData), 1);
1443 static void findIncrCB(Widget w, XtPointer clientData, XtPointer callData)
1445 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1446 ((XmAnyCallbackStruct *)callData)->event);
1447 XtCallActionProc(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1448 "start_incremental_find", ((XmAnyCallbackStruct *)callData)->event,
1449 shiftKeyToDir(callData), 1);
1452 static void replaceCB(Widget w, XtPointer clientData, XtPointer callData)
1454 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1455 ((XmAnyCallbackStruct *)callData)->event);
1456 XtCallActionProc(WidgetToWindow(MENU_WIDGET(w))->lastFocus, "replace_dialog",
1457 ((XmAnyCallbackStruct *)callData)->event,
1458 shiftKeyToDir(callData), 1);
1461 static void replaceSameCB(Widget w, XtPointer clientData, XtPointer callData)
1463 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1464 ((XmAnyCallbackStruct *)callData)->event);
1465 XtCallActionProc(WidgetToWindow(MENU_WIDGET(w))->lastFocus, "replace_again",
1466 ((XmAnyCallbackStruct *)callData)->event,
1467 shiftKeyToDir(callData), 1);
1470 static void replaceFindSameCB(Widget w, XtPointer clientData, XtPointer callData)
1472 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1473 ((XmAnyCallbackStruct *)callData)->event);
1474 XtCallActionProc(WidgetToWindow(MENU_WIDGET(w))->lastFocus, "replace_find_same",
1475 ((XmAnyCallbackStruct *)callData)->event,
1476 shiftKeyToDir(callData), 1);
1479 static void markCB(Widget w, XtPointer clientData, XtPointer callData)
1481 XEvent *event = ((XmAnyCallbackStruct *)callData)->event;
1482 WindowInfo *window = WidgetToWindow(MENU_WIDGET(w));
1484 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1485 ((XmAnyCallbackStruct *)callData)->event);
1486 if (event->type == KeyPress || event->type == KeyRelease)
1487 BeginMarkCommand(window);
1488 else
1489 XtCallActionProc(window->lastFocus, "mark_dialog", event, NULL, 0);
1492 static void gotoMarkCB(Widget w, XtPointer clientData, XtPointer callData)
1494 XEvent *event = ((XmAnyCallbackStruct *)callData)->event;
1495 WindowInfo *window = WidgetToWindow(MENU_WIDGET(w));
1496 int extend = event->xbutton.state & ShiftMask;
1497 static char *params[1] = {"extend"};
1499 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1500 ((XmAnyCallbackStruct *)callData)->event);
1501 if (event->type == KeyPress || event->type == KeyRelease)
1502 BeginGotoMarkCommand(window, extend);
1503 else
1504 XtCallActionProc(window->lastFocus, "goto_mark_dialog", event, params,
1505 extend ? 1 : 0);
1508 static void gotoMatchingCB(Widget w, XtPointer clientData, XtPointer callData)
1510 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1511 ((XmAnyCallbackStruct *)callData)->event);
1512 XtCallActionProc(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1513 ((XmAnyCallbackStruct *)callData)->event->xbutton.state & ShiftMask
1514 ? "select_to_matching" : "goto_matching",
1515 ((XmAnyCallbackStruct *)callData)->event, NULL, 0);
1518 static void autoIndentOffCB(Widget w, WindowInfo *window, caddr_t callData)
1520 static char *params[1] = {"off"};
1521 Widget menu = MENU_WIDGET(w);
1523 window = WidgetToWindow(menu);
1525 #ifdef SGI_CUSTOM
1526 if (shortPrefAskDefault(window->shell, w, "Auto Indent Off")) {
1527 autoIndentOffDefCB(w, window, callData);
1528 SaveNEditPrefs(window->shell, GetPrefShortMenus());
1530 #endif
1531 HidePointerOnKeyedEvent(WidgetToWindow(menu)->lastFocus,
1532 ((XmAnyCallbackStruct *)callData)->event);
1533 XtCallActionProc(WidgetToWindow(menu)->lastFocus, "set_auto_indent",
1534 ((XmAnyCallbackStruct *)callData)->event, params, 1);
1537 static void autoIndentCB(Widget w, WindowInfo *window, caddr_t callData)
1539 static char *params[1] = {"on"};
1540 Widget menu = MENU_WIDGET(w);
1542 window = WidgetToWindow(menu);
1544 #ifdef SGI_CUSTOM
1545 if (shortPrefAskDefault(window->shell, w, "Auto Indent")) {
1546 autoIndentDefCB(w, window, callData);
1547 SaveNEditPrefs(window->shell, GetPrefShortMenus());
1549 #endif
1550 HidePointerOnKeyedEvent(WidgetToWindow(menu)->lastFocus,
1551 ((XmAnyCallbackStruct *)callData)->event);
1552 XtCallActionProc(WidgetToWindow(menu)->lastFocus, "set_auto_indent",
1553 ((XmAnyCallbackStruct *)callData)->event, params, 1);
1556 static void smartIndentCB(Widget w, WindowInfo *window, caddr_t callData)
1558 static char *params[1] = {"smart"};
1559 Widget menu = MENU_WIDGET(w);
1561 window = WidgetToWindow(menu);
1563 #ifdef SGI_CUSTOM
1564 if (shortPrefAskDefault(window->shell, w, "Smart Indent")) {
1565 smartIndentDefCB(w, window, callData);
1566 SaveNEditPrefs(window->shell, GetPrefShortMenus());
1568 #endif
1569 HidePointerOnKeyedEvent(WidgetToWindow(menu)->lastFocus,
1570 ((XmAnyCallbackStruct *)callData)->event);
1571 XtCallActionProc(WidgetToWindow(menu)->lastFocus, "set_auto_indent",
1572 ((XmAnyCallbackStruct *)callData)->event, params, 1);
1575 static void autoSaveCB(Widget w, WindowInfo *window, caddr_t callData)
1577 Widget menu = MENU_WIDGET(w);
1579 window = WidgetToWindow(menu);
1581 #ifdef SGI_CUSTOM
1582 if (shortPrefAskDefault(window->shell, w, "Incremental Backup")) {
1583 autoSaveDefCB(w, window, callData);
1584 SaveNEditPrefs(window->shell, GetPrefShortMenus());
1586 #endif
1587 HidePointerOnKeyedEvent(WidgetToWindow(menu)->lastFocus,
1588 ((XmAnyCallbackStruct *)callData)->event);
1589 XtCallActionProc(WidgetToWindow(menu)->lastFocus, "set_incremental_backup",
1590 ((XmAnyCallbackStruct *)callData)->event, NULL, 0);
1593 static void preserveCB(Widget w, WindowInfo *window, caddr_t callData)
1595 Widget menu = MENU_WIDGET(w);
1597 window = WidgetToWindow(menu);
1599 #ifdef SGI_CUSTOM
1600 if (shortPrefAskDefault(window->shell, w, "Make Backup Copy")) {
1601 preserveDefCB(w, window, callData);
1602 SaveNEditPrefs(window->shell, GetPrefShortMenus());
1604 #endif
1605 HidePointerOnKeyedEvent(WidgetToWindow(menu)->lastFocus,
1606 ((XmAnyCallbackStruct *)callData)->event);
1607 XtCallActionProc(WidgetToWindow(menu)->lastFocus, "set_make_backup_copy",
1608 ((XmAnyCallbackStruct *)callData)->event, NULL, 0);
1611 static void showMatchingOffCB(Widget w, WindowInfo *window, caddr_t callData)
1613 static char *params[1] = {NO_FLASH_STRING};
1614 Widget menu = MENU_WIDGET(w);
1616 window = WidgetToWindow(menu);
1618 #ifdef SGI_CUSTOM
1619 if (shortPrefAskDefault(window->shell, w, "Show Matching Off")) {
1620 showMatchingOffDefCB(w, window, callData);
1621 SaveNEditPrefs(window->shell, GetPrefShortMenus());
1623 #endif
1624 HidePointerOnKeyedEvent(WidgetToWindow(menu)->lastFocus,
1625 ((XmAnyCallbackStruct *)callData)->event);
1626 XtCallActionProc(WidgetToWindow(menu)->lastFocus, "set_show_matching",
1627 ((XmAnyCallbackStruct *)callData)->event, params, 1);
1630 static void showMatchingDelimitCB(Widget w, WindowInfo *window, caddr_t callData)
1632 static char *params[1] = {FLASH_DELIMIT_STRING};
1633 Widget menu = MENU_WIDGET(w);
1635 window = WidgetToWindow(menu);
1637 #ifdef SGI_CUSTOM
1638 if (shortPrefAskDefault(window->shell, w, "Show Matching Delimiter")) {
1639 showMatchingDelimitDefCB(w, window, callData);
1640 SaveNEditPrefs(window->shell, GetPrefShortMenus());
1642 #endif
1643 HidePointerOnKeyedEvent(WidgetToWindow(menu)->lastFocus,
1644 ((XmAnyCallbackStruct *)callData)->event);
1645 XtCallActionProc(WidgetToWindow(menu)->lastFocus, "set_show_matching",
1646 ((XmAnyCallbackStruct *)callData)->event, params, 1);
1649 static void showMatchingRangeCB(Widget w, WindowInfo *window, caddr_t callData)
1651 static char *params[1] = {FLASH_RANGE_STRING};
1652 Widget menu = MENU_WIDGET(w);
1654 window = WidgetToWindow(menu);
1656 #ifdef SGI_CUSTOM
1657 if (shortPrefAskDefault(window->shell, w, "Show Matching Range")) {
1658 showMatchingRangeDefCB(w, window, callData);
1659 SaveNEditPrefs(window->shell, GetPrefShortMenus());
1661 #endif
1662 HidePointerOnKeyedEvent(WidgetToWindow(menu)->lastFocus,
1663 ((XmAnyCallbackStruct *)callData)->event);
1664 XtCallActionProc(WidgetToWindow(menu)->lastFocus, "set_show_matching",
1665 ((XmAnyCallbackStruct *)callData)->event, params, 1);
1668 static void matchSyntaxBasedCB(Widget w, WindowInfo *window, caddr_t callData)
1670 Widget menu = MENU_WIDGET(w);
1672 window = WidgetToWindow(menu);
1674 #ifdef SGI_CUSTOM
1675 if (shortPrefAskDefault(window->shell, w, "Match Syntax Based")) {
1676 matchSyntaxBasedDefCB(w, window, callData);
1677 SaveNEditPrefs(window->shell, GetPrefShortMenus());
1679 #endif
1680 HidePointerOnKeyedEvent(WidgetToWindow(menu)->lastFocus,
1681 ((XmAnyCallbackStruct *)callData)->event);
1682 XtCallActionProc(WidgetToWindow(menu)->lastFocus, "set_match_syntax_based",
1683 ((XmAnyCallbackStruct *)callData)->event, NULL, 0);
1686 static void fontCB(Widget w, WindowInfo *window, caddr_t callData)
1688 ChooseFonts(WidgetToWindow(MENU_WIDGET(w)), True);
1691 static void noWrapCB(Widget w, WindowInfo *window, caddr_t callData)
1693 static char *params[1] = {"none"};
1694 Widget menu = MENU_WIDGET(w);
1696 window = WidgetToWindow(menu);
1698 #ifdef SGI_CUSTOM
1699 if (shortPrefAskDefault(window->shell, w, "No Wrap")) {
1700 noWrapDefCB(w, window, callData);
1701 SaveNEditPrefs(window->shell, GetPrefShortMenus());
1703 #endif
1704 HidePointerOnKeyedEvent(WidgetToWindow(menu)->lastFocus,
1705 ((XmAnyCallbackStruct *)callData)->event);
1706 XtCallActionProc(WidgetToWindow(menu)->lastFocus, "set_wrap_text",
1707 ((XmAnyCallbackStruct *)callData)->event, params, 1);
1710 static void newlineWrapCB(Widget w, WindowInfo *window, caddr_t callData)
1712 static char *params[1] = {"auto"};
1713 Widget menu = MENU_WIDGET(w);
1715 window = WidgetToWindow(menu);
1717 #ifdef SGI_CUSTOM
1718 if (shortPrefAskDefault(window->shell, w, "Auto Newline Wrap")) {
1719 newlineWrapDefCB(w, window, callData);
1720 SaveNEditPrefs(window->shell, GetPrefShortMenus());
1722 #endif
1723 HidePointerOnKeyedEvent(WidgetToWindow(menu)->lastFocus,
1724 ((XmAnyCallbackStruct *)callData)->event);
1725 XtCallActionProc(WidgetToWindow(menu)->lastFocus, "set_wrap_text",
1726 ((XmAnyCallbackStruct *)callData)->event, params, 1);
1729 static void continuousWrapCB(Widget w, WindowInfo *window, caddr_t callData)
1731 static char *params[1] = {"continuous"};
1732 Widget menu = MENU_WIDGET(w);
1734 window = WidgetToWindow(menu);
1736 #ifdef SGI_CUSTOM
1737 if (shortPrefAskDefault(window->shell, w, "Continuous Wrap")) {
1738 contWrapDefCB(w, window, callData);
1739 SaveNEditPrefs(window->shell, GetPrefShortMenus());
1741 #endif
1742 HidePointerOnKeyedEvent(WidgetToWindow(menu)->lastFocus,
1743 ((XmAnyCallbackStruct *)callData)->event);
1744 XtCallActionProc(WidgetToWindow(menu)->lastFocus, "set_wrap_text",
1745 ((XmAnyCallbackStruct *)callData)->event, params, 1);
1748 static void wrapMarginCB(Widget w, WindowInfo *window, caddr_t callData)
1750 window = WidgetToWindow(MENU_WIDGET(w));
1752 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1753 ((XmAnyCallbackStruct *)callData)->event);
1754 WrapMarginDialog(window->shell, window);
1757 static void backlightCharsCB(Widget w, WindowInfo *window, caddr_t callData)
1759 int applyBacklight = XmToggleButtonGetState(w);
1760 window = WidgetToWindow(MENU_WIDGET(w));
1761 SetBacklightChars(window, applyBacklight?GetPrefBacklightCharTypes():NULL);
1764 static void tabsCB(Widget w, WindowInfo *window, caddr_t callData)
1766 window = WidgetToWindow(MENU_WIDGET(w));
1768 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1769 ((XmAnyCallbackStruct *)callData)->event);
1770 TabsPrefDialog(window->shell, window);
1773 static void statsCB(Widget w, WindowInfo *window, caddr_t callData)
1775 Widget menu = MENU_WIDGET(w);
1777 window = WidgetToWindow(menu);
1779 #ifdef SGI_CUSTOM
1780 if (shortPrefAskDefault(window->shell, w, "Statistics Line")) {
1781 statsLineDefCB(w, window, callData);
1782 SaveNEditPrefs(window->shell, GetPrefShortMenus());
1784 #endif
1785 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1786 ((XmAnyCallbackStruct *)callData)->event);
1787 XtCallActionProc(WidgetToWindow(menu)->lastFocus, "set_statistics_line",
1788 ((XmAnyCallbackStruct *)callData)->event, NULL, 0);
1791 static void autoIndentOffDefCB(Widget w, WindowInfo *window, caddr_t callData)
1793 WindowInfo *win;
1795 /* Set the preference and make the other windows' menus agree */
1796 SetPrefAutoIndent(NO_AUTO_INDENT);
1797 for (win=WindowList; win!=NULL; win=win->next) {
1798 if (!IsTopDocument(win))
1799 continue;
1800 XmToggleButtonSetState(win->autoIndentOffDefItem, True, False);
1801 XmToggleButtonSetState(win->autoIndentDefItem, False, False);
1802 XmToggleButtonSetState(win->smartIndentDefItem, False, False);
1806 static void autoIndentDefCB(Widget w, WindowInfo *window, caddr_t callData)
1808 WindowInfo *win;
1810 /* Set the preference and make the other windows' menus agree */
1811 SetPrefAutoIndent(AUTO_INDENT);
1812 for (win=WindowList; win!=NULL; win=win->next) {
1813 if (!IsTopDocument(win))
1814 continue;
1815 XmToggleButtonSetState(win->autoIndentDefItem, True, False);
1816 XmToggleButtonSetState(win->autoIndentOffDefItem, False, False);
1817 XmToggleButtonSetState(win->smartIndentDefItem, False, False);
1821 static void smartIndentDefCB(Widget w, WindowInfo *window, caddr_t callData)
1823 WindowInfo *win;
1825 /* Set the preference and make the other windows' menus agree */
1826 SetPrefAutoIndent(SMART_INDENT);
1827 for (win=WindowList; win!=NULL; win=win->next) {
1828 if (!IsTopDocument(win))
1829 continue;
1830 XmToggleButtonSetState(win->smartIndentDefItem, True, False);
1831 XmToggleButtonSetState(win->autoIndentOffDefItem, False, False);
1832 XmToggleButtonSetState(win->autoIndentDefItem, False, False);
1836 static void autoSaveDefCB(Widget w, WindowInfo *window, caddr_t callData)
1838 WindowInfo *win;
1839 int state = XmToggleButtonGetState(w);
1841 /* Set the preference and make the other windows' menus agree */
1842 SetPrefAutoSave(state);
1843 for (win=WindowList; win!=NULL; win=win->next) {
1844 if (IsTopDocument(win))
1845 XmToggleButtonSetState(win->autoSaveDefItem, state, False);
1849 static void preserveDefCB(Widget w, WindowInfo *window, caddr_t callData)
1851 WindowInfo *win;
1852 int state = XmToggleButtonGetState(w);
1854 /* Set the preference and make the other windows' menus agree */
1855 SetPrefSaveOldVersion(state);
1856 for (win=WindowList; win!=NULL; win=win->next) {
1857 if (IsTopDocument(win))
1858 XmToggleButtonSetState(win->saveLastDefItem, state, False);
1862 static void fontDefCB(Widget w, WindowInfo *window, caddr_t callData)
1864 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1865 ((XmAnyCallbackStruct *)callData)->event);
1866 ChooseFonts(WidgetToWindow(MENU_WIDGET(w)), False);
1869 static void colorDefCB(Widget w, WindowInfo *window, caddr_t callData)
1871 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1872 ((XmAnyCallbackStruct *)callData)->event);
1873 ChooseColors(WidgetToWindow(MENU_WIDGET(w)));
1876 static void noWrapDefCB(Widget w, WindowInfo *window, caddr_t callData)
1878 WindowInfo *win;
1880 /* Set the preference and make the other windows' menus agree */
1881 SetPrefWrap(NO_WRAP);
1882 for (win=WindowList; win!=NULL; win=win->next) {
1883 if (!IsTopDocument(win))
1884 continue;
1885 XmToggleButtonSetState(win->noWrapDefItem, True, False);
1886 XmToggleButtonSetState(win->newlineWrapDefItem, False, False);
1887 XmToggleButtonSetState(win->contWrapDefItem, False, False);
1891 static void newlineWrapDefCB(Widget w, WindowInfo *window, caddr_t callData)
1893 WindowInfo *win;
1895 /* Set the preference and make the other windows' menus agree */
1896 SetPrefWrap(NEWLINE_WRAP);
1897 for (win=WindowList; win!=NULL; win=win->next) {
1898 if (!IsTopDocument(win))
1899 continue;
1900 XmToggleButtonSetState(win->newlineWrapDefItem, True, False);
1901 XmToggleButtonSetState(win->contWrapDefItem, False, False);
1902 XmToggleButtonSetState(win->noWrapDefItem, False, False);
1906 static void contWrapDefCB(Widget w, WindowInfo *window, caddr_t callData)
1908 WindowInfo *win;
1910 /* Set the preference and make the other windows' menus agree */
1911 SetPrefWrap(CONTINUOUS_WRAP);
1912 for (win=WindowList; win!=NULL; win=win->next) {
1913 if (!IsTopDocument(win))
1914 continue;
1915 XmToggleButtonSetState(win->contWrapDefItem, True, False);
1916 XmToggleButtonSetState(win->newlineWrapDefItem, False, False);
1917 XmToggleButtonSetState(win->noWrapDefItem, False, False);
1921 static void wrapMarginDefCB(Widget w, WindowInfo *window, caddr_t callData)
1923 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1924 ((XmAnyCallbackStruct *)callData)->event);
1925 WrapMarginDialog(WidgetToWindow(MENU_WIDGET(w))->shell, NULL);
1928 static void smartTagsDefCB(Widget w, XtPointer client_data, XtPointer callData)
1930 WindowInfo *win;
1932 SetPrefSmartTags(True);
1933 for (win=WindowList; win!=NULL; win=win->next) {
1934 if (!IsTopDocument(win))
1935 continue;
1936 XmToggleButtonSetState(win->smartTagsDefItem, True, False);
1937 XmToggleButtonSetState(win->allTagsDefItem, False, False);
1941 static void showAllTagsDefCB(Widget w, XtPointer client_data, XtPointer callData)
1943 WindowInfo *win;
1945 SetPrefSmartTags(False);
1946 for (win=WindowList; win!=NULL; win=win->next) {
1947 if (!IsTopDocument(win))
1948 continue;
1949 XmToggleButtonSetState(win->smartTagsDefItem, False, False);
1950 XmToggleButtonSetState(win->allTagsDefItem, True, False);
1954 static void shellSelDefCB(Widget widget, WindowInfo* window, caddr_t callData)
1956 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(widget))->lastFocus,
1957 ((XmAnyCallbackStruct*) callData)->event);
1958 SelectShellDialog(WidgetToWindow(MENU_WIDGET(widget))->shell, NULL);
1961 static void tabsDefCB(Widget w, WindowInfo *window, caddr_t callData)
1963 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
1964 ((XmAnyCallbackStruct *)callData)->event);
1965 TabsPrefDialog(WidgetToWindow(MENU_WIDGET(w))->shell, NULL);
1968 static void showMatchingOffDefCB(Widget w, WindowInfo *window, caddr_t callData)
1970 WindowInfo *win;
1972 /* Set the preference and make the other windows' menus agree */
1973 SetPrefShowMatching(NO_FLASH);
1974 for (win=WindowList; win!=NULL; win=win->next) {
1975 if (!IsTopDocument(win))
1976 continue;
1977 XmToggleButtonSetState(win->showMatchingOffDefItem, True, False);
1978 XmToggleButtonSetState(win->showMatchingDelimitDefItem, False, False);
1979 XmToggleButtonSetState(win->showMatchingRangeDefItem, False, False);
1983 static void showMatchingDelimitDefCB(Widget w, WindowInfo *window, caddr_t callData)
1985 WindowInfo *win;
1987 /* Set the preference and make the other windows' menus agree */
1988 SetPrefShowMatching(FLASH_DELIMIT);
1989 for (win=WindowList; win!=NULL; win=win->next) {
1990 if (!IsTopDocument(win))
1991 continue;
1992 XmToggleButtonSetState(win->showMatchingOffDefItem, False, False);
1993 XmToggleButtonSetState(win->showMatchingDelimitDefItem, True, False);
1994 XmToggleButtonSetState(win->showMatchingRangeDefItem, False, False);
1998 static void showMatchingRangeDefCB(Widget w, WindowInfo *window, caddr_t callData)
2000 WindowInfo *win;
2002 /* Set the preference and make the other windows' menus agree */
2003 SetPrefShowMatching(FLASH_RANGE);
2004 for (win=WindowList; win!=NULL; win=win->next) {
2005 if (!IsTopDocument(win))
2006 continue;
2007 XmToggleButtonSetState(win->showMatchingOffDefItem, False, False);
2008 XmToggleButtonSetState(win->showMatchingDelimitDefItem, False, False);
2009 XmToggleButtonSetState(win->showMatchingRangeDefItem, True, False);
2013 static void matchSyntaxBasedDefCB(Widget w, WindowInfo *window, caddr_t callData)
2015 WindowInfo *win;
2017 int state = XmToggleButtonGetState(w);
2019 /* Set the preference and make the other windows' menus agree */
2020 SetPrefMatchSyntaxBased(state);
2021 for (win=WindowList; win!=NULL; win=win->next) {
2022 if (IsTopDocument(win))
2023 XmToggleButtonSetState(win->matchSyntaxBasedDefItem, state, False);
2027 static void backlightCharsDefCB(Widget w, WindowInfo *window, caddr_t callData)
2029 WindowInfo *win;
2030 int state = XmToggleButtonGetState(w);
2032 /* Set the preference and make the other windows' menus agree */
2033 SetPrefBacklightChars(state);
2034 for (win=WindowList; win!=NULL; win=win->next) {
2035 if (IsTopDocument(win))
2036 XmToggleButtonSetState(win->backlightCharsDefItem, state, False);
2040 static void highlightOffDefCB(Widget w, WindowInfo *window, caddr_t callData)
2042 WindowInfo *win;
2044 /* Set the preference and make the other windows' menus agree */
2045 SetPrefHighlightSyntax(False);
2046 for (win=WindowList; win!=NULL; win=win->next) {
2047 if (!IsTopDocument(win))
2048 continue;
2049 XmToggleButtonSetState(win->highlightOffDefItem, True, False);
2050 XmToggleButtonSetState(win->highlightDefItem, False, False);
2054 static void highlightDefCB(Widget w, WindowInfo *window, caddr_t callData)
2056 WindowInfo *win;
2058 /* Set the preference and make the other windows' menus agree */
2059 SetPrefHighlightSyntax(True);
2060 for (win=WindowList; win!=NULL; win=win->next) {
2061 if (!IsTopDocument(win))
2062 continue;
2063 XmToggleButtonSetState(win->highlightOffDefItem, False, False);
2064 XmToggleButtonSetState(win->highlightDefItem, True, False);
2068 static void highlightingDefCB(Widget w, WindowInfo *window, caddr_t callData)
2070 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2071 ((XmAnyCallbackStruct *)callData)->event);
2072 EditHighlightPatterns(WidgetToWindow(MENU_WIDGET(w)));
2075 static void smartMacrosDefCB(Widget w, WindowInfo *window, caddr_t callData)
2077 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2078 ((XmAnyCallbackStruct *)callData)->event);
2079 EditSmartIndentMacros(WidgetToWindow(MENU_WIDGET(w)));
2082 static void stylesDefCB(Widget w, WindowInfo *window, caddr_t callData)
2084 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2085 ((XmAnyCallbackStruct *)callData)->event);
2086 EditHighlightStyles(NULL);
2089 static void languageDefCB(Widget w, WindowInfo *window, caddr_t callData)
2091 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2092 ((XmAnyCallbackStruct *)callData)->event);
2093 EditLanguageModes();
2096 #ifndef VMS
2097 static void shellDefCB(Widget w, WindowInfo *window, caddr_t callData)
2099 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2100 ((XmAnyCallbackStruct *)callData)->event);
2101 EditShellMenu(WidgetToWindow(MENU_WIDGET(w)));
2103 #endif /* VMS */
2105 static void macroDefCB(Widget w, WindowInfo *window, caddr_t callData)
2107 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2108 ((XmAnyCallbackStruct *)callData)->event);
2109 EditMacroMenu(WidgetToWindow(MENU_WIDGET(w)));
2112 static void bgMenuDefCB(Widget w, WindowInfo *window, caddr_t callData)
2114 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2115 ((XmAnyCallbackStruct *)callData)->event);
2116 EditBGMenu(WidgetToWindow(MENU_WIDGET(w)));
2119 static void customizeTitleDefCB(Widget w, WindowInfo *window, caddr_t callData)
2121 window = WidgetToWindow(MENU_WIDGET(w));
2123 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2124 ((XmAnyCallbackStruct *)callData)->event);
2125 EditCustomTitleFormat(window);
2128 static void searchDlogsDefCB(Widget w, WindowInfo *window, caddr_t callData)
2130 WindowInfo *win;
2131 int state = XmToggleButtonGetState(w);
2133 /* Set the preference and make the other windows' menus agree */
2134 SetPrefSearchDlogs(state);
2135 for (win=WindowList; win!=NULL; win=win->next) {
2136 if (IsTopDocument(win))
2137 XmToggleButtonSetState(win->searchDlogsDefItem, state, False);
2141 static void beepOnSearchWrapDefCB(Widget w, WindowInfo *window, caddr_t callData)
2143 WindowInfo *win;
2144 int state = XmToggleButtonGetState(w);
2146 /* Set the preference and make the other windows' menus agree */
2147 SetPrefBeepOnSearchWrap(state);
2148 for (win=WindowList; win!=NULL; win=win->next) {
2149 if (IsTopDocument(win))
2150 XmToggleButtonSetState(win->beepOnSearchWrapDefItem, state, False);
2154 static void keepSearchDlogsDefCB(Widget w, WindowInfo *window, caddr_t callData)
2156 WindowInfo *win;
2157 int state = XmToggleButtonGetState(w);
2159 /* Set the preference and make the other windows' menus agree */
2160 SetPrefKeepSearchDlogs(state);
2161 for (win=WindowList; win!=NULL; win=win->next) {
2162 if (IsTopDocument(win))
2163 XmToggleButtonSetState(win->keepSearchDlogsDefItem, state, False);
2167 static void searchWrapsDefCB(Widget w, WindowInfo *window, caddr_t callData)
2169 WindowInfo *win;
2170 int state = XmToggleButtonGetState(w);
2172 /* Set the preference and make the other windows' menus agree */
2173 SetPrefSearchWraps(state);
2174 for (win=WindowList; win!=NULL; win=win->next) {
2175 if (IsTopDocument(win))
2176 XmToggleButtonSetState(win->searchWrapsDefItem, state, False);
2180 static void appendLFCB(Widget w, WindowInfo* window, caddr_t callData)
2182 WindowInfo *win;
2183 int state = XmToggleButtonGetState(w);
2185 SetPrefAppendLF(state);
2186 for (win = WindowList; win != NULL; win = win->next) {
2187 if (IsTopDocument(win))
2188 XmToggleButtonSetState(win->appendLFItem, state, False);
2192 static void sortOpenPrevDefCB(Widget w, WindowInfo *window, caddr_t callData)
2194 WindowInfo *win;
2195 int state = XmToggleButtonGetState(w);
2197 /* Set the preference, make the other windows' menus agree,
2198 and invalidate their Open Previous menus */
2199 SetPrefSortOpenPrevMenu(state);
2200 for (win=WindowList; win!=NULL; win=win->next) {
2201 if (IsTopDocument(win))
2202 XmToggleButtonSetState(win->sortOpenPrevDefItem, state, False);
2206 static void reposDlogsDefCB(Widget w, WindowInfo *window, caddr_t callData)
2208 WindowInfo *win;
2209 int state = XmToggleButtonGetState(w);
2211 /* Set the preference and make the other windows' menus agree */
2212 SetPrefRepositionDialogs(state);
2213 SetPointerCenteredDialogs(state);
2214 for (win=WindowList; win!=NULL; win=win->next) {
2215 if (IsTopDocument(win))
2216 XmToggleButtonSetState(win->reposDlogsDefItem, state, False);
2220 static void autoScrollDefCB(Widget w, WindowInfo *window, caddr_t callData)
2222 WindowInfo *win;
2223 int state = XmToggleButtonGetState(w);
2225 /* Set the preference and make the other windows' menus agree */
2226 SetPrefAutoScroll(state);
2227 /* XXX: Should we ensure auto-scroll now if needed? */
2228 for (win=WindowList; win!=NULL; win=win->next) {
2229 if (IsTopDocument(win))
2230 XmToggleButtonSetState(win->autoScrollDefItem, state, False);
2234 static void modWarnDefCB(Widget w, WindowInfo *window, caddr_t callData)
2236 WindowInfo *win;
2237 int state = XmToggleButtonGetState(w);
2239 /* Set the preference and make the other windows' menus agree */
2240 SetPrefWarnFileMods(state);
2241 for (win=WindowList; win!=NULL; win=win->next) {
2242 if (!IsTopDocument(win))
2243 continue;
2244 XmToggleButtonSetState(win->modWarnDefItem, state, False);
2245 XtSetSensitive(win->modWarnRealDefItem, state);
2249 static void modWarnRealDefCB(Widget w, WindowInfo *window, caddr_t callData)
2251 WindowInfo *win;
2252 int state = XmToggleButtonGetState(w);
2254 /* Set the preference and make the other windows' menus agree */
2255 SetPrefWarnRealFileMods(state);
2256 for (win=WindowList; win!=NULL; win=win->next) {
2257 if (IsTopDocument(win))
2258 XmToggleButtonSetState(win->modWarnRealDefItem, state, False);
2262 static void exitWarnDefCB(Widget w, WindowInfo *window, caddr_t callData)
2264 WindowInfo *win;
2265 int state = XmToggleButtonGetState(w);
2267 /* Set the preference and make the other windows' menus agree */
2268 SetPrefWarnExit(state);
2269 for (win=WindowList; win!=NULL; win=win->next) {
2270 if (IsTopDocument(win))
2271 XmToggleButtonSetState(win->exitWarnDefItem, state, False);
2275 static void openInTabDefCB(Widget w, WindowInfo *window, caddr_t callData)
2277 WindowInfo *win;
2278 int state = XmToggleButtonGetState(w);
2280 /* Set the preference and make the other windows' menus agree */
2281 SetPrefOpenInTab(state);
2282 for (win=WindowList; win!=NULL; win=win->next)
2283 XmToggleButtonSetState(win->openInTabDefItem, state, False);
2286 static void tabBarDefCB(Widget w, WindowInfo *window, caddr_t callData)
2288 WindowInfo *win;
2289 int state = XmToggleButtonGetState(w);
2291 /* Set the preference and make the other windows' menus agree */
2292 SetPrefTabBar(state);
2293 for (win=WindowList; win!=NULL; win=win->next) {
2294 if (!IsTopDocument(win))
2295 continue;
2296 XmToggleButtonSetState(win->tabBarDefItem, state, False);
2297 ShowWindowTabBar(win);
2301 static void tabBarHideDefCB(Widget w, WindowInfo *window, caddr_t callData)
2303 WindowInfo *win;
2304 int state = XmToggleButtonGetState(w);
2306 /* Set the preference and make the other windows' menus agree */
2307 SetPrefTabBarHideOne(state);
2308 for (win=WindowList; win!=NULL; win=win->next) {
2309 if (!IsTopDocument(win))
2310 continue;
2311 XmToggleButtonSetState(win->tabBarHideDefItem, state, False);
2312 ShowWindowTabBar(win);
2316 static void toolTipsDefCB(Widget w, WindowInfo *window, caddr_t callData)
2318 WindowInfo *win;
2319 int state = XmToggleButtonGetState(w);
2321 /* Set the preference and make the other windows' menus agree */
2322 SetPrefToolTips(state);
2323 for (win=WindowList; win!=NULL; win=win->next) {
2324 XtVaSetValues(win->tab, XltNshowBubble, GetPrefToolTips(), NULL);
2325 if (IsTopDocument(win))
2326 XmToggleButtonSetState(win->toolTipsDefItem, state, False);
2330 static void tabNavigateDefCB(Widget w, WindowInfo *window, caddr_t callData)
2332 WindowInfo *win;
2333 int state = XmToggleButtonGetState(w);
2335 /* Set the preference and make the other windows' menus agree */
2336 SetPrefGlobalTabNavigate(state);
2337 for (win=WindowList; win!=NULL; win=win->next) {
2338 if (IsTopDocument(win))
2339 XmToggleButtonSetState(win->tabNavigateDefItem, state, False);
2343 static void tabSortDefCB(Widget w, WindowInfo *window, caddr_t callData)
2345 WindowInfo *win;
2346 int state = XmToggleButtonGetState(w);
2348 /* Set the preference and make the other windows' menus agree */
2349 SetPrefSortTabs(state);
2350 for (win=WindowList; win!=NULL; win=win->next) {
2351 if (IsTopDocument(win))
2352 XmToggleButtonSetState(win->tabSortDefItem, state, False);
2355 /* If we just enabled sorting, sort all tabs. Note that this reorders
2356 the next pointers underneath us, which is scary, but SortTabBar never
2357 touches windows that are earlier in the WindowList so it's ok. */
2358 if (state) {
2359 Widget shell=(Widget)0;
2360 for (win=WindowList; win!=NULL; win=win->next) {
2361 if ( win->shell != shell ) {
2362 SortTabBar(win);
2363 shell = win->shell;
2369 static void statsLineDefCB(Widget w, WindowInfo *window, caddr_t callData)
2371 WindowInfo *win;
2372 int state = XmToggleButtonGetState(w);
2374 /* Set the preference and make the other windows' menus agree */
2375 SetPrefStatsLine(state);
2376 for (win=WindowList; win!=NULL; win=win->next) {
2377 if (IsTopDocument(win))
2378 XmToggleButtonSetState(win->statsLineDefItem, state, False);
2382 static void iSearchLineDefCB(Widget w, WindowInfo *window, caddr_t callData)
2384 WindowInfo *win;
2385 int state = XmToggleButtonGetState(w);
2387 /* Set the preference and make the other windows' menus agree */
2388 SetPrefISearchLine(state);
2389 for (win=WindowList; win!=NULL; win=win->next) {
2390 if (IsTopDocument(win))
2391 XmToggleButtonSetState(win->iSearchLineDefItem, state, False);
2395 static void lineNumsDefCB(Widget w, WindowInfo *window, caddr_t callData)
2397 WindowInfo *win;
2398 int state = XmToggleButtonGetState(w);
2400 /* Set the preference and make the other windows' menus agree */
2401 SetPrefLineNums(state);
2402 for (win=WindowList; win!=NULL; win=win->next) {
2403 if (IsTopDocument(win))
2404 XmToggleButtonSetState(win->lineNumsDefItem, state, False);
2408 static void pathInWindowsMenuDefCB(Widget w, WindowInfo *window, caddr_t callData)
2410 WindowInfo *win;
2411 int state = XmToggleButtonGetState(w);
2413 /* Set the preference and make the other windows' menus agree */
2414 SetPrefShowPathInWindowsMenu(state);
2415 for (win=WindowList; win!=NULL; win=win->next) {
2416 if (IsTopDocument(win))
2417 XmToggleButtonSetState(win->pathInWindowsMenuDefItem, state, False);
2419 InvalidateWindowMenus();
2422 static void searchLiteralCB(Widget w, WindowInfo *window, caddr_t callData)
2424 WindowInfo *win;
2426 /* Set the preference and make the other windows' menus agree */
2427 if (XmToggleButtonGetState(w)) {
2428 SetPrefSearch(SEARCH_LITERAL);
2429 for (win=WindowList; win!=NULL; win=win->next){
2430 if (!IsTopDocument(win))
2431 continue;
2432 XmToggleButtonSetState(win->searchLiteralDefItem, True, False);
2433 XmToggleButtonSetState(win->searchCaseSenseDefItem, False, False);
2434 XmToggleButtonSetState(win->searchLiteralWordDefItem, False, False);
2435 XmToggleButtonSetState(win->searchCaseSenseWordDefItem, False, False);
2436 XmToggleButtonSetState(win->searchRegexDefItem, False, False);
2437 XmToggleButtonSetState(win->searchRegexNoCaseDefItem, False, False);
2442 static void searchCaseSenseCB(Widget w, WindowInfo *window, caddr_t callData)
2444 WindowInfo *win;
2446 /* Set the preference and make the other windows' menus agree */
2447 if (XmToggleButtonGetState(w)) {
2448 SetPrefSearch(SEARCH_CASE_SENSE);
2449 for (win=WindowList; win!=NULL; win=win->next) {
2450 if (!IsTopDocument(win))
2451 continue;
2452 XmToggleButtonSetState(win->searchLiteralDefItem, False, False);
2453 XmToggleButtonSetState(win->searchCaseSenseDefItem, True, False);
2454 XmToggleButtonSetState(win->searchLiteralWordDefItem, False, False);
2455 XmToggleButtonSetState(win->searchCaseSenseWordDefItem, False, False);
2456 XmToggleButtonSetState(win->searchRegexDefItem, False, False);
2457 XmToggleButtonSetState(win->searchRegexNoCaseDefItem, False, False);
2462 static void searchLiteralWordCB(Widget w, WindowInfo *window, caddr_t callData)
2464 WindowInfo *win;
2466 /* Set the preference and make the other windows' menus agree */
2467 if (XmToggleButtonGetState(w)) {
2468 SetPrefSearch(SEARCH_LITERAL_WORD);
2469 for (win=WindowList; win!=NULL; win=win->next){
2470 if (!IsTopDocument(win))
2471 continue;
2472 XmToggleButtonSetState(win->searchLiteralDefItem, False, False);
2473 XmToggleButtonSetState(win->searchCaseSenseDefItem, False, False);
2474 XmToggleButtonSetState(win->searchLiteralWordDefItem, True, False);
2475 XmToggleButtonSetState(win->searchCaseSenseWordDefItem, False, False);
2476 XmToggleButtonSetState(win->searchRegexDefItem, False, False);
2477 XmToggleButtonSetState(win->searchRegexNoCaseDefItem, False, False);
2482 static void searchCaseSenseWordCB(Widget w, WindowInfo *window, caddr_t callData)
2484 WindowInfo *win;
2486 /* Set the preference and make the other windows' menus agree */
2487 if (XmToggleButtonGetState(w)) {
2488 SetPrefSearch(SEARCH_CASE_SENSE_WORD);
2489 for (win=WindowList; win!=NULL; win=win->next) {
2490 if (!IsTopDocument(win))
2491 continue;
2492 XmToggleButtonSetState(win->searchLiteralDefItem, False, False);
2493 XmToggleButtonSetState(win->searchCaseSenseDefItem, False, False);
2494 XmToggleButtonSetState(win->searchLiteralWordDefItem, False, False);
2495 XmToggleButtonSetState(win->searchCaseSenseWordDefItem, True, False);
2496 XmToggleButtonSetState(win->searchRegexDefItem, False, False);
2497 XmToggleButtonSetState(win->searchRegexNoCaseDefItem, False, False);
2502 static void searchRegexCB(Widget w, WindowInfo *window, caddr_t callData)
2504 WindowInfo *win;
2506 /* Set the preference and make the other windows' menus agree */
2507 if (XmToggleButtonGetState(w)) {
2508 SetPrefSearch(SEARCH_REGEX);
2509 for (win=WindowList; win!=NULL; win=win->next){
2510 if (!IsTopDocument(win))
2511 continue;
2512 XmToggleButtonSetState(win->searchLiteralDefItem, False, False);
2513 XmToggleButtonSetState(win->searchCaseSenseDefItem, False, False);
2514 XmToggleButtonSetState(win->searchLiteralWordDefItem, False, False);
2515 XmToggleButtonSetState(win->searchCaseSenseWordDefItem, False, False);
2516 XmToggleButtonSetState(win->searchRegexDefItem, True, False);
2517 XmToggleButtonSetState(win->searchRegexNoCaseDefItem, False, False);
2522 static void searchRegexNoCaseCB(Widget w, WindowInfo *window, caddr_t callData)
2524 WindowInfo *win;
2526 /* Set the preference and make the other windows' menus agree */
2527 if (XmToggleButtonGetState(w)) {
2528 SetPrefSearch(SEARCH_REGEX_NOCASE);
2529 for (win=WindowList; win!=NULL; win=win->next){
2530 if (!IsTopDocument(win))
2531 continue;
2532 XmToggleButtonSetState(win->searchLiteralDefItem, False, False);
2533 XmToggleButtonSetState(win->searchCaseSenseDefItem, False, False);
2534 XmToggleButtonSetState(win->searchLiteralWordDefItem, False, False);
2535 XmToggleButtonSetState(win->searchCaseSenseWordDefItem, False, False);
2536 XmToggleButtonSetState(win->searchRegexDefItem, False, False);
2537 XmToggleButtonSetState(win->searchRegexNoCaseDefItem, True, False);
2542 #ifdef REPLACE_SCOPE
2543 static void replaceScopeWindowCB(Widget w, WindowInfo *window, caddr_t callData)
2545 WindowInfo *win;
2547 /* Set the preference and make the other windows' menus agree */
2548 if (XmToggleButtonGetState(w)) {
2549 SetPrefReplaceDefScope(REPL_DEF_SCOPE_WINDOW);
2550 for (win=WindowList; win!=NULL; win=win->next){
2551 if (!IsTopDocument(win))
2552 continue;
2553 XmToggleButtonSetState(win->replScopeWinDefItem, True, False);
2554 XmToggleButtonSetState(win->replScopeSelDefItem, False, False);
2555 XmToggleButtonSetState(win->replScopeSmartDefItem, False, False);
2560 static void replaceScopeSelectionCB(Widget w, WindowInfo *window, caddr_t callData)
2562 WindowInfo *win;
2564 /* Set the preference and make the other windows' menus agree */
2565 if (XmToggleButtonGetState(w)) {
2566 SetPrefReplaceDefScope(REPL_DEF_SCOPE_SELECTION);
2567 for (win=WindowList; win!=NULL; win=win->next){
2568 if (!IsTopDocument(win))
2569 continue;
2570 XmToggleButtonSetState(win->replScopeWinDefItem, False, False);
2571 XmToggleButtonSetState(win->replScopeSelDefItem, True, False);
2572 XmToggleButtonSetState(win->replScopeSmartDefItem, False, False);
2577 static void replaceScopeSmartCB(Widget w, WindowInfo *window, caddr_t callData)
2579 WindowInfo *win;
2581 /* Set the preference and make the other windows' menus agree */
2582 if (XmToggleButtonGetState(w)) {
2583 SetPrefReplaceDefScope(REPL_DEF_SCOPE_SMART);
2584 for (win=WindowList; win!=NULL; win=win->next){
2585 if (!IsTopDocument(win))
2586 continue;
2587 XmToggleButtonSetState(win->replScopeWinDefItem, False, False);
2588 XmToggleButtonSetState(win->replScopeSelDefItem, False, False);
2589 XmToggleButtonSetState(win->replScopeSmartDefItem, True, False);
2593 #endif
2595 static void size24x80CB(Widget w, WindowInfo *window, caddr_t callData)
2597 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2598 ((XmAnyCallbackStruct *)callData)->event);
2599 setWindowSizeDefault(24, 80);
2602 static void size40x80CB(Widget w, WindowInfo *window, caddr_t callData)
2604 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2605 ((XmAnyCallbackStruct *)callData)->event);
2606 setWindowSizeDefault(40, 80);
2609 static void size60x80CB(Widget w, WindowInfo *window, caddr_t callData)
2611 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2612 ((XmAnyCallbackStruct *)callData)->event);
2613 setWindowSizeDefault(60, 80);
2616 static void size80x80CB(Widget w, WindowInfo *window, caddr_t callData)
2618 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2619 ((XmAnyCallbackStruct *)callData)->event);
2620 setWindowSizeDefault(80, 80);
2623 static void sizeCustomCB(Widget w, WindowInfo *window, caddr_t callData)
2625 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2626 ((XmAnyCallbackStruct *)callData)->event);
2627 RowColumnPrefDialog(WidgetToWindow(MENU_WIDGET(w))->shell);
2628 updateWindowSizeMenus();
2631 static void savePrefCB(Widget w, WindowInfo *window, caddr_t callData)
2633 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2634 ((XmAnyCallbackStruct *)callData)->event);
2635 SaveNEditPrefs(WidgetToWindow(MENU_WIDGET(w))->shell, False);
2638 static void formFeedCB(Widget w, XtPointer clientData, XtPointer callData)
2640 static char *params[1] = {"\f"};
2642 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2643 ((XmAnyCallbackStruct *)callData)->event);
2644 XtCallActionProc(WidgetToWindow(MENU_WIDGET(w))->lastFocus, "insert_string",
2645 ((XmAnyCallbackStruct *)callData)->event, params, 1);
2648 static void cancelShellCB(Widget w, WindowInfo *window, XtPointer callData)
2650 #ifndef VMS
2651 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2652 ((XmAnyCallbackStruct *)callData)->event);
2653 AbortShellCommand(WidgetToWindow(MENU_WIDGET(w)));
2654 #endif
2657 static void learnCB(Widget w, WindowInfo *window, caddr_t callData)
2659 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2660 ((XmAnyCallbackStruct *)callData)->event);
2661 BeginLearn(WidgetToWindow(MENU_WIDGET(w)));
2664 static void finishLearnCB(Widget w, WindowInfo *window, caddr_t callData)
2666 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2667 ((XmAnyCallbackStruct *)callData)->event);
2668 FinishLearn();
2671 static void cancelLearnCB(Widget w, WindowInfo *window, caddr_t callData)
2673 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2674 ((XmAnyCallbackStruct *)callData)->event);
2675 CancelMacroOrLearn(WidgetToWindow(MENU_WIDGET(w)));
2678 static void replayCB(Widget w, WindowInfo *window, caddr_t callData)
2680 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
2681 ((XmAnyCallbackStruct *)callData)->event);
2682 Replay(WidgetToWindow(MENU_WIDGET(w)));
2685 static void windowMenuCB(Widget w, WindowInfo *window, caddr_t callData)
2687 window = WidgetToWindow(MENU_WIDGET(w));
2689 if (!window->windowMenuValid) {
2690 updateWindowMenu(window);
2691 window->windowMenuValid = True;
2695 static void prevOpenMenuCB(Widget w, WindowInfo *window, caddr_t callData)
2697 window = WidgetToWindow(MENU_WIDGET(w));
2699 updatePrevOpenMenu(window);
2702 static void unloadTagsFileMenuCB(Widget w, WindowInfo *window, caddr_t callData)
2704 updateTagsFileMenu(WidgetToWindow(MENU_WIDGET(w)));
2707 static void unloadTipsFileMenuCB(Widget w, WindowInfo *window, caddr_t callData)
2709 updateTipsFileMenu(WidgetToWindow(MENU_WIDGET(w)));
2713 ** open a new tab or window.
2715 static void newAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
2717 WindowInfo *window = WidgetToWindow(w);
2718 int openInTab = GetPrefOpenInTab();
2720 if (*nArgs > 0) {
2721 if (strcmp(args[0], "prefs") == 0) {
2722 /* accept default */;
2724 else if (strcmp(args[0], "tab") == 0) {
2725 openInTab = 1;
2727 else if (strcmp(args[0], "window") == 0) {
2728 openInTab = 0;
2730 else if (strcmp(args[0], "opposite") == 0) {
2731 openInTab = !openInTab;
2733 else {
2734 fprintf(stderr, "nedit: Unknown argument to action procedure \"new\": %s\n", args[0]);
2738 EditNewFile(openInTab? window : NULL, NULL, False, NULL, window->path);
2739 CheckCloseDim();
2743 ** These are just here because our techniques make it hard to bind a menu item
2744 ** to an action procedure that takes arguments. The user doesn't need to know
2745 ** about them -- they can use new( "opposite" ) or new( "tab" ).
2747 static void newOppositeAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
2749 WindowInfo *window = WidgetToWindow(w);
2751 EditNewFile(GetPrefOpenInTab()? NULL : window, NULL, False, NULL,
2752 window->path);
2753 CheckCloseDim();
2755 static void newTabAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
2757 WindowInfo *window = WidgetToWindow(w);
2759 EditNewFile(window, NULL, False, NULL, window->path);
2760 CheckCloseDim();
2763 static void openDialogAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
2765 WindowInfo *window = WidgetToWindow(w);
2766 char fullname[MAXPATHLEN], *params[2];
2767 int response;
2768 int n=1;
2770 response = PromptForExistingFile(window, "Open File", fullname);
2771 if (response != GFN_OK)
2772 return;
2773 params[0] = fullname;
2775 if (*nArgs>0 && !strcmp(args[0], "1"))
2776 params[n++] = "1";
2778 XtCallActionProc(window->lastFocus, "open", event, params, n);
2779 CheckCloseDim();
2782 static void openAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
2784 WindowInfo *window = WidgetToWindow(w);
2785 char filename[MAXPATHLEN], pathname[MAXPATHLEN];
2787 if (*nArgs == 0) {
2788 fprintf(stderr, "nedit: open action requires file argument\n");
2789 return;
2791 if (0 != ParseFilename(args[0], filename, pathname)
2792 || strlen(filename) + strlen(pathname) > MAXPATHLEN - 1) {
2793 fprintf(stderr, "nedit: invalid file name for open action: %s\n",
2794 args[0]);
2795 return;
2797 EditExistingFile(window, filename, pathname, 0, NULL, False,
2798 NULL, GetPrefOpenInTab(), False);
2799 CheckCloseDim();
2802 static void openSelectedAP(Widget w, XEvent *event, String *args,
2803 Cardinal *nArgs)
2805 OpenSelectedFile(WidgetToWindow(w), event->xbutton.time);
2806 CheckCloseDim();
2809 static void closeAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
2811 int preResponse = PROMPT_SBC_DIALOG_RESPONSE;
2813 if (*nArgs > 0) {
2814 if (strcmp(args[0], "prompt") == 0) {
2815 preResponse = PROMPT_SBC_DIALOG_RESPONSE;
2817 else if (strcmp(args[0], "save") == 0) {
2818 preResponse = YES_SBC_DIALOG_RESPONSE;
2820 else if (strcmp(args[0], "nosave") == 0) {
2821 preResponse = NO_SBC_DIALOG_RESPONSE;
2824 CloseFileAndWindow(WidgetToWindow(w), preResponse);
2825 CheckCloseDim();
2828 static void saveAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
2830 WindowInfo *window = WidgetToWindow(w);
2832 if (CheckReadOnly(window))
2833 return;
2834 SaveWindow(window);
2837 static void saveAsDialogAP(Widget w, XEvent *event, String *args,
2838 Cardinal *nArgs)
2840 WindowInfo *window = WidgetToWindow(w);
2841 int response, addWrap, fileFormat;
2842 char fullname[MAXPATHLEN], *params[2];
2844 response = PromptForNewFile(window, "Save File As", fullname,
2845 &fileFormat, &addWrap);
2846 if (response != GFN_OK)
2847 return;
2848 window->fileFormat = fileFormat;
2849 params[0] = fullname;
2850 params[1] = "wrapped";
2851 XtCallActionProc(window->lastFocus, "save_as", event, params, addWrap?2:1);
2854 static void saveAsAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
2856 if (*nArgs == 0) {
2857 fprintf(stderr, "nedit: save_as action requires file argument\n");
2858 return;
2860 SaveWindowAs(WidgetToWindow(w), args[0],
2861 *nArgs == 2 && !strCaseCmp(args[1], "wrapped"));
2864 static void revertDialogAP(Widget w, XEvent *event, String *args,
2865 Cardinal *nArgs)
2867 WindowInfo *window = WidgetToWindow(w);
2868 int b;
2870 /* re-reading file is irreversible, prompt the user first */
2871 if (window->fileChanged)
2873 b = DialogF(DF_QUES, window->shell, 2, "Discard Changes",
2874 "Discard changes to\n%s%s?", "OK", "Cancel", window->path,
2875 window->filename);
2876 } else
2878 b = DialogF(DF_QUES, window->shell, 2, "Reload File",
2879 "Re-load file\n%s%s?", "Re-read", "Cancel", window->path,
2880 window->filename);
2883 if (b != 1)
2885 return;
2887 XtCallActionProc(window->lastFocus, "revert_to_saved", event, NULL, 0);
2891 static void revertAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
2893 RevertToSaved(WidgetToWindow(w));
2896 static void includeDialogAP(Widget w, XEvent *event, String *args,
2897 Cardinal *nArgs)
2899 WindowInfo *window = WidgetToWindow(w);
2900 char filename[MAXPATHLEN], *params[1];
2901 int response;
2903 if (CheckReadOnly(window))
2904 return;
2905 response = PromptForExistingFile(window, "Include File", filename);
2906 if (response != GFN_OK)
2907 return;
2908 params[0] = filename;
2909 XtCallActionProc(window->lastFocus, "include_file", event, params, 1);
2912 static void includeAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
2914 WindowInfo *window = WidgetToWindow(w);
2916 if (CheckReadOnly(window))
2917 return;
2918 if (*nArgs == 0) {
2919 fprintf(stderr, "nedit: include action requires file argument\n");
2920 return;
2922 IncludeFile(WidgetToWindow(w), args[0]);
2925 static void loadMacroDialogAP(Widget w, XEvent *event, String *args,
2926 Cardinal *nArgs)
2928 WindowInfo *window = WidgetToWindow(w);
2929 char filename[MAXPATHLEN], *params[1];
2930 int response;
2932 response = PromptForExistingFile(window, "Load Macro File", filename);
2933 if (response != GFN_OK)
2934 return;
2935 params[0] = filename;
2936 XtCallActionProc(window->lastFocus, "load_macro_file", event, params, 1);
2939 static void loadMacroAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
2941 if (*nArgs == 0) {
2942 fprintf(stderr,"nedit: load_macro_file action requires file argument\n");
2943 return;
2945 ReadMacroFile(WidgetToWindow(w), args[0], True);
2948 static void loadTagsDialogAP(Widget w, XEvent *event, String *args,
2949 Cardinal *nArgs)
2951 WindowInfo *window = WidgetToWindow(w);
2952 char filename[MAXPATHLEN], *params[1];
2953 int response;
2955 response = PromptForExistingFile(window, "Load Tags File", filename);
2956 if (response != GFN_OK)
2957 return;
2958 params[0] = filename;
2959 XtCallActionProc(window->lastFocus, "load_tags_file", event, params, 1);
2962 static void loadTagsAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
2964 if (*nArgs == 0) {
2965 fprintf(stderr,"nedit: load_tags_file action requires file argument\n");
2966 return;
2969 if (!AddTagsFile(args[0], TAG))
2971 DialogF(DF_WARN, WidgetToWindow(w)->shell, 1, "Error Reading File",
2972 "Error reading ctags file:\n'%s'\ntags not loaded", "OK",
2973 args[0]);
2977 static void unloadTagsAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
2979 if (*nArgs == 0) {
2980 fprintf(stderr,
2981 "nedit: unload_tags_file action requires file argument\n");
2982 return;
2985 if (DeleteTagsFile(args[0], TAG, True)) {
2986 WindowInfo *win;
2988 /* refresh the "Unload Tags File" tear-offs after unloading, or
2989 close the tear-offs if all tags files have been unloaded */
2990 for (win=WindowList; win!=NULL; win=win->next) {
2991 if (IsTopDocument(win) &&
2992 !XmIsMenuShell(XtParent(win->unloadTagsMenuPane))) {
2993 if (XtIsSensitive(win->unloadTagsMenuItem))
2994 updateTagsFileMenu(win);
2995 else
2996 _XmDismissTearOff(XtParent(win->unloadTagsMenuPane),
2997 NULL, NULL);
3003 static void loadTipsDialogAP(Widget w, XEvent *event, String *args,
3004 Cardinal *nArgs)
3006 WindowInfo *window = WidgetToWindow(w);
3007 char filename[MAXPATHLEN], *params[1];
3008 int response;
3010 response = PromptForExistingFile(window, "Load Calltips File", filename);
3011 if (response != GFN_OK)
3012 return;
3013 params[0] = filename;
3014 XtCallActionProc(window->lastFocus, "load_tips_file", event, params, 1);
3017 static void loadTipsAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3019 if (*nArgs == 0) {
3020 fprintf(stderr,"nedit: load_tips_file action requires file argument\n");
3021 return;
3024 if (!AddTagsFile(args[0], TIP))
3026 DialogF(DF_WARN, WidgetToWindow(w)->shell, 1, "Error Reading File",
3027 "Error reading tips file:\n'%s'\ntips not loaded", "OK",
3028 args[0]);
3032 static void unloadTipsAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3034 if (*nArgs == 0) {
3035 fprintf(stderr,
3036 "nedit: unload_tips_file action requires file argument\n");
3037 return;
3039 /* refresh the "Unload Calltips File" tear-offs after unloading, or
3040 close the tear-offs if all tips files have been unloaded */
3041 if (DeleteTagsFile(args[0], TIP, True)) {
3042 WindowInfo *win;
3044 for (win=WindowList; win!=NULL; win=win->next) {
3045 if (IsTopDocument(win) &&
3046 !XmIsMenuShell(XtParent(win->unloadTipsMenuPane))) {
3047 if (XtIsSensitive(win->unloadTipsMenuItem))
3048 updateTipsFileMenu(win);
3049 else
3050 _XmDismissTearOff(XtParent(win->unloadTipsMenuPane),
3051 NULL, NULL);
3057 static void printAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3059 PrintWindow(WidgetToWindow(w), False);
3062 static void printSelAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3064 PrintWindow(WidgetToWindow(w), True);
3067 static void exitAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3069 WindowInfo *window = WidgetToWindow(w);
3071 if (!CheckPrefsChangesSaved(window->shell))
3072 return;
3074 /* If this is not the last window (more than one window is open),
3075 confirm with the user before exiting. */
3076 if (GetPrefWarnExit() && !(window == WindowList && window->next == NULL)) {
3077 int resp, titleLen, lineLen;
3078 char exitMsg[DF_MAX_MSG_LENGTH], *ptr, *title;
3079 char filename[MAXPATHLEN];
3080 WindowInfo *win;
3082 /* List the windows being edited and make sure the
3083 user really wants to exit */
3084 ptr = exitMsg;
3085 lineLen = 0;
3086 strcpy(ptr, "Editing: "); ptr += 9; lineLen += 9;
3087 for (win=WindowList; win!=NULL; win=win->next) {
3088 sprintf(filename, "%s%s", win->filename, win->fileChanged? "*": "");
3089 title = filename;
3090 titleLen = strlen(title);
3091 if (ptr - exitMsg + titleLen + 30 >= DF_MAX_MSG_LENGTH) {
3092 strcpy(ptr, "..."); ptr += 3;
3093 break;
3095 if (lineLen + titleLen + (win->next==NULL?5:2) > 50) {
3096 *ptr++ = '\n';
3097 lineLen = 0;
3099 if (win->next == NULL) {
3100 sprintf(ptr, "and %s.", title);
3101 ptr += 5 + titleLen;
3102 lineLen += 5 + titleLen;
3103 } else {
3104 sprintf(ptr, "%s, ", title);
3105 ptr += 2 + titleLen;
3106 lineLen += 2 + titleLen;
3109 sprintf(ptr, "\n\nExit NEdit?");
3110 resp = DialogF(DF_QUES, window->shell, 2, "Exit", "%s", "Exit",
3111 "Cancel", exitMsg);
3112 if (resp == 2)
3113 return;
3116 /* Close all files and exit when the last one is closed */
3117 if (CloseAllFilesAndWindows())
3118 exit(EXIT_SUCCESS);
3121 static void undoAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3123 WindowInfo *window = WidgetToWindow(w);
3125 if (CheckReadOnly(window))
3126 return;
3127 Undo(window);
3130 static void redoAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3132 WindowInfo *window = WidgetToWindow(w);
3134 if (CheckReadOnly(window))
3135 return;
3136 Redo(window);
3139 static void clearAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3141 WindowInfo *window = WidgetToWindow(w);
3143 if (CheckReadOnly(window))
3144 return;
3145 BufRemoveSelected(window->buffer);
3148 static void selAllAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3150 WindowInfo *window = WidgetToWindow(w);
3152 BufSelect(window->buffer, 0, window->buffer->length);
3155 static void shiftLeftAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3157 WindowInfo *window = WidgetToWindow(w);
3159 if (CheckReadOnly(window))
3160 return;
3161 ShiftSelection(window, SHIFT_LEFT, False);
3164 static void shiftLeftTabAP(Widget w, XEvent *event, String *args,
3165 Cardinal *nArgs)
3167 WindowInfo *window = WidgetToWindow(w);
3169 if (CheckReadOnly(window))
3170 return;
3171 ShiftSelection(window, SHIFT_LEFT, True);
3174 static void shiftRightAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3176 WindowInfo *window = WidgetToWindow(w);
3178 if (CheckReadOnly(window))
3179 return;
3180 ShiftSelection(window, SHIFT_RIGHT, False);
3183 static void shiftRightTabAP(Widget w, XEvent *event, String *args,
3184 Cardinal *nArgs)
3186 WindowInfo *window = WidgetToWindow(w);
3188 if (CheckReadOnly(window))
3189 return;
3190 ShiftSelection(window, SHIFT_RIGHT, True);
3193 static void findDialogAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3195 DoFindDlog(WidgetToWindow(w), searchDirection(0, args, nArgs),
3196 searchKeepDialogs(0, args, nArgs), searchType(0, args, nArgs),
3197 event->xbutton.time);
3200 static void findAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3202 if (*nArgs == 0) {
3203 fprintf(stderr, "nedit: find action requires search string argument\n");
3204 return;
3206 SearchAndSelect(WidgetToWindow(w), searchDirection(1, args, nArgs), args[0],
3207 searchType(1, args, nArgs), searchWrap(1, args, nArgs));
3210 static void findSameAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3212 SearchAndSelectSame(WidgetToWindow(w), searchDirection(0, args, nArgs),
3213 searchWrap(0, args, nArgs));
3216 static void findSelAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3218 SearchForSelected(WidgetToWindow(w), searchDirection(0, args, nArgs),
3219 searchType(0, args, nArgs), searchWrap(0, args, nArgs),
3220 event->xbutton.time);
3223 static void startIncrFindAP(Widget w, XEvent *event, String *args,
3224 Cardinal *nArgs)
3226 BeginISearch(WidgetToWindow(w), searchDirection(0, args, nArgs));
3229 static void findIncrAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3231 int i, continued = FALSE;
3232 if (*nArgs == 0) {
3233 fprintf(stderr, "nedit: find action requires search string argument\n");
3234 return;
3236 for (i=1; i<(int)*nArgs; i++)
3237 if (!strCaseCmp(args[i], "continued"))
3238 continued = TRUE;
3239 SearchAndSelectIncremental(WidgetToWindow(w),
3240 searchDirection(1, args, nArgs), args[0],
3241 searchType(1, args, nArgs), searchWrap(1, args, nArgs), continued);
3244 static void replaceDialogAP(Widget w, XEvent *event, String *args,
3245 Cardinal *nArgs)
3247 WindowInfo *window = WidgetToWindow(w);
3249 if (CheckReadOnly(window))
3250 return;
3251 DoFindReplaceDlog(window, searchDirection(0, args, nArgs),
3252 searchKeepDialogs(0, args, nArgs), searchType(0, args, nArgs),
3253 event->xbutton.time);
3256 static void replaceAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3258 WindowInfo *window = WidgetToWindow(w);
3260 if (CheckReadOnly(window))
3261 return;
3262 if (*nArgs < 2) {
3263 fprintf(stderr,
3264 "nedit: replace action requires search and replace string arguments\n");
3265 return;
3267 SearchAndReplace(window, searchDirection(2, args, nArgs),
3268 args[0], args[1], searchType(2, args, nArgs), searchWrap(2, args, nArgs));
3271 static void replaceAllAP(Widget w, XEvent *event, String *args,
3272 Cardinal *nArgs)
3274 WindowInfo *window = WidgetToWindow(w);
3276 if (CheckReadOnly(window))
3277 return;
3278 if (*nArgs < 2) {
3279 fprintf(stderr,
3280 "nedit: replace_all action requires search and replace string arguments\n");
3281 return;
3283 ReplaceAll(window, args[0], args[1], searchType(2, args, nArgs));
3286 static void replaceInSelAP(Widget w, XEvent *event, String *args,
3287 Cardinal *nArgs)
3289 WindowInfo *window = WidgetToWindow(w);
3291 if (CheckReadOnly(window))
3292 return;
3293 if (*nArgs < 2) {
3294 fprintf(stderr,
3295 "nedit: replace_in_selection requires search and replace string arguments\n");
3296 return;
3298 ReplaceInSelection(window, args[0], args[1],
3299 searchType(2, args, nArgs));
3302 static void replaceSameAP(Widget w, XEvent *event, String *args,
3303 Cardinal *nArgs)
3305 WindowInfo *window = WidgetToWindow(w);
3307 if (CheckReadOnly(window))
3308 return;
3309 ReplaceSame(window, searchDirection(0, args, nArgs), searchWrap(0, args, nArgs));
3312 static void replaceFindAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3314 WindowInfo *window = WidgetToWindow(w);
3316 if (CheckReadOnly(window))
3318 return;
3321 if (*nArgs < 2)
3323 DialogF(DF_WARN, window->shell, 1, "Error in replace_find",
3324 "replace_find action requires search and replace string arguments",
3325 "OK");
3326 return;
3329 ReplaceAndSearch(window, searchDirection(2, args, nArgs), args[0], args[1],
3330 searchType(2, args, nArgs), searchWrap(0, args, nArgs));
3333 static void replaceFindSameAP(Widget w, XEvent *event, String *args,
3334 Cardinal *nArgs)
3336 WindowInfo *window = WidgetToWindow(w);
3338 if (CheckReadOnly(window))
3339 return;
3340 ReplaceFindSame(window, searchDirection(0, args, nArgs), searchWrap(0, args, nArgs));
3343 static void gotoAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3345 int lineNum, column, position, curCol;
3347 /* Accept various formats:
3348 [line]:[column] (menu action)
3349 line (macro call)
3350 line, column (macro call) */
3351 if (*nArgs == 0 || *nArgs > 2
3352 || (*nArgs == 1
3353 && StringToLineAndCol(args[0], &lineNum, &column ) == -1)
3354 || (*nArgs == 2
3355 && (!StringToNum(args[0], &lineNum)
3356 || !StringToNum(args[1], &column)))) {
3357 fprintf(stderr,"nedit: goto_line_number action requires line and/or column number\n");
3358 return;
3361 /* User specified column, but not line number */
3362 if (lineNum == -1) {
3363 position = TextGetCursorPos(w);
3364 if (TextPosToLineAndCol(w, position, &lineNum, &curCol) == False) {
3365 return;
3367 } else if ( column == -1 ) {
3368 /* User didn't specify a column */
3369 SelectNumberedLine(WidgetToWindow(w), lineNum);
3370 return;
3373 position = TextLineAndColToPos(w, lineNum, column );
3374 if ( position == -1 ) {
3375 return;
3378 TextSetCursorPos(w, position);
3379 return;
3382 static void gotoDialogAP(Widget w, XEvent *event, String *args,
3383 Cardinal *nArgs)
3385 GotoLineNumber(WidgetToWindow(w));
3388 static void gotoSelectedAP(Widget w, XEvent *event, String *args,
3389 Cardinal *nArgs)
3391 GotoSelectedLineNumber(WidgetToWindow(w), event->xbutton.time);
3394 static void repeatDialogAP(Widget w, XEvent *event, String *args,
3395 Cardinal *nArgs)
3397 RepeatDialog(WidgetToWindow(w));
3400 static void repeatMacroAP(Widget w, XEvent *event, String *args,
3401 Cardinal *nArgs)
3403 int how;
3405 if (*nArgs != 2) {
3406 fprintf(stderr, "nedit: repeat_macro requires two arguments\n");
3407 return;
3409 if (!strcmp(args[0], "in_selection"))
3410 how = REPEAT_IN_SEL;
3411 else if (!strcmp(args[0], "to_end"))
3412 how = REPEAT_TO_END;
3413 else if (sscanf(args[0], "%d", &how) != 1) {
3414 fprintf(stderr, "nedit: repeat_macro requires method/count\n");
3415 return;
3417 RepeatMacro(WidgetToWindow(w), args[1], how);
3420 static void markAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3422 if (*nArgs == 0 || strlen(args[0]) != 1 ||
3423 !isalnum((unsigned char)args[0][0])) {
3424 fprintf(stderr,"nedit: mark action requires a single-letter label\n");
3425 return;
3427 AddMark(WidgetToWindow(w), w, args[0][0]);
3430 static void markDialogAP(Widget w, XEvent *event, String *args,
3431 Cardinal *nArgs)
3433 MarkDialog(WidgetToWindow(w));
3436 static void gotoMarkAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3438 if (*nArgs == 0 || strlen(args[0]) != 1 ||
3439 !isalnum((unsigned char)args[0][0])) {
3440 fprintf(stderr,
3441 "nedit: goto_mark action requires a single-letter label\n");
3442 return;
3444 GotoMark(WidgetToWindow(w), w, args[0][0], *nArgs > 1 &&
3445 !strcmp(args[1], "extend"));
3448 static void gotoMarkDialogAP(Widget w, XEvent *event, String *args,
3449 Cardinal *nArgs)
3451 GotoMarkDialog(WidgetToWindow(w), *nArgs!=0 && !strcmp(args[0], "extend"));
3454 static void selectToMatchingAP(Widget w, XEvent *event, String *args,
3455 Cardinal *nArgs)
3457 SelectToMatchingCharacter(WidgetToWindow(w));
3460 static void gotoMatchingAP(Widget w, XEvent *event, String *args,
3461 Cardinal *nArgs)
3463 GotoMatchingCharacter(WidgetToWindow(w));
3466 static void findDefAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3468 FindDefinition(WidgetToWindow(w), event->xbutton.time,
3469 *nArgs == 0 ? NULL : args[0]);
3472 static void showTipAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3474 FindDefCalltip(WidgetToWindow(w), event->xbutton.time,
3475 *nArgs == 0 ? NULL : args[0]);
3478 static void splitPaneAP(Widget w, XEvent *event, String *args,
3479 Cardinal *nArgs)
3481 WindowInfo *window = WidgetToWindow(w);
3483 SplitPane(window);
3484 if (IsTopDocument(window)) {
3485 XtSetSensitive(window->splitPaneItem, window->nPanes < MAX_PANES);
3486 XtSetSensitive(window->closePaneItem, window->nPanes > 0);
3490 static void closePaneAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3492 WindowInfo *window = WidgetToWindow(w);
3494 ClosePane(window);
3495 if (IsTopDocument(window)) {
3496 XtSetSensitive(window->splitPaneItem, window->nPanes < MAX_PANES);
3497 XtSetSensitive(window->closePaneItem, window->nPanes > 0);
3501 static void detachDocumentDialogAP(Widget w, XEvent *event, String *args,
3502 Cardinal *nArgs)
3504 WindowInfo *window = WidgetToWindow(w);
3505 int resp;
3507 if (NDocuments(window) < 2)
3508 return;
3510 resp = DialogF(DF_QUES, window->shell, 2, "Detach %s?",
3511 "Detach", "Cancel", window->filename);
3513 if (resp == 1)
3514 DetachDocument(window);
3517 static void detachDocumentAP(Widget w, XEvent *event, String *args,
3518 Cardinal *nArgs)
3520 WindowInfo *window = WidgetToWindow(w);
3522 if (NDocuments(window) < 2)
3523 return;
3525 DetachDocument(window);
3528 static void moveDocumentDialogAP(Widget w, XEvent *event, String *args,
3529 Cardinal *nArgs)
3531 MoveDocumentDialog(WidgetToWindow(w));
3534 static void nextDocumentAP(Widget w, XEvent *event, String *args,
3535 Cardinal *nArgs)
3537 NextDocument(WidgetToWindow(w));
3540 static void prevDocumentAP(Widget w, XEvent *event, String *args,
3541 Cardinal *nArgs)
3543 PreviousDocument(WidgetToWindow(w));
3546 static void lastDocumentAP(Widget w, XEvent *event, String *args,
3547 Cardinal *nArgs)
3549 LastDocument(WidgetToWindow(w));
3552 static void capitalizeAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3554 WindowInfo *window = WidgetToWindow(w);
3556 if (CheckReadOnly(window))
3557 return;
3558 UpcaseSelection(window);
3561 static void lowercaseAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3563 WindowInfo *window = WidgetToWindow(w);
3565 if (CheckReadOnly(window))
3566 return;
3567 DowncaseSelection(window);
3570 static void fillAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3572 WindowInfo *window = WidgetToWindow(w);
3574 if (CheckReadOnly(window))
3575 return;
3576 FillSelection(window);
3579 static void controlDialogAP(Widget w, XEvent *event, String *args,
3580 Cardinal *nArgs)
3582 WindowInfo *window = WidgetToWindow(w);
3583 unsigned char charCodeString[2];
3584 char charCodeText[DF_MAX_PROMPT_LENGTH], dummy[DF_MAX_PROMPT_LENGTH];
3585 char *params[1];
3586 int charCode, nRead, response;
3588 if (CheckReadOnly(window))
3589 return;
3591 response = DialogF(DF_PROMPT, window->shell, 2, "Insert Ctrl Code",
3592 "ASCII Character Code:", charCodeText, "OK", "Cancel");
3594 if (response == 2)
3595 return;
3596 /* If we don't scan for a trailing string invalid input
3597 would be accepted sometimes. */
3598 nRead = sscanf(charCodeText, "%i%s", &charCode, dummy);
3599 if (nRead != 1 || charCode < 0 || charCode > 255) {
3600 XBell(TheDisplay, 0);
3601 return;
3603 charCodeString[0] = (unsigned char)charCode;
3604 charCodeString[1] = '\0';
3605 params[0] = (char *)charCodeString;
3607 if (!BufSubstituteNullChars((char *)charCodeString, 1, window->buffer))
3609 DialogF(DF_ERR, window->shell, 1, "Error", "Too much binary data",
3610 "OK");
3611 return;
3614 XtCallActionProc(w, "insert_string", event, params, 1);
3617 #ifndef VMS
3618 static void filterDialogAP(Widget w, XEvent *event, String *args,
3619 Cardinal *nArgs)
3621 WindowInfo *window = WidgetToWindow(w);
3622 char *params[1], cmdText[DF_MAX_PROMPT_LENGTH];
3623 int resp;
3624 static char **cmdHistory = NULL;
3625 static int nHistoryCmds = 0;
3627 if (CheckReadOnly(window))
3628 return;
3629 if (!window->buffer->primary.selected) {
3630 XBell(TheDisplay, 0);
3631 return;
3634 SetDialogFPromptHistory(cmdHistory, nHistoryCmds);
3636 resp = DialogF(DF_PROMPT, window->shell, 2, "Filter Selection",
3637 "Shell command: (use up arrow key to recall previous)",
3638 cmdText, "OK", "Cancel");
3640 if (resp == 2)
3641 return;
3642 AddToHistoryList(cmdText, &cmdHistory, &nHistoryCmds);
3643 params[0] = cmdText;
3644 XtCallActionProc(w, "filter_selection", event, params, 1);
3647 static void shellFilterAP(Widget w, XEvent *event, String *args,
3648 Cardinal *nArgs)
3650 WindowInfo *window = WidgetToWindow(w);
3652 if (CheckReadOnly(window))
3653 return;
3654 if (*nArgs == 0) {
3655 fprintf(stderr,
3656 "nedit: filter_selection requires shell command argument\n");
3657 return;
3659 FilterSelection(window, args[0],
3660 event->xany.send_event == MACRO_EVENT_MARKER);
3663 static void execDialogAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3665 WindowInfo *window = WidgetToWindow(w);
3666 char *params[1], cmdText[DF_MAX_PROMPT_LENGTH];
3667 int resp;
3668 static char **cmdHistory = NULL;
3669 static int nHistoryCmds = 0;
3671 if (CheckReadOnly(window))
3672 return;
3673 SetDialogFPromptHistory(cmdHistory, nHistoryCmds);
3675 resp = DialogF(DF_PROMPT, window->shell, 2, "Execute Command",
3676 "Shell command: (use up arrow key to recall previous;\n"
3677 "%% expands to current filename, # to line number)", cmdText, "OK",
3678 "Cancel");
3680 if (resp == 2)
3681 return;
3682 AddToHistoryList(cmdText, &cmdHistory, &nHistoryCmds);
3683 params[0] = cmdText;
3684 XtCallActionProc(w, "execute_command", event, params, 1);;
3687 static void execAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3689 WindowInfo *window = WidgetToWindow(w);
3691 if (CheckReadOnly(window))
3692 return;
3693 if (*nArgs == 0) {
3694 fprintf(stderr,
3695 "nedit: execute_command requires shell command argument\n");
3696 return;
3698 ExecShellCommand(window, args[0],
3699 event->xany.send_event == MACRO_EVENT_MARKER);
3702 static void execLineAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3704 WindowInfo *window = WidgetToWindow(w);
3706 if (CheckReadOnly(window))
3707 return;
3708 ExecCursorLine(window, event->xany.send_event == MACRO_EVENT_MARKER);
3711 static void shellMenuAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3713 if (*nArgs == 0) {
3714 fprintf(stderr,
3715 "nedit: shell_menu_command requires item-name argument\n");
3716 return;
3718 HidePointerOnKeyedEvent(w, event);
3719 DoNamedShellMenuCmd(WidgetToWindow(w), args[0],
3720 event->xany.send_event == MACRO_EVENT_MARKER);
3722 #endif
3724 static void macroMenuAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3726 if (*nArgs == 0) {
3727 fprintf(stderr,
3728 "nedit: macro_menu_command requires item-name argument\n");
3729 return;
3731 /* Don't allow users to execute a macro command from the menu (or accel)
3732 if there's already a macro command executing, UNLESS the macro is
3733 directly called from another one. NEdit can't handle
3734 running multiple, independent uncoordinated, macros in the same
3735 window. Macros may invoke macro menu commands recursively via the
3736 macro_menu_command action proc, which is important for being able to
3737 repeat any operation, and to embed macros within eachother at any
3738 level, however, a call here with a macro running means that THE USER
3739 is explicitly invoking another macro via the menu or an accelerator,
3740 UNLESS the macro event marker is set */
3741 if (event->xany.send_event != MACRO_EVENT_MARKER) {
3742 if (WidgetToWindow(w)->macroCmdData != NULL) {
3743 XBell(TheDisplay, 0);
3744 return;
3747 HidePointerOnKeyedEvent(w, event);
3748 DoNamedMacroMenuCmd(WidgetToWindow(w), args[0]);
3751 static void bgMenuAP(Widget w, XEvent *event, String *args, Cardinal *nArgs)
3753 if (*nArgs == 0) {
3754 fprintf(stderr,
3755 "nedit: bg_menu_command requires item-name argument\n");
3756 return;
3758 /* Same remark as for macro menu commands (see above). */
3759 if (event->xany.send_event != MACRO_EVENT_MARKER) {
3760 if (WidgetToWindow(w)->macroCmdData != NULL) {
3761 XBell(TheDisplay, 0);
3762 return;
3765 HidePointerOnKeyedEvent(w, event);
3766 DoNamedBGMenuCmd(WidgetToWindow(w), args[0]);
3769 static void beginningOfSelectionAP(Widget w, XEvent *event, String *args,
3770 Cardinal *nArgs)
3772 textBuffer *buf = TextGetBuffer(w);
3773 int start, end, isRect, rectStart, rectEnd;
3775 if (!BufGetSelectionPos(buf, &start, &end, &isRect, &rectStart, &rectEnd))
3776 return;
3777 if (!isRect)
3778 TextSetCursorPos(w, start);
3779 else
3780 TextSetCursorPos(w, BufCountForwardDispChars(buf,
3781 BufStartOfLine(buf, start), rectStart));
3784 static void endOfSelectionAP(Widget w, XEvent *event, String *args,
3785 Cardinal *nArgs)
3787 textBuffer *buf = TextGetBuffer(w);
3788 int start, end, isRect, rectStart, rectEnd;
3790 if (!BufGetSelectionPos(buf, &start, &end, &isRect, &rectStart, &rectEnd))
3791 return;
3792 if (!isRect)
3793 TextSetCursorPos(w, end);
3794 else
3795 TextSetCursorPos(w, BufCountForwardDispChars(buf,
3796 BufStartOfLine(buf, end), rectEnd));
3799 static void raiseWindowAP(Widget w, XEvent *event, String *args,
3800 Cardinal *nArgs)
3802 WindowInfo *window = WidgetToWindow(w);
3803 WindowInfo *nextWindow;
3804 WindowInfo *tmpWindow;
3805 int windowIndex;
3806 Boolean focus = GetPrefFocusOnRaise();
3808 if (*nArgs > 0) {
3809 if (strcmp(args[0], "last") == 0) {
3810 window = WindowList;
3812 else if (strcmp(args[0], "first") == 0) {
3813 window = WindowList;
3814 if (window != NULL) {
3815 nextWindow = window->next;
3816 while (nextWindow != NULL) {
3817 window = nextWindow;
3818 nextWindow = nextWindow->next;
3822 else if (strcmp(args[0], "previous") == 0) {
3823 tmpWindow = window;
3824 window = WindowList;
3825 if (window != NULL) {
3826 nextWindow = window->next;
3827 while (nextWindow != NULL && nextWindow != tmpWindow) {
3828 window = nextWindow;
3829 nextWindow = nextWindow->next;
3831 if (nextWindow == NULL && tmpWindow != WindowList) {
3832 window = NULL;
3836 else if (strcmp(args[0], "next") == 0) {
3837 if (window != NULL) {
3838 window = window->next;
3839 if (window == NULL) {
3840 window = WindowList;
3844 else {
3845 if (sscanf(args[0], "%d", &windowIndex) == 1) {
3846 if (windowIndex > 0) {
3847 for (window = WindowList; window != NULL && windowIndex > 1;
3848 --windowIndex) {
3849 window = window->next;
3852 else if (windowIndex < 0) {
3853 for (window = WindowList; window != NULL;
3854 window = window->next) {
3855 ++windowIndex;
3857 if (windowIndex >= 0) {
3858 for (window = WindowList; window != NULL &&
3859 windowIndex > 0; window = window->next) {
3860 --windowIndex;
3863 else {
3864 window = NULL;
3867 else {
3868 window = NULL;
3871 else {
3872 window = NULL;
3876 if (*nArgs > 1) {
3877 if (strcmp(args[1], "focus") == 0) {
3878 focus = True;
3880 else if (strcmp(args[1], "nofocus") == 0) {
3881 focus = False;
3885 if (window != NULL) {
3886 RaiseFocusDocumentWindow(window, focus);
3888 else {
3889 XBell(TheDisplay, 0);
3893 static void focusPaneAP(Widget w, XEvent *event, String *args,
3894 Cardinal *nArgs)
3896 WindowInfo *window = WidgetToWindow(w);
3897 Widget newFocusPane = NULL;
3898 int paneIndex;
3900 if (*nArgs > 0) {
3901 if (strcmp(args[0], "first") == 0) {
3902 paneIndex = 0;
3904 else if (strcmp(args[0], "last") == 0) {
3905 paneIndex = window->nPanes;
3907 else if (strcmp(args[0], "next") == 0) {
3908 paneIndex = WidgetToPaneIndex(window, window->lastFocus) + 1;
3909 if (paneIndex > window->nPanes) {
3910 paneIndex = 0;
3913 else if (strcmp(args[0], "previous") == 0) {
3914 paneIndex = WidgetToPaneIndex(window, window->lastFocus) - 1;
3915 if (paneIndex < 0) {
3916 paneIndex = window->nPanes;
3919 else {
3920 if (sscanf(args[0], "%d", &paneIndex) == 1) {
3921 if (paneIndex > 0) {
3922 paneIndex = paneIndex - 1;
3924 else if (paneIndex < 0) {
3925 paneIndex = window->nPanes + (paneIndex + 1);
3927 else {
3928 paneIndex = -1;
3932 if (paneIndex >= 0 && paneIndex <= window->nPanes) {
3933 newFocusPane = GetPaneByIndex(window, paneIndex);
3935 if (newFocusPane != NULL) {
3936 window->lastFocus = newFocusPane;
3937 XmProcessTraversal(window->lastFocus, XmTRAVERSE_CURRENT);
3939 else {
3940 XBell(TheDisplay, 0);
3943 else {
3944 fprintf(stderr, "nedit: focus_pane requires argument\n");
3948 #define ACTION_BOOL_PARAM_OR_TOGGLE(newState, numArgs, argvVal, oValue, actionName) \
3949 if ((numArgs) > 0) { \
3950 int intState; \
3952 if (sscanf(argvVal[0], "%d", &intState) == 1) { \
3953 (newState) = (intState != 0); \
3955 else { \
3956 fprintf(stderr, "nedit: %s requires 0 or 1 argument\n", actionName); \
3957 return; \
3960 else { \
3961 (newState) = !(oValue); \
3964 static void setStatisticsLineAP(Widget w, XEvent *event, String *args,
3965 Cardinal *nArgs)
3967 WindowInfo *window = WidgetToWindow(w);
3968 Boolean newState;
3970 /* stats line is a shell-level item, so we toggle the button
3971 state regardless of it's 'topness' */
3972 ACTION_BOOL_PARAM_OR_TOGGLE(newState, *nArgs, args, window->showStats,
3973 "set_statistics_line");
3974 XmToggleButtonSetState(window->statsLineItem, newState, False);
3975 ShowStatsLine(window, newState);
3978 static void setIncrementalSearchLineAP(Widget w, XEvent *event, String *args,
3979 Cardinal *nArgs)
3981 WindowInfo *window = WidgetToWindow(w);
3982 Boolean newState;
3984 /* i-search line is a shell-level item, so we toggle the button
3985 state regardless of it's 'topness' */
3986 ACTION_BOOL_PARAM_OR_TOGGLE(newState, *nArgs, args,
3987 window->showISearchLine, "set_incremental_search_line");
3988 XmToggleButtonSetState(window->iSearchLineItem, newState, False);
3989 ShowISearchLine(window, newState);
3992 static void setShowLineNumbersAP(Widget w, XEvent *event, String *args,
3993 Cardinal *nArgs)
3995 WindowInfo *window = WidgetToWindow(w);
3996 Boolean newState;
3998 /* line numbers panel is a shell-level item, so we toggle the button
3999 state regardless of it's 'topness' */
4000 ACTION_BOOL_PARAM_OR_TOGGLE(newState, *nArgs, args,
4001 window->showLineNumbers, "set_show_line_numbers");
4002 XmToggleButtonSetState(window->lineNumsItem, newState, False);
4003 ShowLineNumbers(window, newState);
4006 static void setAutoIndentAP(Widget w, XEvent *event, String *args,
4007 Cardinal *nArgs)
4009 WindowInfo *window = WidgetToWindow(w);
4010 if (*nArgs > 0) {
4011 if (strcmp(args[0], "off") == 0) {
4012 SetAutoIndent(window, NO_AUTO_INDENT);
4014 else if (strcmp(args[0], "on") == 0) {
4015 SetAutoIndent(window, AUTO_INDENT);
4017 else if (strcmp(args[0], "smart") == 0) {
4018 SetAutoIndent(window, SMART_INDENT);
4020 else {
4021 fprintf(stderr, "nedit: set_auto_indent invalid argument\n");
4024 else {
4025 fprintf(stderr, "nedit: set_auto_indent requires argument\n");
4029 static void setWrapTextAP(Widget w, XEvent *event, String *args,
4030 Cardinal *nArgs)
4032 WindowInfo *window = WidgetToWindow(w);
4033 if (*nArgs > 0) {
4034 if (strcmp(args[0], "none") == 0) {
4035 SetAutoWrap(window, NO_WRAP);
4037 else if (strcmp(args[0], "auto") == 0) {
4038 SetAutoWrap(window, NEWLINE_WRAP);
4040 else if (strcmp(args[0], "continuous") == 0) {
4041 SetAutoWrap(window, CONTINUOUS_WRAP);
4043 else {
4044 fprintf(stderr, "nedit: set_wrap_text invalid argument\n");
4047 else {
4048 fprintf(stderr, "nedit: set_wrap_text requires argument\n");
4052 static void setWrapMarginAP(Widget w, XEvent *event, String *args,
4053 Cardinal *nArgs)
4055 WindowInfo *window = WidgetToWindow(w);
4057 if (*nArgs > 0) {
4058 int newMargin = 0;
4059 if (sscanf(args[0], "%d", &newMargin) == 1 &&
4060 newMargin >= 0 &&
4061 newMargin < 1000) {
4062 int i;
4064 XtVaSetValues(window->textArea, textNwrapMargin, newMargin, NULL);
4065 for (i = 0; i < window->nPanes; ++i) {
4066 XtVaSetValues(window->textPanes[i], textNwrapMargin, newMargin, NULL);
4069 else {
4070 fprintf(stderr,
4071 "nedit: set_wrap_margin requires integer argument >= 0 and < 1000\n");
4074 else {
4075 fprintf(stderr, "nedit: set_wrap_margin requires argument\n");
4079 static void setHighlightSyntaxAP(Widget w, XEvent *event, String *args,
4080 Cardinal *nArgs)
4082 WindowInfo *window = WidgetToWindow(w);
4083 Boolean newState;
4085 ACTION_BOOL_PARAM_OR_TOGGLE(newState, *nArgs, args, window->highlightSyntax, "set_highlight_syntax");
4087 if (IsTopDocument(window))
4088 XmToggleButtonSetState(window->highlightItem, newState, False);
4089 window->highlightSyntax = newState;
4090 if (window->highlightSyntax) {
4091 StartHighlighting(window, True);
4092 } else {
4093 StopHighlighting(window);
4097 static void setMakeBackupCopyAP(Widget w, XEvent *event, String *args,
4098 Cardinal *nArgs)
4100 WindowInfo *window = WidgetToWindow(w);
4101 Boolean newState;
4103 ACTION_BOOL_PARAM_OR_TOGGLE(newState, *nArgs, args, window->saveOldVersion, "set_make_backup_copy");
4105 #ifndef VMS
4106 if (IsTopDocument(window))
4107 XmToggleButtonSetState(window->saveLastItem, newState, False);
4108 #endif
4109 window->saveOldVersion = newState;
4112 static void setIncrementalBackupAP(Widget w, XEvent *event, String *args,
4113 Cardinal *nArgs)
4115 WindowInfo *window = WidgetToWindow(w);
4116 Boolean newState;
4118 ACTION_BOOL_PARAM_OR_TOGGLE(newState, *nArgs, args, window->autoSave, "set_incremental_backup");
4120 if (IsTopDocument(window))
4121 XmToggleButtonSetState(window->autoSaveItem, newState, False);
4122 window->autoSave = newState;
4125 static void setShowMatchingAP(Widget w, XEvent *event, String *args,
4126 Cardinal *nArgs)
4128 WindowInfo *window = WidgetToWindow(w);
4129 if (*nArgs > 0) {
4130 if (strcmp(args[0], NO_FLASH_STRING) == 0) {
4131 SetShowMatching(window, NO_FLASH);
4133 else if (strcmp(args[0], FLASH_DELIMIT_STRING) == 0) {
4134 SetShowMatching(window, FLASH_DELIMIT);
4136 else if (strcmp(args[0], FLASH_RANGE_STRING) == 0) {
4137 SetShowMatching(window, FLASH_RANGE);
4139 /* For backward compatibility with pre-5.2 versions, we also
4140 accept 0 and 1 as aliases for NO_FLASH and FLASH_DELIMIT.
4141 It is quite unlikely, though, that anyone ever used this
4142 action procedure via the macro language or a key binding,
4143 so this can probably be left out safely. */
4144 else if (strcmp(args[0], "0") == 0) {
4145 SetShowMatching(window, NO_FLASH);
4147 else if (strcmp(args[0], "1") == 0) {
4148 SetShowMatching(window, FLASH_DELIMIT);
4150 else {
4151 fprintf(stderr, "nedit: Invalid argument for set_show_matching\n");
4154 else {
4155 fprintf(stderr, "nedit: set_show_matching requires argument\n");
4159 static void setMatchSyntaxBasedAP(Widget w, XEvent *event, String *args,
4160 Cardinal *nArgs)
4162 WindowInfo *window = WidgetToWindow(w);
4163 Boolean newState;
4165 ACTION_BOOL_PARAM_OR_TOGGLE(newState, *nArgs, args, window->matchSyntaxBased, "set_match_syntax_based");
4167 if (IsTopDocument(window))
4168 XmToggleButtonSetState(window->matchSyntaxBasedItem, newState, False);
4169 window->matchSyntaxBased = newState;
4172 static void setOvertypeModeAP(Widget w, XEvent *event, String *args,
4173 Cardinal *nArgs)
4175 WindowInfo *window = WidgetToWindow(w);
4176 Boolean newState;
4178 if (window == NULL)
4179 return;
4181 ACTION_BOOL_PARAM_OR_TOGGLE(newState, *nArgs, args, window->overstrike, "set_overtype_mode");
4183 if (IsTopDocument(window))
4184 XmToggleButtonSetState(window->overtypeModeItem, newState, False);
4185 SetOverstrike(window, newState);
4188 static void setLockedAP(Widget w, XEvent *event, String *args,
4189 Cardinal *nArgs)
4191 WindowInfo *window = WidgetToWindow(w);
4192 Boolean newState;
4194 ACTION_BOOL_PARAM_OR_TOGGLE(newState, *nArgs, args, IS_USER_LOCKED(window->lockReasons), "set_locked");
4196 SET_USER_LOCKED(window->lockReasons, newState);
4197 if (IsTopDocument(window))
4198 XmToggleButtonSetState(window->readOnlyItem, IS_ANY_LOCKED(window->lockReasons), False);
4199 UpdateWindowTitle(window);
4200 UpdateWindowReadOnly(window);
4203 static void setTabDistAP(Widget w, XEvent *event, String *args,
4204 Cardinal *nArgs)
4206 WindowInfo *window = WidgetToWindow(w);
4208 if (*nArgs > 0) {
4209 int newTabDist = 0;
4210 if (sscanf(args[0], "%d", &newTabDist) == 1 &&
4211 newTabDist > 0 &&
4212 newTabDist <= MAX_EXP_CHAR_LEN) {
4213 SetTabDist(window, newTabDist);
4215 else {
4216 fprintf(stderr,
4217 "nedit: set_tab_dist requires integer argument > 0 and <= %d\n",
4218 MAX_EXP_CHAR_LEN);
4221 else {
4222 fprintf(stderr, "nedit: set_tab_dist requires argument\n");
4226 static void setEmTabDistAP(Widget w, XEvent *event, String *args,
4227 Cardinal *nArgs)
4229 WindowInfo *window = WidgetToWindow(w);
4231 if (*nArgs > 0) {
4232 int newEmTabDist = 0;
4233 if (sscanf(args[0], "%d", &newEmTabDist) == 1 &&
4234 newEmTabDist < 1000) {
4235 if (newEmTabDist < 0) {
4236 newEmTabDist = 0;
4238 SetEmTabDist(window, newEmTabDist);
4240 else {
4241 fprintf(stderr,
4242 "nedit: set_em_tab_dist requires integer argument >= -1 and < 1000\n");
4245 else {
4246 fprintf(stderr, "nedit: set_em_tab_dist requires integer argument\n");
4250 static void setUseTabsAP(Widget w, XEvent *event, String *args,
4251 Cardinal *nArgs)
4253 WindowInfo *window = WidgetToWindow(w);
4254 Boolean newState;
4256 ACTION_BOOL_PARAM_OR_TOGGLE(newState, *nArgs, args, window->buffer->useTabs, "set_use_tabs");
4258 window->buffer->useTabs = newState;
4261 static void setFontsAP(Widget w, XEvent *event, String *args,
4262 Cardinal *nArgs)
4264 WindowInfo *window = WidgetToWindow(w);
4265 if (*nArgs >= 4) {
4266 SetFonts(window, args[0], args[1], args[2], args[3]);
4268 else {
4269 fprintf(stderr, "nedit: set_fonts requires 4 arguments\n");
4273 static void setLanguageModeAP(Widget w, XEvent *event, String *args,
4274 Cardinal *nArgs)
4276 WindowInfo *window = WidgetToWindow(w);
4278 if (*nArgs > 0) {
4279 SetLanguageMode(window, FindLanguageMode(args[0]), FALSE);
4281 else {
4282 fprintf(stderr, "nedit: set_language_mode requires argument\n");
4287 ** Same as AddSubMenu from libNUtil.a but 1) mnemonic is optional (NEdit
4288 ** users like to be able to re-arrange the mnemonics so they can set Alt
4289 ** key combinations as accelerators), 2) supports the short/full option
4290 ** of SGI_CUSTOM mode, 3) optionally returns the cascade button widget
4291 ** in "cascadeBtn" if "cascadeBtn" is non-NULL.
4293 static Widget createMenu(Widget parent, char *name, char *label,
4294 char mnemonic, Widget *cascadeBtn, int mode)
4296 Widget menu, cascade;
4297 XmString st1;
4299 menu = CreatePulldownMenu(parent, name, NULL, 0);
4300 cascade = XtVaCreateWidget(name, xmCascadeButtonWidgetClass, parent,
4301 XmNlabelString, st1=XmStringCreateSimple(label),
4302 XmNsubMenuId, menu, NULL);
4303 XmStringFree(st1);
4304 if (mnemonic != 0)
4305 XtVaSetValues(cascade, XmNmnemonic, mnemonic, NULL);
4306 #ifdef SGI_CUSTOM
4307 if (mode == SHORT || !GetPrefShortMenus())
4308 XtManageChild(cascade);
4309 if (mode == FULL)
4310 addToToggleShortList(cascade);
4311 #else
4312 XtManageChild(cascade);
4313 #endif
4314 if (cascadeBtn != NULL)
4315 *cascadeBtn = cascade;
4316 return menu;
4320 ** Same as AddMenuItem from libNUtil.a without setting the accelerator
4321 ** (these are set in the fallback app-defaults so users can change them),
4322 ** and with the short/full option required in SGI_CUSTOM mode.
4324 static Widget createMenuItem(Widget parent, char *name, char *label,
4325 char mnemonic, menuCallbackProc callback, void *cbArg, int mode)
4327 Widget button;
4328 XmString st1;
4331 button = XtVaCreateWidget(name, xmPushButtonWidgetClass, parent,
4332 XmNlabelString, st1=XmStringCreateSimple(label),
4333 XmNmnemonic, mnemonic, NULL);
4334 XtAddCallback(button, XmNactivateCallback, (XtCallbackProc)callback, cbArg);
4335 XmStringFree(st1);
4336 #ifdef SGI_CUSTOM
4337 if (mode == SHORT || !GetPrefShortMenus())
4338 XtManageChild(button);
4339 if (mode == FULL)
4340 addToToggleShortList(button);
4341 XtVaSetValues(button, XmNuserData, PERMANENT_MENU_ITEM, NULL);
4342 #else
4343 XtManageChild(button);
4344 #endif
4345 return button;
4349 ** "fake" menu items allow accelerators to be attached, but don't show up
4350 ** in the menu. They are necessary to process the shifted menu items because
4351 ** Motif does not properly process the event descriptions in accelerator
4352 ** resources, and you can't specify "shift key is optional"
4354 static Widget createFakeMenuItem(Widget parent, char *name,
4355 menuCallbackProc callback, void *cbArg)
4357 Widget button;
4358 XmString st1;
4360 button = XtVaCreateManagedWidget(name, xmPushButtonWidgetClass, parent,
4361 XmNlabelString, st1=XmStringCreateSimple(""),
4362 XmNshadowThickness, 0,
4363 XmNmarginHeight, 0,
4364 XmNheight, 0, NULL);
4365 XtAddCallback(button, XmNactivateCallback, (XtCallbackProc)callback, cbArg);
4366 XmStringFree(st1);
4367 XtVaSetValues(button, XmNtraversalOn, False, NULL);
4369 return button;
4373 ** Add a toggle button item to an already established pull-down or pop-up
4374 ** menu, including mnemonics, accelerators and callbacks.
4376 static Widget createMenuToggle(Widget parent, char *name, char *label,
4377 char mnemonic, menuCallbackProc callback, void *cbArg, int set,
4378 int mode)
4380 Widget button;
4381 XmString st1;
4383 button = XtVaCreateWidget(name, xmToggleButtonWidgetClass, parent,
4384 XmNlabelString, st1=XmStringCreateSimple(label),
4385 XmNmnemonic, mnemonic,
4386 XmNset, set, NULL);
4387 XtAddCallback(button, XmNvalueChangedCallback, (XtCallbackProc)callback,
4388 cbArg);
4389 XmStringFree(st1);
4390 #ifdef SGI_CUSTOM
4391 if (mode == SHORT || !GetPrefShortMenus())
4392 XtManageChild(button);
4393 if (mode == FULL)
4394 addToToggleShortList(button);
4395 XtVaSetValues(button, XmNuserData, PERMANENT_MENU_ITEM, NULL);
4396 #else
4397 XtManageChild(button);
4398 #endif
4399 return button;
4403 ** Create a toggle button with a diamond (radio-style) appearance
4405 static Widget createMenuRadioToggle(Widget parent, char *name, char *label,
4406 char mnemonic, menuCallbackProc callback, void *cbArg, int set,
4407 int mode)
4409 Widget button;
4410 button = createMenuToggle(parent, name, label, mnemonic, callback, cbArg,
4411 set, mode);
4412 XtVaSetValues(button, XmNindicatorType, XmONE_OF_MANY, NULL);
4413 return button;
4416 static Widget createMenuSeparator(Widget parent, char *name, int mode)
4418 Widget button;
4420 button = XmCreateSeparator(parent, name, NULL, 0);
4421 #ifdef SGI_CUSTOM
4422 if (mode == SHORT || !GetPrefShortMenus())
4423 XtManageChild(button);
4424 if (mode == FULL)
4425 addToToggleShortList(button);
4426 XtVaSetValues(button, XmNuserData, PERMANENT_MENU_ITEM, NULL);
4427 #else
4428 XtManageChild(button);
4429 #endif
4430 return button;
4434 ** Make sure the close menu item is dimmed appropriately for the current
4435 ** set of windows. It should be dim only for the last Untitled, unmodified,
4436 ** editor window, and sensitive otherwise.
4438 void CheckCloseDim(void)
4440 WindowInfo *window;
4442 if (WindowList == NULL)
4443 return;
4444 if (WindowList->next==NULL &&
4445 !WindowList->filenameSet && !WindowList->fileChanged) {
4446 XtSetSensitive(WindowList->closeItem, FALSE);
4447 return;
4450 for (window=WindowList; window!=NULL; window=window->next) {
4451 if (!IsTopDocument(window))
4452 continue;
4453 XtSetSensitive(window->closeItem, True);
4458 ** Invalidate the Window menus of all NEdit windows to but don't change
4459 ** the menus until they're needed (Originally, this was "UpdateWindowMenus",
4460 ** but creating and destroying manu items for every window every time a
4461 ** new window was created or something changed, made things move very
4462 ** slowly with more than 10 or so windows).
4464 void InvalidateWindowMenus(void)
4466 WindowInfo *w;
4468 /* Mark the window menus invalid (to be updated when the user pulls one
4469 down), unless the menu is torn off, meaning it is visible to the user
4470 and should be updated immediately */
4471 for (w=WindowList; w!=NULL; w=w->next) {
4472 if (!XmIsMenuShell(XtParent(w->windowMenuPane)))
4473 updateWindowMenu(w);
4474 else
4475 w->windowMenuValid = False;
4480 ** Mark the Previously Opened Files menus of all NEdit windows as invalid.
4481 ** Since actually changing the menus is slow, they're just marked and updated
4482 ** when the user pulls one down.
4484 static void invalidatePrevOpenMenus(void)
4486 WindowInfo *w;
4488 /* Mark the menus invalid (to be updated when the user pulls one
4489 down), unless the menu is torn off, meaning it is visible to the user
4490 and should be updated immediately */
4491 for (w=WindowList; w!=NULL; w=w->next) {
4492 if (!XmIsMenuShell(XtParent(w->prevOpenMenuPane)))
4493 updatePrevOpenMenu(w);
4498 ** Add a file to the list of previously opened files for display in the
4499 ** File menu.
4501 void AddToPrevOpenMenu(const char *filename)
4503 int i;
4504 char *nameCopy;
4505 WindowInfo *w;
4507 /* If the Open Previous command is disabled, just return */
4508 if (GetPrefMaxPrevOpenFiles() < 1) {
4509 return;
4512 /* Refresh list of previously opened files to avoid Big Race Condition,
4513 where two sessions overwrite each other's changes in NEdit's
4514 history file.
4515 Of course there is still Little Race Condition, which occurs if a
4516 Session A reads the list, then Session B reads the list and writes
4517 it before Session A gets a chance to write. */
4518 ReadNEditDB();
4520 /* If the name is already in the list, move it to the start */
4521 for (i=0; i<NPrevOpen; i++) {
4522 if (!strcmp(filename, PrevOpen[i])) {
4523 nameCopy = PrevOpen[i];
4524 memmove(&PrevOpen[1], &PrevOpen[0], sizeof(char *) * i);
4525 PrevOpen[0] = nameCopy;
4526 invalidatePrevOpenMenus();
4527 WriteNEditDB();
4528 return;
4532 /* If the list is already full, make room */
4533 if (NPrevOpen >= GetPrefMaxPrevOpenFiles()) {
4534 /* This is only safe if GetPrefMaxPrevOpenFiles() > 0. */
4535 XtFree(PrevOpen[--NPrevOpen]);
4538 /* Add it to the list */
4539 nameCopy = XtMalloc(strlen(filename) + 1);
4540 strcpy(nameCopy, filename);
4541 memmove(&PrevOpen[1], &PrevOpen[0], sizeof(char *) * NPrevOpen);
4542 PrevOpen[0] = nameCopy;
4543 NPrevOpen++;
4545 /* Mark the Previously Opened Files menu as invalid in all windows */
4546 invalidatePrevOpenMenus();
4548 /* Undim the menu in all windows if it was previously empty */
4549 if (NPrevOpen > 0) {
4550 for (w=WindowList; w!=NULL; w=w->next) {
4551 if (!IsTopDocument(w))
4552 continue;
4553 XtSetSensitive(w->prevOpenMenuItem, True);
4557 /* Write the menu contents to disk to restore in later sessions */
4558 WriteNEditDB();
4561 static char* getWindowsMenuEntry(const WindowInfo* window)
4563 static char fullTitle[MAXPATHLEN * 2 + 3+ 1];
4565 sprintf(fullTitle, "%s%s", window->filename,
4566 window->fileChanged? "*" : "");
4568 if (GetPrefShowPathInWindowsMenu() && window->filenameSet)
4570 strcat(fullTitle, " - ");
4571 strcat(fullTitle, window->path);
4574 return(fullTitle);
4578 ** Update the Window menu of a single window to reflect the current state of
4579 ** all NEdit windows as determined by the global WindowList.
4581 static void updateWindowMenu(const WindowInfo *window)
4583 WindowInfo *w;
4584 WidgetList items;
4585 Cardinal nItems;
4586 int i, n, nWindows, windowIndex;
4587 WindowInfo **windows;
4589 if (!IsTopDocument(window))
4590 return;
4592 /* Make a sorted list of windows */
4593 for (w=WindowList, nWindows=0; w!=NULL; w=w->next, nWindows++);
4594 windows = (WindowInfo **)XtMalloc(sizeof(WindowInfo *) * nWindows);
4595 for (w=WindowList, i=0; w!=NULL; w=w->next, i++)
4596 windows[i] = w;
4597 qsort(windows, nWindows, sizeof(WindowInfo *), compareWindowNames);
4599 /* if the menu is torn off, unmanage the menu pane
4600 before updating it to prevent the tear-off menu
4601 from shrinking/expanding as the menu entries
4602 are added */
4603 if (!XmIsMenuShell(XtParent(window->windowMenuPane)))
4604 XtUnmanageChild(window->windowMenuPane);
4606 /* While it is not possible on some systems (ibm at least) to substitute
4607 a new menu pane, it is possible to substitute menu items, as long as
4608 at least one remains in the menu at all times. This routine assumes
4609 that the menu contains permanent items marked with the value
4610 PERMANENT_MENU_ITEM in the userData resource, and adds and removes items
4611 which it marks with the value TEMPORARY_MENU_ITEM */
4613 /* Go thru all of the items in the menu and rename them to
4614 match the window list. Delete any extras */
4615 XtVaGetValues(window->windowMenuPane, XmNchildren, &items,
4616 XmNnumChildren, &nItems, NULL);
4617 windowIndex = 0;
4618 nWindows = NWindows();
4619 for (n=0; n<(int)nItems; n++) {
4620 XtPointer userData;
4621 XtVaGetValues(items[n], XmNuserData, &userData, NULL);
4622 if (userData == TEMPORARY_MENU_ITEM) {
4623 if (windowIndex >= nWindows) {
4624 /* unmanaging before destroying stops parent from displaying */
4625 XtUnmanageChild(items[n]);
4626 XtDestroyWidget(items[n]);
4627 } else {
4628 XmString st1;
4629 char* title = getWindowsMenuEntry(windows[windowIndex]);
4630 XtVaSetValues(items[n], XmNlabelString,
4631 st1=XmStringCreateSimple(title), NULL);
4632 XtRemoveAllCallbacks(items[n], XmNactivateCallback);
4633 XtAddCallback(items[n], XmNactivateCallback,
4634 (XtCallbackProc)raiseCB, windows[windowIndex]);
4635 XmStringFree(st1);
4636 windowIndex++;
4641 /* Add new items for the titles of the remaining windows to the menu */
4642 for (; windowIndex<nWindows; windowIndex++) {
4643 XmString st1;
4644 char* title = getWindowsMenuEntry(windows[windowIndex]);
4645 Widget btn = XtVaCreateManagedWidget("win", xmPushButtonWidgetClass,
4646 window->windowMenuPane,
4647 XmNlabelString, st1=XmStringCreateSimple(title),
4648 XmNmarginHeight, 0,
4649 XmNuserData, TEMPORARY_MENU_ITEM, NULL);
4650 XtAddCallback(btn, XmNactivateCallback, (XtCallbackProc)raiseCB,
4651 windows[windowIndex]);
4652 XmStringFree(st1);
4654 XtFree((char *)windows);
4656 /* if the menu is torn off, we need to manually adjust the
4657 dimension of the menuShell _before_ re-managing the menu
4658 pane, to either expose the hidden menu entries or remove
4659 the empty space */
4660 if (!XmIsMenuShell(XtParent(window->windowMenuPane))) {
4661 Dimension width, height;
4663 XtVaGetValues(window->windowMenuPane, XmNwidth, &width,
4664 XmNheight, &height, NULL);
4665 XtVaSetValues(XtParent(window->windowMenuPane), XmNwidth, width,
4666 XmNheight, height, NULL);
4667 XtManageChild(window->windowMenuPane);
4672 ** Update the Previously Opened Files menu of a single window to reflect the
4673 ** current state of the list as retrieved from FIXME.
4674 ** Thanks to Markus Schwarzenberg for the sorting part.
4676 static void updatePrevOpenMenu(WindowInfo *window)
4678 Widget btn;
4679 WidgetList items;
4680 Cardinal nItems;
4681 int n, index;
4682 XmString st1;
4683 char **prevOpenSorted;
4685 /* Read history file to get entries written by other sessions. */
4686 ReadNEditDB();
4688 /* Sort the previously opened file list if requested */
4689 prevOpenSorted = (char **)XtMalloc(NPrevOpen * sizeof(char*));
4690 memcpy(prevOpenSorted, PrevOpen, NPrevOpen * sizeof(char*));
4691 if (GetPrefSortOpenPrevMenu())
4692 qsort(prevOpenSorted, NPrevOpen, sizeof(char*), cmpStrPtr);
4694 /* Go thru all of the items in the menu and rename them to match the file
4695 list. In older Motifs (particularly ibm), it was dangerous to replace
4696 a whole menu pane, which would be much simpler. However, since the
4697 code was already written for the Windows menu and is well tested, I'll
4698 stick with this weird method of re-naming the items */
4699 XtVaGetValues(window->prevOpenMenuPane, XmNchildren, &items,
4700 XmNnumChildren, &nItems, NULL);
4701 index = 0;
4702 for (n=0; n<(int)nItems; n++) {
4703 if (index >= NPrevOpen) {
4704 /* unmanaging before destroying stops parent from displaying */
4705 XtUnmanageChild(items[n]);
4706 XtDestroyWidget(items[n]);
4707 } else {
4708 XtVaSetValues(items[n], XmNlabelString,
4709 st1=XmStringCreateSimple(prevOpenSorted[index]), NULL);
4710 XtRemoveAllCallbacks(items[n], XmNactivateCallback);
4711 XtAddCallback(items[n], XmNactivateCallback,
4712 (XtCallbackProc)openPrevCB, prevOpenSorted[index]);
4713 XmStringFree(st1);
4714 index++;
4718 /* Add new items for the remaining file names to the menu */
4719 for (; index<NPrevOpen; index++) {
4720 btn = XtVaCreateManagedWidget("win", xmPushButtonWidgetClass,
4721 window->prevOpenMenuPane,
4722 XmNlabelString, st1=XmStringCreateSimple(prevOpenSorted[index]),
4723 XmNmarginHeight, 0,
4724 XmNuserData, TEMPORARY_MENU_ITEM, NULL);
4725 XtAddCallback(btn, XmNactivateCallback, (XtCallbackProc)openPrevCB,
4726 prevOpenSorted[index]);
4727 XmStringFree(st1);
4730 XtFree((char*)prevOpenSorted);
4734 ** This function manages the display of the Tags File Menu, which is displayed
4735 ** when the user selects Un-load Tags File.
4737 static void updateTagsFileMenu(WindowInfo *window)
4739 tagFile *tf;
4740 Widget btn;
4741 WidgetList items;
4742 Cardinal nItems;
4743 int n;
4744 XmString st1;
4746 /* Go thru all of the items in the menu and rename them to match the file
4747 list. In older Motifs (particularly ibm), it was dangerous to replace
4748 a whole menu pane, which would be much simpler. However, since the
4749 code was already written for the Windows menu and is well tested, I'll
4750 stick with this weird method of re-naming the items */
4751 XtVaGetValues(window->unloadTagsMenuPane, XmNchildren, &items,
4752 XmNnumChildren, &nItems, NULL);
4753 tf = TagsFileList;
4754 for (n=0; n<(int)nItems; n++) {
4755 if (!tf) {
4756 /* unmanaging before destroying stops parent from displaying */
4757 XtUnmanageChild(items[n]);
4758 XtDestroyWidget(items[n]);
4759 } else {
4760 XtVaSetValues(items[n], XmNlabelString,
4761 st1=XmStringCreateSimple(tf->filename), NULL);
4762 XtRemoveAllCallbacks(items[n], XmNactivateCallback);
4763 XtAddCallback(items[n], XmNactivateCallback,
4764 (XtCallbackProc)unloadTagsFileCB, tf->filename);
4765 XmStringFree(st1);
4766 tf = tf->next;
4770 /* Add new items for the remaining file names to the menu */
4771 while (tf) {
4772 btn = XtVaCreateManagedWidget("win", xmPushButtonWidgetClass,
4773 window->unloadTagsMenuPane, XmNlabelString,
4774 st1=XmStringCreateSimple(tf->filename),XmNmarginHeight, 0,
4775 XmNuserData, TEMPORARY_MENU_ITEM, NULL);
4776 XtAddCallback(btn, XmNactivateCallback,
4777 (XtCallbackProc)unloadTagsFileCB, tf->filename);
4778 XmStringFree(st1);
4779 tf = tf->next;
4784 ** This function manages the display of the Tips File Menu, which is displayed
4785 ** when the user selects Un-load Calltips File.
4787 static void updateTipsFileMenu(WindowInfo *window)
4789 tagFile *tf;
4790 Widget btn;
4791 WidgetList items;
4792 Cardinal nItems;
4793 int n;
4794 XmString st1;
4796 /* Go thru all of the items in the menu and rename them to match the file
4797 list. In older Motifs (particularly ibm), it was dangerous to replace
4798 a whole menu pane, which would be much simpler. However, since the
4799 code was already written for the Windows menu and is well tested, I'll
4800 stick with this weird method of re-naming the items */
4801 XtVaGetValues(window->unloadTipsMenuPane, XmNchildren, &items,
4802 XmNnumChildren, &nItems, NULL);
4803 tf = TipsFileList;
4804 for (n=0; n<(int)nItems; n++) {
4805 if (!tf) {
4806 /* unmanaging before destroying stops parent from displaying */
4807 XtUnmanageChild(items[n]);
4808 XtDestroyWidget(items[n]);
4809 } else {
4810 XtVaSetValues(items[n], XmNlabelString,
4811 st1=XmStringCreateSimple(tf->filename), NULL);
4812 XtRemoveAllCallbacks(items[n], XmNactivateCallback);
4813 XtAddCallback(items[n], XmNactivateCallback,
4814 (XtCallbackProc)unloadTipsFileCB, tf->filename);
4815 XmStringFree(st1);
4816 tf = tf->next;
4820 /* Add new items for the remaining file names to the menu */
4821 while (tf) {
4822 btn = XtVaCreateManagedWidget("win", xmPushButtonWidgetClass,
4823 window->unloadTipsMenuPane, XmNlabelString,
4824 st1=XmStringCreateSimple(tf->filename),XmNmarginHeight, 0,
4825 XmNuserData, TEMPORARY_MENU_ITEM, NULL);
4826 XtAddCallback(btn, XmNactivateCallback,
4827 (XtCallbackProc)unloadTipsFileCB, tf->filename);
4828 XmStringFree(st1);
4829 tf = tf->next;
4834 ** Comparison function for sorting file names for the Open Previous submenu
4836 static int cmpStrPtr(const void *strA, const void *strB)
4838 return strcmp(*((char**)strA), *((char**)strB));
4841 #ifdef VMS
4842 static char neditDBBadFilenameChars[] = "\n\t*?(){}!@#%&' ";
4843 #else
4844 static char neditDBBadFilenameChars[] = "\n";
4845 #endif
4848 ** Write dynamic database of file names for "Open Previous". Eventually,
4849 ** this may hold window positions, and possibly file marks, in which case,
4850 ** it should be moved to a different module, but for now it's just a list
4851 ** of previously opened files.
4853 void WriteNEditDB(void)
4855 const char* fullName = GetRCFileName(NEDIT_HISTORY);
4856 FILE *fp;
4857 int i;
4858 static char fileHeader[] =
4859 "# File name database for NEdit Open Previous command\n";
4861 if (fullName == NULL) {
4862 /* GetRCFileName() might return NULL if an error occurs during
4863 creation of the preference file directory. */
4864 return;
4867 /* If the Open Previous command is disabled, just return */
4868 if (GetPrefMaxPrevOpenFiles() < 1) {
4869 return;
4872 /* open the file */
4873 if ((fp = fopen(fullName, "w")) == NULL) {
4874 #ifdef VMS
4875 /* When the version number, ";1" is specified as part of the file
4876 name, fopen(fullName, "w"), will only open for writing if the
4877 file does not exist. Using, fopen(fullName, "r+"), opens an
4878 existing file for "update" - read/write pointer is placed at the
4879 beginning of file.
4880 By calling ftruncate(), we discard the old contents and avoid
4881 trailing garbage in the file if the new contents is shorter. */
4882 if ((fp = fopen(fullName, "r+")) == NULL) {
4883 return;
4885 if (ftruncate(fileno(fp), 0) != 0) {
4886 fclose(fp);
4887 return;
4889 #else
4890 return;
4891 #endif
4894 /* write the file header text to the file */
4895 fprintf(fp, "%s", fileHeader);
4897 /* Write the list of file names */
4898 for (i = 0; i < NPrevOpen; ++i) {
4899 size_t lineLen = strlen(PrevOpen[i]);
4901 if (lineLen > 0 && PrevOpen[i][0] != '#' &&
4902 strcspn(PrevOpen[i], neditDBBadFilenameChars) == lineLen) {
4903 fprintf(fp, "%s\n", PrevOpen[i]);
4907 fclose(fp);
4911 ** Read database of file names for 'Open Previous' submenu.
4913 ** Eventually, this may hold window positions, and possibly file marks (in
4914 ** which case it should be moved to a different module) but for now it's
4915 ** just a list of previously opened files.
4917 ** This list is read once at startup and potentially refreshed before a
4918 ** new entry is about to be written to the file or before the menu is
4919 ** displayed. If the file is modified since the last read (or not read
4920 ** before), it is read in, otherwise nothing is done.
4922 void ReadNEditDB(void)
4924 const char *fullName = GetRCFileName(NEDIT_HISTORY);
4925 char line[MAXPATHLEN + 2];
4926 char *nameCopy;
4927 struct stat attribute;
4928 FILE *fp;
4929 size_t lineLen;
4930 static time_t lastNeditdbModTime = 0;
4932 /* If the Open Previous command is disabled or the user set the
4933 resource to an (invalid) negative value, just return. */
4934 if (GetPrefMaxPrevOpenFiles() < 1) {
4935 return;
4938 /* Initialize the files list and allocate a (permanent) block memory
4939 of the size prescribed by the maxPrevOpenFiles resource */
4940 if (!PrevOpen) {
4941 PrevOpen = (char**) XtMalloc(sizeof(char*) * GetPrefMaxPrevOpenFiles());
4942 NPrevOpen = 0;
4945 /* Don't move this check ahead of the previous statements. PrevOpen
4946 must be initialized at all times. */
4947 if (fullName == NULL)
4949 /* GetRCFileName() might return NULL if an error occurs during
4950 creation of the preference file directory. */
4951 return;
4954 /* Stat history file to see whether someone touched it after this
4955 session last changed it. */
4956 if (0 == stat(fullName, &attribute)) {
4957 if (lastNeditdbModTime >= attribute.st_mtime) {
4958 /* Do nothing, history file is unchanged. */
4959 return;
4960 } else {
4961 /* Memorize modtime to compare to next time. */
4962 lastNeditdbModTime = attribute.st_mtime;
4964 } else {
4965 /* stat() failed, probably for non-exiting history database. */
4966 if (ENOENT != errno)
4968 perror("nedit: Error reading history database");
4970 return;
4973 /* open the file */
4974 if ((fp = fopen(fullName, "r")) == NULL) {
4975 return;
4978 /* Clear previous list. */
4979 while (0 != NPrevOpen) {
4980 XtFree(PrevOpen[--NPrevOpen]);
4983 /* read lines of the file, lines beginning with # are considered to be
4984 comments and are thrown away. Lines are subject to cursory checking,
4985 then just copied to the Open Previous file menu list */
4986 while (True) {
4987 if (fgets(line, sizeof(line), fp) == NULL) {
4988 /* end of file */
4989 fclose(fp);
4990 return;
4992 if (line[0] == '#') {
4993 /* comment */
4994 continue;
4996 lineLen = strlen(line);
4997 if (lineLen == 0) {
4998 /* blank line */
4999 continue;
5001 if (line[lineLen - 1] != '\n') {
5002 /* no newline, probably truncated */
5003 fprintf(stderr, "nedit: Line too long in history file\n");
5004 while (fgets(line, sizeof(line), fp) != NULL) {
5005 lineLen = strlen(line);
5006 if (lineLen > 0 && line[lineLen - 1] == '\n') {
5007 break;
5010 continue;
5012 line[--lineLen] = '\0';
5013 if (strcspn(line, neditDBBadFilenameChars) != lineLen) {
5014 /* non-filename characters */
5015 fprintf(stderr, "nedit: History file may be corrupted\n");
5016 continue;
5018 nameCopy = XtMalloc(lineLen + 1);
5019 strcpy(nameCopy, line);
5020 PrevOpen[NPrevOpen++] = nameCopy;
5021 if (NPrevOpen >= GetPrefMaxPrevOpenFiles()) {
5022 /* too many entries */
5023 fclose(fp);
5024 return;
5029 static void setWindowSizeDefault(int rows, int cols)
5031 SetPrefRows(rows);
5032 SetPrefCols(cols);
5033 updateWindowSizeMenus();
5036 static void updateWindowSizeMenus(void)
5038 WindowInfo *win;
5040 for (win=WindowList; win!=NULL; win=win->next)
5041 updateWindowSizeMenu(win);
5044 static void updateWindowSizeMenu(WindowInfo *win)
5046 int rows = GetPrefRows(), cols = GetPrefCols();
5047 char title[50];
5048 XmString st1;
5050 if (!IsTopDocument(win))
5051 return;
5053 XmToggleButtonSetState(win->size24x80DefItem, rows==24&&cols==80,False);
5054 XmToggleButtonSetState(win->size40x80DefItem, rows==40&&cols==80,False);
5055 XmToggleButtonSetState(win->size60x80DefItem, rows==60&&cols==80,False);
5056 XmToggleButtonSetState(win->size80x80DefItem, rows==80&&cols==80,False);
5057 if ((rows!=24 && rows!=40 && rows!=60 && rows!=80) || cols!=80) {
5058 XmToggleButtonSetState(win->sizeCustomDefItem, True, False);
5059 sprintf(title, "Custom... (%d x %d)", rows, cols);
5060 XtVaSetValues(win->sizeCustomDefItem,
5061 XmNlabelString, st1=XmStringCreateSimple(title), NULL);
5062 XmStringFree(st1);
5063 } else {
5064 XmToggleButtonSetState(win->sizeCustomDefItem, False, False);
5065 XtVaSetValues(win->sizeCustomDefItem,
5066 XmNlabelString, st1=XmStringCreateSimple("Custom..."), NULL);
5067 XmStringFree(st1);
5072 ** Scans action argument list for arguments "forward" or "backward" to
5073 ** determine search direction for search and replace actions. "ignoreArgs"
5074 ** tells the routine how many required arguments there are to ignore before
5075 ** looking for keywords
5077 static int searchDirection(int ignoreArgs, String *args, Cardinal *nArgs)
5079 int i;
5081 for (i=ignoreArgs; i<(int)*nArgs; i++) {
5082 if (!strCaseCmp(args[i], "forward"))
5083 return SEARCH_FORWARD;
5084 if (!strCaseCmp(args[i], "backward"))
5085 return SEARCH_BACKWARD;
5087 return SEARCH_FORWARD;
5091 ** Scans action argument list for arguments "keep" or "nokeep" to
5092 ** determine whether to keep dialogs up for search and replace. "ignoreArgs"
5093 ** tells the routine how many required arguments there are to ignore before
5094 ** looking for keywords
5096 static int searchKeepDialogs(int ignoreArgs, String *args, Cardinal *nArgs)
5098 int i;
5100 for (i=ignoreArgs; i<(int)*nArgs; i++) {
5101 if (!strCaseCmp(args[i], "keep"))
5102 return TRUE;
5103 if (!strCaseCmp(args[i], "nokeep"))
5104 return FALSE;
5106 return GetPrefKeepSearchDlogs();
5110 ** Scans action argument list for arguments "wrap" or "nowrap" to
5111 ** determine search direction for search and replace actions. "ignoreArgs"
5112 ** tells the routine how many required arguments there are to ignore before
5113 ** looking for keywords
5115 static int searchWrap(int ignoreArgs, String *args, Cardinal *nArgs)
5117 int i;
5119 for (i=ignoreArgs; i<(int)*nArgs; i++) {
5120 if (!strCaseCmp(args[i], "wrap"))
5121 return(TRUE);
5122 if (!strCaseCmp(args[i], "nowrap"))
5123 return(FALSE);
5125 return GetPrefSearchWraps();
5129 ** Scans action argument list for arguments "literal", "case" or "regex" to
5130 ** determine search type for search and replace actions. "ignoreArgs"
5131 ** tells the routine how many required arguments there are to ignore before
5132 ** looking for keywords
5134 static int searchType(int ignoreArgs, String *args, Cardinal *nArgs)
5136 int i, tmpSearchType;
5138 for (i=ignoreArgs; i<(int)*nArgs; i++) {
5139 if (StringToSearchType(args[i], &tmpSearchType))
5140 return tmpSearchType;
5142 return GetPrefSearch();
5146 ** Return a pointer to the string describing search direction for search action
5147 ** routine parameters given a callback XmAnyCallbackStruct pointed to by
5148 ** "callData", by checking if the shift key is pressed (for search callbacks).
5150 static char **shiftKeyToDir(XtPointer callData)
5152 static char *backwardParam[1] = {"backward"};
5153 static char *forwardParam[1] = {"forward"};
5154 if (((XmAnyCallbackStruct *)callData)->event->xbutton.state & ShiftMask)
5155 return backwardParam;
5156 return forwardParam;
5159 static void raiseCB(Widget w, WindowInfo *window, caddr_t callData)
5161 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
5162 ((XmAnyCallbackStruct *)callData)->event);
5163 RaiseFocusDocumentWindow(window, True /* always focus */);
5166 static void openPrevCB(Widget w, char *name, caddr_t callData)
5168 char *params[1];
5169 Widget menu = MENU_WIDGET(w);
5171 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
5172 ((XmAnyCallbackStruct *)callData)->event);
5173 params[0] = name;
5174 XtCallActionProc(WidgetToWindow(menu)->lastFocus, "open",
5175 ((XmAnyCallbackStruct *)callData)->event, params, 1);
5176 CheckCloseDim();
5179 static void unloadTagsFileCB(Widget w, char *name, caddr_t callData)
5181 char *params[1];
5182 Widget menu = MENU_WIDGET(w);
5184 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
5185 ((XmAnyCallbackStruct *)callData)->event);
5186 params[0] = name;
5187 XtCallActionProc(WidgetToWindow(menu)->lastFocus, "unload_tags_file",
5188 ((XmAnyCallbackStruct *)callData)->event, params, 1);
5191 static void unloadTipsFileCB(Widget w, char *name, caddr_t callData)
5193 char *params[1];
5194 #if XmVersion >= 1002
5195 Widget menu = XmGetPostedFromWidget(XtParent(w)); /* If menu is torn off */
5196 #else
5197 Widget menu = w;
5198 #endif
5200 params[0] = name;
5201 XtCallActionProc(WidgetToWindow(menu)->lastFocus, "unload_tips_file",
5202 ((XmAnyCallbackStruct *)callData)->event, params, 1);
5206 ** strCaseCmp compares its arguments and returns 0 if the two strings
5207 ** are equal IGNORING case differences. Otherwise returns 1.
5209 static int strCaseCmp(const char *str1, const char *str2)
5211 const char *c1, *c2;
5213 for (c1=str1, c2=str2; *c1!='\0' && *c2!='\0'; c1++, c2++)
5214 if (toupper((unsigned char)*c1) != toupper((unsigned char)*c2))
5215 return 1;
5216 if (*c1 == *c2) {
5217 return(0);
5219 else {
5220 return(1);
5225 ** Comparison function for sorting windows by title for the window menu.
5226 ** Windows are sorted by Untitled and then alphabetically by filename and
5227 ** then alphabetically by path.
5229 static int compareWindowNames(const void *windowA, const void *windowB)
5231 int rc;
5232 const WindowInfo *a = *((WindowInfo**)windowA);
5233 const WindowInfo *b = *((WindowInfo**)windowB);
5234 /* Untitled first */
5235 rc = a->filenameSet == b->filenameSet ? 0 :
5236 a->filenameSet && !b->filenameSet ? 1 : -1;
5237 if (rc != 0)
5238 return rc;
5239 rc = strcmp(a->filename, b->filename);
5240 if (rc != 0)
5241 return rc;
5242 rc = strcmp(a->path, b->path);
5243 return rc;
5247 ** Create popup for right button programmable menu
5249 Widget CreateBGMenu(WindowInfo *window)
5251 Arg args[1];
5253 /* There is still some mystery here. It's important to get the XmNmenuPost
5254 resource set to the correct menu button, or the menu will not post
5255 properly, but there's also some danger that it will take over the entire
5256 button and interfere with text widget translations which use the button
5257 with modifiers. I don't entirely understand why it works properly now
5258 when it failed often in development, and certainly ignores the ~ syntax
5259 in translation event specifications. */
5260 XtSetArg(args[0], XmNmenuPost, GetPrefBGMenuBtn());
5261 return CreatePopupMenu(window->textArea, "bgMenu", args, 1);
5265 ** Create context popup menu for tabs & tab bar
5267 Widget CreateTabContextMenu(Widget parent, WindowInfo *window)
5269 Widget menu;
5270 Arg args[8];
5271 int n;
5273 n = 0;
5274 XtSetArg(args[n], XmNtearOffModel, XmTEAR_OFF_DISABLED); n++;
5275 menu = CreatePopupMenu(parent, "tabContext", args, n);
5277 createMenuItem(menu, "new", "New Tab", 0, doTabActionCB, "new_tab", SHORT);
5278 createMenuItem(menu, "close", "Close Tab", 0, doTabActionCB, "close", SHORT);
5279 createMenuSeparator(menu, "sep1", SHORT);
5280 window->contextDetachDocumentItem = createMenuItem(menu, "detach",
5281 "Detach Tab", 0, doTabActionCB, "detach_document", SHORT);
5282 XtSetSensitive(window->contextDetachDocumentItem, False);
5283 window->contextMoveDocumentItem = createMenuItem(menu, "attach",
5284 "Move Tab To...", 0, doTabActionCB, "move_document_dialog", SHORT);
5286 return menu;
5290 ** Add a translation to the text widget to trigger the background menu using
5291 ** the mouse-button + modifier combination specified in the resource:
5292 ** nedit.bgMenuBtn.
5294 void AddBGMenuAction(Widget widget)
5296 static XtTranslations table = NULL;
5298 if (table == NULL) {
5299 char translations[MAX_ACCEL_LEN + 25];
5300 sprintf(translations, "%s: post_window_bg_menu()\n",GetPrefBGMenuBtn());
5301 table = XtParseTranslationTable(translations);
5303 XtOverrideTranslations(widget, table);
5306 static void bgMenuPostAP(Widget w, XEvent *event, String *args,
5307 Cardinal *nArgs)
5309 WindowInfo *window = WidgetToWindow(w);
5311 /* The Motif popup handling code BLOCKS events while the menu is posted,
5312 including the matching btn-up events which complete various dragging
5313 operations which it may interrupt. Cancel to head off problems */
5314 XtCallActionProc(window->lastFocus, "process_cancel", event, NULL, 0);
5316 /* Pop up the menu */
5317 XmMenuPosition(window->bgMenuPane, (XButtonPressedEvent *)event);
5318 XtManageChild(window->bgMenuPane);
5321 These statements have been here for a very long time, but seem
5322 unnecessary and are even dangerous: when any of the lock keys are on,
5323 Motif thinks it shouldn't display the background menu, but this
5324 callback is called anyway. When we then grab the focus and force the
5325 menu to be drawn, bad things can happen (like a total lockup of the X
5326 server).
5328 XtPopup(XtParent(window->bgMenuPane), XtGrabNonexclusive);
5329 XtMapWidget(XtParent(window->bgMenuPane));
5330 XtMapWidget(window->bgMenuPane);
5334 void AddTabContextMenuAction(Widget widget)
5336 static XtTranslations table = NULL;
5338 if (table == NULL) {
5339 char *translations = "<Btn3Down>: post_tab_context_menu()\n";
5340 table = XtParseTranslationTable(translations);
5342 XtOverrideTranslations(widget, table);
5346 ** action procedure for posting context menu of tabs
5348 static void tabMenuPostAP(Widget w, XEvent *event, String *args,
5349 Cardinal *nArgs)
5351 WindowInfo *window;
5352 XButtonPressedEvent *xbutton = (XButtonPressedEvent *)event;
5353 Widget wgt;
5355 /* Determine if the context menu was called from tabs or gutter,
5356 then stored the corresponding window info as userData of
5357 the popup menu pane, which will later be extracted by
5358 doTabActionCB() to act upon. When the context menu was called
5359 from the gutter, the active doc is assumed.
5361 Lesstif requires the action [to pupop the menu] to also be
5362 to the tabs, else nothing happed when right-click on tabs.
5363 Even so, the action procedure sometime appear to be called
5364 from the gutter even if users did right-click on the tabs.
5365 Here we try to cater for the uncertainty. */
5366 if (XtClass(w) == xrwsBubbleButtonWidgetClass)
5367 window = TabToWindow(w);
5368 else if (xbutton->subwindow) {
5369 wgt = XtWindowToWidget(XtDisplay(w), xbutton->subwindow);
5370 window = TabToWindow(wgt);
5372 else {
5373 window = WidgetToWindow(w);
5375 XtVaSetValues(window->tabMenuPane, XmNuserData, (XtPointer)window, NULL);
5377 /* The Motif popup handling code BLOCKS events while the menu is posted,
5378 including the matching btn-up events which complete various dragging
5379 operations which it may interrupt. Cancel to head off problems */
5380 XtCallActionProc(window->lastFocus, "process_cancel", event, NULL, 0);
5382 /* Pop up the menu */
5383 XmMenuPosition(window->tabMenuPane, (XButtonPressedEvent *)event);
5384 XtManageChild(window->tabMenuPane);
5388 ** Event handler for restoring the input hint of menu tearoffs
5389 ** previously disabled in ShowHiddenTearOff()
5391 static void tearoffMappedCB(Widget w, XtPointer clientData, XUnmapEvent *event)
5393 Widget shell = (Widget)clientData;
5394 XWMHints *wmHints;
5396 if (event->type != MapNotify)
5397 return;
5399 /* restore the input hint previously disabled in ShowHiddenTearOff() */
5400 wmHints = XGetWMHints(TheDisplay, XtWindow(shell));
5401 wmHints->input = True;
5402 wmHints->flags |= InputHint;
5403 XSetWMHints(TheDisplay, XtWindow(shell), wmHints);
5404 XFree(wmHints);
5406 /* we only need to do this only */
5407 XtRemoveEventHandler(shell, StructureNotifyMask, False,
5408 (XtEventHandler)tearoffMappedCB, shell);
5412 ** Redisplay (map) a hidden tearoff
5414 void ShowHiddenTearOff(Widget menuPane)
5416 Widget shell;
5418 if (!menuPane)
5419 return;
5421 shell = XtParent(menuPane);
5422 if (!XmIsMenuShell(shell)) {
5423 XWindowAttributes winAttr;
5425 XGetWindowAttributes(XtDisplay(shell), XtWindow(shell), &winAttr);
5426 if (winAttr.map_state == IsUnmapped) {
5427 XWMHints *wmHints;
5429 /* to workaround a problem where the remapped tearoffs
5430 always receive the input focus insteads of the text
5431 editing window, we disable the input hint of the
5432 tearoff shell temporarily. */
5433 wmHints = XGetWMHints(XtDisplay(shell), XtWindow(shell));
5434 wmHints->input = False;
5435 wmHints->flags |= InputHint;
5436 XSetWMHints(XtDisplay(shell), XtWindow(shell), wmHints);
5437 XFree(wmHints);
5439 /* show the tearoff */
5440 XtMapWidget(shell);
5442 /* the input hint will be restored when the tearoff
5443 is mapped */
5444 XtAddEventHandler(shell, StructureNotifyMask, False,
5445 (XtEventHandler)tearoffMappedCB, shell);
5450 #ifdef SGI_CUSTOM
5451 static void shortMenusCB(Widget w, WindowInfo *window, caddr_t callData)
5453 WindowInfo *win;
5454 int i, state = XmToggleButtonGetState(w);
5455 Widget parent;
5457 window = WidgetToWindow(w);
5459 HidePointerOnKeyedEvent(WidgetToWindow(MENU_WIDGET(w))->lastFocus,
5460 ((XmAnyCallbackStruct *)callData)->event);
5461 /* Set the preference */
5462 SetPrefShortMenus(state);
5464 /* Re-create the menus for all windows */
5465 for (win=WindowList; win!=NULL; win=win->next) {
5466 for (i=0; i<win->nToggleShortItems; i++) {
5467 if (state)
5468 XtUnmanageChild(win->toggleShortItems[i]);
5469 else
5470 XtManageChild(win->toggleShortItems[i]);
5473 if (GetPrefShortMenus())
5474 SaveNEditPrefs(window->shell, True);
5477 static void addToToggleShortList(Widget w)
5479 if (ShortMenuWindow->nToggleShortItems >= MAX_SHORTENED_ITEMS) {
5480 fprintf(stderr,"nedit, internal error: increase MAX_SHORTENED_ITEMS\n");
5481 return;
5483 ShortMenuWindow->toggleShortItems[ShortMenuWindow->nToggleShortItems++] = w;
5487 ** Present the user a dialog for specifying whether or not a short
5488 ** menu mode preference should be applied toward the default setting.
5489 ** Return True if user requested to reset and save the default value.
5490 ** If operation was canceled, will return toggle widget "w" to it's
5491 ** original (opposite) state.
5493 static int shortPrefAskDefault(Widget parent, Widget w, const char *settingName)
5495 char msg[100] = "";
5497 if (!GetPrefShortMenus()) {
5498 return False;
5501 sprintf(msg, "%s: %s\nSave as default for future windows as well?",
5502 settingName, XmToggleButtonGetState(w) ? "On" : "Off");
5503 switch (DialogF (DF_QUES, parent, 3, "Save Default", msg, "Yes", "No",
5504 "Cancel"))
5506 case 1: /* yes */
5507 return True;
5508 case 2: /* no */
5509 return False;
5510 case 3: /* cancel */
5511 XmToggleButtonSetState(w, !XmToggleButtonGetState(w), False);
5512 return False;
5514 return False; /* not reached */
5516 #endif