1 /*
2 FXiTe - The Free eXtensIble Text Editor
3 Copyright (c) 2009-2013 Jeffrey Pohlmeyer <yetanothergeek@gmail.com>
4
5 This program is free software; you can redistribute it and/or modify it
6 under the terms of the GNU General Public License version 3 as
7 published by the Free Software Foundation.
8
9 This software is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
13
14 You should have received a copy of the GNU General Public License
15 along with this program; if not, write to the Free Software
16 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
17 */
18
19
20 #include <fx.h>
21 #include <SciLexer.h>
22
23 #include "prefs_base.h"
24 #include "shmenu.h"
25 #include "lang.h"
26 #include "menuspec.h"
27 #include "appwin.h"
28
29 #include "intl.h"
30 #include "mainmenu.h"
31
32 #define TEST_SOMETHING 0
33
34 #define TW TopWindow
35
36 // Create a new menu command, menu check box, or menu radio item...
37 #define MkMnuCmd(p,s) MenuMgr::MakeMenuCommand(p,tw,TW::s,'m')
38 #define MkMnuChk(p,s,c) ((FXMenuCheck*)MenuMgr::MakeMenuCommand(p,tw,TW::s,'k',c))
39 #define MkMnuRad(p,s) ((FXMenuRadio*)MenuMgr::MakeMenuCommand(p,tw,TW::s,'r'))
40
41
42
43 static const char*usercmdflags[]={
44 "save", _("Save open files first."),
45 NULL
46 };
47
48
49 static const char*usersnipflags[]={
50 "read", _("Insert file's contents."),
51 "exec", _("Insert command output."),
52 NULL
53 };
54
55
MainMenu(FXComposite * p)56 MainMenu::MainMenu(FXComposite* p):FXMenuBar(p,LAYOUT_SIDE_TOP|LAYOUT_FILL_X)
57 {
58 tw=(TopWindow*)p;
59 prefs=SettingsBase::instance();
60 CreateMenus();
61 new FXHorizontalSeparator(p,LAYOUT_SIDE_TOP|LAYOUT_FILL_X|SEPARATOR_GROOVE);
62 }
63
64
65 /*
66 Fox menus don't re-focus the previously active widget after they are dismissed.
67 This sub-class helps to work around that.
68 */
69 class MyMenuPane: public FXMenuPane {
70 FXDECLARE(MyMenuPane)
MyMenuPane()71 MyMenuPane(){}
72 public:
MyMenuPane(FXComposite * o)73 MyMenuPane(FXComposite*o):FXMenuPane(o) {}
onCmdUnpost(FXObject * o,FXSelector sel,void * p)74 long onCmdUnpost(FXObject*o, FXSelector sel, void*p ){
75 long rv=FXMenuPane::onCmdUnpost(o,sel,p);
76 getApp()->addChore(TopWindow::instance(),TopWindow::ID_FOCUS_DOC,NULL);
77 return rv;
78 }
79 };
80
81
82
83 FXDEFMAP(MyMenuPane) MyMenuPaneMap[] = {
84 FXMAPFUNC(SEL_COMMAND,FXWindow::ID_UNPOST,MyMenuPane::onCmdUnpost),
85 };
86
FXIMPLEMENT(MyMenuPane,FXMenuPane,MyMenuPaneMap,ARRAYNUMBER (MyMenuPaneMap))87 FXIMPLEMENT(MyMenuPane,FXMenuPane,MyMenuPaneMap,ARRAYNUMBER(MyMenuPaneMap))
88
89
90 void MainMenu::CreateLanguageMenu()
91 {
92 langmenu=new MyMenuPane(tw);
93 langcasc=new FXMenuCascade(viewmenu,_("&Language"),NULL,langmenu);
94 FXMenuRadio*mr;
95
96 cpp_langmenu=new MyMenuPane(langmenu);
97 cpp_langcasc=new FXMenuCascade(langmenu,_("C/C++"),NULL,cpp_langmenu);
98
99 scr_langmenu=new MyMenuPane(langmenu);
100 scr_langcasc=new FXMenuCascade(langmenu,_("Scripting"),NULL,scr_langmenu);
101
102 cfg_langmenu=new MyMenuPane(langmenu);
103 cfg_langcasc=new FXMenuCascade(langmenu,_("Config"),NULL,cfg_langmenu);
104
105 html_langmenu=new MyMenuPane(langmenu);
106 html_langcasc=new FXMenuCascade(langmenu,_("Web"),NULL,html_langmenu);
107
108 inf_langmenu=new MyMenuPane(langmenu);
109 inf_langcasc=new FXMenuCascade(langmenu,_("Info"),NULL,inf_langmenu);
110
111 lgcy_langmenu=new MyMenuPane(langmenu);
112 lgcy_langcasc=new FXMenuCascade(langmenu,_("Legacy"),NULL,lgcy_langmenu);
113
114 tex_langmenu=new MyMenuPane(langmenu);
115 tex_langcasc=new FXMenuCascade(langmenu,_("Typeset"),NULL,tex_langmenu);
116
117 db_langmenu=new MyMenuPane(langmenu);
118 db_langcasc=new FXMenuCascade(langmenu,_("Database"),NULL,db_langmenu);
119
120 asm_langmenu=new MyMenuPane(langmenu);
121 asm_langcasc=new FXMenuCascade(langmenu,_("Asm/HDL"),NULL,asm_langmenu);
122
123 misc_langmenu=new MyMenuPane(langmenu);
124 misc_langcasc=new FXMenuCascade(langmenu,_("Other"),NULL,misc_langmenu);
125
126 mr=new FXMenuRadio(misc_langmenu,_("none"),tw,TW::ID_SET_LANGUAGE);
127 mr->setUserData(NULL);
128
129 for (LangStyle*ls=languages; ls->name; ls++) {
130 FXMenuPane*mp;
131 switch (ls->id) {
132 case SCLEX_COBOL:
133 case SCLEX_F77:
134 case SCLEX_FORTRAN:
135 case SCLEX_FREEBASIC:
136 case SCLEX_PASCAL:
137 case SCLEX_SMALLTALK:
138 case SCLEX_ERLANG:
139 case SCLEX_LISP:
140 case SCLEX_HASKELL:
141 case SCLEX_MODULA:
142 case SCLEX_ADA: {
143 mp=lgcy_langmenu;
144 break;
145 }
146 case SCLEX_CSS:
147 case SCLEX_HTML:
148 case SCLEX_MARKDOWN:
149 case SCLEX_TXT2TAGS: {
150 mp=(compare(ls->name,"docbook")==0)?tex_langmenu:html_langmenu;
151 break;
152 }
153 case SCLEX_CPP: {
154 mp=(compare(ls->name,"javascript")==0)?html_langmenu:cpp_langmenu;
155 break;
156 }
157 case SCLEX_BASH:
158 case SCLEX_BATCH:
159 case SCLEX_LUA:
160 case SCLEX_PERL:
161 case SCLEX_PYTHON:
162 case SCLEX_RUBY:
163 case SCLEX_R:
164 case SCLEX_TCL: {
165 mp=scr_langmenu;
166 break;
167 }
168 case SCLEX_FLAGSHIP:
169 case SCLEX_SQL: {
170 mp=db_langmenu;
171 break;
172 }
173 case SCLEX_DIFF:
174 case SCLEX_ERRORLIST: {
175 mp=inf_langmenu;
176 break;
177 }
178 case SCLEX_CONF:
179 case SCLEX_CMAKE:
180 case SCLEX_MAKEFILE:
181 case SCLEX_PO:
182 case SCLEX_PROPERTIES:
183 case SCLEX_XML: {
184 mp=cfg_langmenu;
185 break;
186 }
187 case SCLEX_ASM:
188 case SCLEX_VHDL:
189 case SCLEX_VERILOG:
190 case SCLEX_A68K: {
191 mp=asm_langmenu;
192 break;
193 }
194 case SCLEX_LATEX:
195 case SCLEX_TEX:
196 case SCLEX_METAPOST:
197 case SCLEX_PS: {
198 mp=tex_langmenu;
199 break;
200 }
201 default: { mp=misc_langmenu; }
202 }
203 mr=new FXMenuRadio(mp,ls->name,tw,TW::ID_SET_LANGUAGE);
204 mr->setUserData((void*)ls);
205 }
206 }
207
208
209
NewTitle(FXComposite * p,const FXString & text,FXIcon * ic=NULL,FXPopup * pup=NULL,FXuint opts=0)210 static FXMenuTitle*NewTitle(FXComposite*p, const FXString&text, FXIcon*ic=NULL, FXPopup*pup=NULL, FXuint opts=0)
211 {
212 FXMenuTitle*rv=new FXMenuTitle(p, text, ic, pup, opts);
213 if (pup) { pup->setUserData((void*)rv); }
214 return rv;
215 }
216
217
218
NewCascade(FXComposite * p,const FXString & text,FXIcon * ic=NULL,FXPopup * pup=NULL,FXuint opts=0)219 static FXMenuCascade*NewCascade(FXComposite*p, const FXString&text, FXIcon*ic=NULL, FXPopup*pup=NULL, FXuint opts=0)
220 {
221 FXMenuCascade*rv=new FXMenuCascade(p, text, ic, pup, opts);
222 if (pup) { pup->setUserData((void*)rv); }
223 return rv;
224 }
225
226
227
CreateTabsMenu()228 void MainMenu::CreateTabsMenu()
229 {
230 tabmenu=new MyMenuPane(tw);
231 NewCascade(viewmenu,_("&Tabs"),NULL,tabmenu);
232
233 tabsidemenu=new MyMenuPane(tw);
234 NewCascade(tabmenu,_("&Position"),NULL,tabsidemenu);
235
236 FXMenuRadio*tT=MkMnuRad(tabsidemenu,ID_TABS_TOP);
237 FXMenuRadio*tB=MkMnuRad(tabsidemenu,ID_TABS_BOTTOM);
238 FXMenuRadio*tL=MkMnuRad(tabsidemenu,ID_TABS_LEFT);
239 FXMenuRadio*tR=MkMnuRad(tabsidemenu,ID_TABS_RIGHT);
240
241 switch (prefs->DocTabPosition) {
242 case 'B': { tB->setCheck(); break; }
243 case 'L': { tL->setCheck(); break; }
244 case 'R': { tR->setCheck(); break; }
245 default: { tT->setCheck(); break; }
246 }
247
248 tabwidthmenu=new MyMenuPane(tw);
249 NewCascade(tabmenu,_("&Width"),NULL,tabwidthmenu);
250
251 FXMenuRadio*tU=MkMnuRad(tabwidthmenu,ID_TABS_UNIFORM);
252 FXMenuRadio*tP=MkMnuRad(tabwidthmenu,ID_TABS_COMPACT);
253 FXMenuRadio*tA=MkMnuRad(tabwidthmenu,ID_TABS_BY_POS);
254 switch (prefs->DocTabsPacked) {
255 case 'U': { tU->setCheck(); break; }
256 case 'P': { tP->setCheck(); break; }
257 case 'A': { tA->setCheck(); break; }
258 }
259 }
260
261
262
CreateZoomMenu()263 void MainMenu::CreateZoomMenu()
264 {
265 viewzoommenu=new MyMenuPane(tw);
266 NewCascade(viewmenu,_("&Zoom"),NULL,viewzoommenu);
267 MkMnuCmd(viewzoommenu,ID_ZOOM_IN);
268 MkMnuCmd(viewzoommenu,ID_ZOOM_OUT);
269 MkMnuCmd(viewzoommenu,ID_ZOOM_NONE);
270 MkMnuCmd(viewzoommenu,ID_ZOOM_NEAR);
271 MkMnuCmd(viewzoommenu,ID_ZOOM_FAR);
272 }
273
274
275
CreateMenus()276 void MainMenu::CreateMenus()
277 {
278 filemenu=new MyMenuPane(tw);
279 NewTitle(this,_("&File"),NULL,filemenu);
280 MkMnuCmd(filemenu,ID_NEW);
281 MkMnuCmd(filemenu,ID_OPEN_FILES);
282 openselmenu=MkMnuCmd(filemenu,ID_OPEN_SELECTED);
283 recent_files=new HistMenu(filemenu, _("Open pre&vious"), "RecentFiles", tw, TW::ID_OPEN_PREVIOUS);
284
285 new FXMenuSeparator(filemenu, 0);
286 MkMnuCmd(filemenu,ID_SAVE);
287 MkMnuCmd(filemenu,ID_SAVEAS);
288 MkMnuCmd(filemenu,ID_SAVEALL);
289 MkMnuCmd(filemenu,ID_SAVECOPY);
290
291 new FXMenuSeparator(filemenu, 0);
292 MkMnuCmd(filemenu,ID_RELOAD);
293
294 fileexportmenu=new MyMenuPane(tw);
295 NewCascade(filemenu,_("E&xport"),NULL,fileexportmenu);
296 MkMnuCmd(fileexportmenu,ID_EXPORT_PDF);
297 MkMnuCmd(fileexportmenu,ID_EXPORT_HTML);
298
299 new FXMenuSeparator(filemenu, 0);
300 MkMnuCmd(filemenu,ID_CLOSE);
301 MkMnuCmd(filemenu,ID_CLOSEALL);
302 new FXMenuSeparator(filemenu, 0);
303 MkMnuCmd(filemenu,ID_INSERT_FILE);
304 MkMnuCmd(filemenu,ID_LOAD_TAGS);
305 unloadtagsmenu=new FXMenuCascade(filemenu,_("&Unload tags file"),NULL,(new MyMenuPane(filemenu)));
306 unloadtagsmenu->disable();
307 MkMnuCmd(filemenu,ID_SELECT_DIR);
308 new FXMenuSeparator(filemenu, 0);
309 MkMnuCmd(filemenu,ID_QUIT);
310
311 editmenu=new MyMenuPane(tw);
312 NewTitle(this,_("&Edit"),NULL,editmenu);
313
314 MkMnuCmd(editmenu,ID_UNDO);
315 MkMnuCmd(editmenu,ID_REDO);
316 new FXMenuSeparator(editmenu, 0);
317 MkMnuCmd(editmenu,ID_CUT);
318 MkMnuCmd(editmenu,ID_COPY);
319 MkMnuCmd(editmenu,ID_PASTE);
320
321 editdeletemenu=new MyMenuPane(tw);
322 NewCascade(editmenu,_("&Delete"),NULL,editdeletemenu);
323
324 MkMnuCmd(editdeletemenu,ID_DEL_WORD_LEFT);
325 MkMnuCmd(editdeletemenu,ID_DEL_WORD_RIGHT);
326 MkMnuCmd(editdeletemenu,ID_DEL_LINE_LEFT);
327 MkMnuCmd(editdeletemenu,ID_DEL_LINE_RIGHT);
328
329 new FXMenuSeparator(editmenu, 0);
330 MkMnuCmd(editmenu,ID_TOLOWER);
331 MkMnuCmd(editmenu,ID_TOUPPER);
332
333 editindentmenu=new MyMenuPane(tw);
334 NewCascade(editmenu,_("&Indent"),NULL,editindentmenu);
335
336 MkMnuCmd(editindentmenu,ID_INDENT_STEP);
337 MkMnuCmd(editindentmenu,ID_UNINDENT_STEP);
338 MkMnuCmd(editindentmenu,ID_INDENT_FULL);
339 MkMnuCmd(editindentmenu,ID_UNINDENT_FULL);
340
341 new FXMenuSeparator(editmenu, 0);
342 readonly_chk=MkMnuChk(editmenu,ID_READONLY,false);
343 wordwrap_chk=MkMnuChk(editmenu,ID_WORDWRAP,false);
344
345 fileformatmenu=new MyMenuPane(tw);
346 fileformatcasc=NewCascade(editmenu,_("File &Format"),NULL,fileformatmenu);
347
348 fmt_dos_mnu=MkMnuRad(fileformatmenu,ID_FMT_DOS);
349 fmt_mac_mnu=MkMnuRad(fileformatmenu,ID_FMT_MAC);
350 fmt_unx_mnu=MkMnuRad(fileformatmenu,ID_FMT_UNIX);
351
352 MkMnuCmd(editmenu,ID_PREFS_DIALOG);
353
354 searchmenu=new MyMenuPane(tw);
355 NewTitle(this,_("&Search"),NULL,searchmenu);
356
357 MkMnuCmd(searchmenu,ID_FIND);
358 MkMnuCmd(searchmenu,ID_FINDNEXT);
359 MkMnuCmd(searchmenu,ID_FINDPREV);
360
361 searchselectmenu=new MyMenuPane(tw);
362 NewCascade(searchmenu,_("Find &Selected"),NULL,searchselectmenu);
363 MkMnuCmd(searchselectmenu,ID_NEXT_SELECTED);
364 MkMnuCmd(searchselectmenu,ID_PREV_SELECTED);
365 MkMnuCmd(searchmenu,ID_REPLACE_IN_DOC);
366
367 new FXMenuSeparator(searchmenu, 0);
368 MkMnuCmd(searchmenu,ID_GOTO);
369 MkMnuCmd(searchmenu,ID_GOTO_SELECTED);
370 MkMnuCmd(searchmenu,ID_GOTO_ERROR);
371
372 searchmarkmenu=new MyMenuPane(tw);
373 NewCascade(searchmenu,_("&Bookmark"),NULL,searchmarkmenu);
374 MkMnuCmd(searchmarkmenu,ID_BOOKMARK_SET);
375 MkMnuCmd(searchmarkmenu,ID_BOOKMARK_RETURN);
376
377 new FXMenuSeparator(searchmenu, 0);
378
379 findtagmenu=MkMnuCmd(searchmenu,ID_FIND_TAG);
380 findtagmenu->disable();
381 showtipmenu=MkMnuCmd(searchmenu,ID_SHOW_CALLTIP);
382 showtipmenu->disable();
383 autocompmenu=MkMnuCmd(searchmenu,ID_AUTO_COMPLETE);
384 autocompmenu->disable();
385
386
387 viewmenu=new MyMenuPane(tw);
388 NewTitle(this,_("&View"),NULL,viewmenu);
389
390 CreateLanguageMenu();
391 CreateTabsMenu();
392 CreateZoomMenu();
393
394 new FXMenuSeparator(viewmenu, 0);
395
396 status_chk = MkMnuChk(viewmenu, ID_SHOW_STATUSBAR, prefs->ShowStatusBar);
397 outpane_chk = MkMnuChk(viewmenu, ID_SHOW_OUTLIST, prefs->ShowOutputPane);
398 linenums_chk = MkMnuChk(viewmenu, ID_SHOW_LINENUMS, prefs->ShowLineNumbers);
399 toolbar_chk = MkMnuChk(viewmenu, ID_SHOW_TOOLBAR, prefs->ShowToolbar);
400
401 new FXMenuSeparator(viewmenu, 0);
402
403 margin_chk = MkMnuChk(viewmenu, ID_SHOW_MARGIN, prefs->ShowRightEdge);
404 guides_chk = MkMnuChk(viewmenu, ID_SHOW_INDENT, prefs->ShowIndentGuides);
405 white_chk = MkMnuChk(viewmenu, ID_SHOW_WHITESPACE, prefs->ShowWhiteSpace);
406 invert_chk = MkMnuChk(viewmenu, ID_INVERT_COLORS, prefs->InvertColors);
407 caretline_chk = MkMnuChk(viewmenu, ID_SHOW_CARET_LINE, prefs->ShowCaretLine);
408
409 new FXMenuSeparator(viewmenu, 0);
410
411 MkMnuCmd(viewmenu,ID_CYCLE_SPLITTER);
412 MkMnuCmd(viewmenu,ID_CLEAR_OUTPUT);
413
414 toolsmenu=new MyMenuPane(tw);
415 NewTitle(this,_("&Tools"),NULL,toolsmenu);
416
417 filterselmenu=MkMnuCmd(toolsmenu,ID_FILTER_SEL);
418 MkMnuCmd(toolsmenu,ID_INSERT_CMD_OUT);
419 MkMnuCmd(toolsmenu,ID_RUN_COMMAND);
420
421 recordermenu=new MyMenuPane(tw);
422 NewCascade(toolsmenu,_("Macro &recorder"),NULL,recordermenu);
423
424 recorderstartmenu=MkMnuCmd(recordermenu,ID_MACRO_RECORD);
425 playbackmenu=MkMnuCmd(recordermenu,ID_MACRO_PLAYBACK);
426 playbackmenu->disable();
427 showmacromenu=MkMnuCmd(recordermenu,ID_MACRO_TRANSLATE);
428 showmacromenu->disable();
429 new FXMenuSeparator(toolsmenu, 0);
430
431 MkMnuCmd(toolsmenu,ID_RESCAN_USER_MENU);
432 MkMnuCmd(toolsmenu,ID_CONFIGURE_TOOLS);
433 new FXMenuSeparator(toolsmenu, 0);
434
435 FXString scriptdir;
436 scriptdir.format("%s%s", tw->ConfigDir().text(), "tools");
437 FXDir::create(scriptdir);
438
439 scriptdir.format("%s%s%c%s", tw->ConfigDir().text(), "tools", PATHSEP, "commands");
440 FXDir::create(scriptdir);
441 usercmdmenu=new UserMenu(toolsmenu, _("&Commands"), scriptdir, 'C', tw, TW::ID_USER_COMMAND, usercmdflags);
442 usercmdmenu->helpText(_("Commands: Execute a command and send its output to the output pane."));
443
444 scriptdir.format("%s%s%c%s", tw->ConfigDir().text(), "tools", PATHSEP, "filters");
445 FXDir::create(scriptdir);
446 userfiltermenu=new UserMenu(toolsmenu, _("&Filters"), scriptdir, 'F', tw, TW::ID_USER_FILTER);
447 userfiltermenu->helpText(_("Filters: Pipe selected text to a command and replace with its output."));
448
449 scriptdir.format("%s%s%c%s", tw->ConfigDir().text(), "tools", PATHSEP, "snippets");
450 FXDir::create(scriptdir);
451 usersnipmenu=new UserMenu(toolsmenu, _("&Snippets"), scriptdir, 'S', tw, TW::ID_USER_SNIPPET, usersnipflags);
452 usersnipmenu->helpText(_("Snippets: Insert the text of a file or the output of a command."));
453
454 scriptdir.format("%s%s%c%s", tw->ConfigDir().text(), "tools", PATHSEP, "macros");
455 FXDir::create(scriptdir);
456 usermacromenu=new UserMenu(toolsmenu, _("&Macros"), scriptdir, 'M', tw, TW::ID_USER_MACRO);
457 usermacromenu->helpText(_("Macros: Execute a Lua macro using the built-in interpreter."));
458
459 #if TEST_SOMETHING
460 new FXMenuCommand(toolsmenu, _("Test something\tF2"), NULL, tw, ID_TEST_SOMETHING);
461 #endif
462
463 docmenu=new MyMenuPane(tw);
464 NewTitle(this,_("&Documents"),NULL,docmenu);
465
466 MkMnuCmd(docmenu,ID_TAB_NEXT);
467 MkMnuCmd(docmenu,ID_TAB_PREV);
468
469 tabordermenu=new MyMenuPane(tw);
470 NewCascade(docmenu,_("&Move"),NULL,tabordermenu);
471
472 MkMnuCmd(tabordermenu,ID_TAB_TOFIRST);
473 MkMnuCmd(tabordermenu,ID_TAB_TOLAST);
474 MkMnuCmd(tabordermenu,ID_TAB_UP);
475 MkMnuCmd(tabordermenu,ID_TAB_DOWN);
476
477 FXMenuCommand*tmpcmd=new FXMenuCommand(tabordermenu,"foo",NULL,NULL,0);
478 FXint dh=tmpcmd->getDefaultHeight();
479 delete tmpcmd;
480 getApp()->getRootWindow()->getDefaultHeight();
481 doclistmenu=new FXScrollPane(docmenu,24);
482 doclistmenu->setNumVisible((FXint)((getApp()->getRootWindow()->getDefaultHeight()/dh)*0.75));
483 NewCascade(docmenu, _("&Select"), NULL, doclistmenu);
484
485 new FXMenuSeparator(docmenu, 0);
486 MkMnuCmd(docmenu,ID_FOCUS_OUTLIST);
487
488 helpmenu=new MyMenuPane(tw);
489 NewTitle(this,_("&Help"),NULL,helpmenu /*,LAYOUT_RIGHT*/);
490
491 MkMnuCmd(helpmenu,ID_SHOW_HELP);
492 MkMnuCmd(helpmenu,ID_SHOW_LUA_HELP);
493 new FXMenuSeparator(helpmenu, 0);
494 MkMnuCmd(helpmenu,ID_HELP_ABOUT);
495 }
496
497
498
~MainMenu()499 MainMenu::~MainMenu()
500 {
501 delete usercmdmenu;
502 delete userfiltermenu;
503 delete usersnipmenu;
504 delete usermacromenu;
505 delete tabmenu;
506 delete filemenu;
507 delete doclistmenu;
508 delete docmenu;
509 delete tabordermenu;
510 delete tabsidemenu;
511 delete tabwidthmenu;
512 delete editdeletemenu;
513 delete editindentmenu;
514 delete editmenu;
515 delete searchselectmenu;
516 delete searchmarkmenu;
517 delete searchmenu;
518 delete recordermenu;
519 delete toolsmenu;
520 delete helpmenu;
521 delete fileexportmenu;
522 delete langmenu;
523 delete viewzoommenu;
524 delete viewmenu;
525 delete recent_files;
526 }
527
528
529
RescanUserMenus()530 void MainMenu::RescanUserMenus()
531 {
532 usercmdmenu->rescan();
533 userfiltermenu->rescan();
534 usersnipmenu->rescan();
535 usermacromenu->rescan();
536 }
537
538
539
UserMenus() const540 UserMenu**MainMenu::UserMenus() const
541 {
542 static UserMenu* menus[]={ usercmdmenu, userfiltermenu, usersnipmenu, usermacromenu, NULL };
543 return menus;
544 }
545
546
547
EnableFileFormats()548 void MainMenu::EnableFileFormats()
549 {
550
551 }
552
553
554
EnableFilterMenu(bool enabled)555 void MainMenu::EnableFilterMenu(bool enabled)
556 {
557 if (enabled) { userfiltermenu->enable(); } else { userfiltermenu->disable(); }
558 SetMenuEnabled(filterselmenu,enabled);
559 }
560
561
562
SetMenuEnabled(FXMenuCommand * mnu,bool enabled)563 void MainMenu::SetMenuEnabled(FXMenuCommand*mnu, bool enabled)
564 {
565 FXLabel*btn=(FXLabel*)(mnu->getUserData());
566 if (enabled) {
567 mnu->enable();
568 if (btn) { btn->enable(); }
569 } else {
570 mnu->disable();
571 if (btn) { btn->disable(); }
572 }
573 }
574
575
576
EnableTagMenus(bool enabled)577 void MainMenu::EnableTagMenus(bool enabled)
578 {
579 if (enabled) { unloadtagsmenu->enable(); } else { unloadtagsmenu->disable(); }
580 SetMenuEnabled(findtagmenu, enabled);
581 SetMenuEnabled(showtipmenu, enabled);
582 SetMenuEnabled(autocompmenu, enabled);
583 }
584
585
586
AddFileToTagsList(const FXString & filename)587 void MainMenu::AddFileToTagsList(const FXString &filename)
588 {
589 FXMenuPane*pane=(FXMenuPane*)unloadtagsmenu->getMenu();
590 FXWindow*w;
591 FXString fn=FXPath::simplify(FXPath::absolute(filename));
592 for ( w=pane->getFirst(); w; w=w->getNext() ) {
593 if (strcmp(fn.text(),((FXMenuCaption*)w)->getText().text())==0) {
594 return;
595 }
596 }
597 EnableTagMenus(true);
598 FXMenuCommand*mc=new FXMenuCommand(pane,"",NULL,this,TopWindow::ID_UNLOAD_TAGS);
599 mc->create();
600 mc->setText(fn);
601 }
602
603
604
UnloadTagFile(FXMenuCommand * mc)605 void MainMenu::UnloadTagFile(FXMenuCommand*mc)
606 {
607 mc->hide();
608 mc->destroy();
609 delete mc;
610 if (unloadtagsmenu->getMenu()->numChildren()==0) {
611 EnableTagMenus(false);
612 }
613 }
614
615
616
RemoveFileFromTagsList(const FXString & filename)617 bool MainMenu::RemoveFileFromTagsList(const FXString &filename)
618 {
619 FXMenuPane*pane=(FXMenuPane*)unloadtagsmenu->getMenu();
620 if (filename.empty()) { /* remove all tag files */
621 while (pane->numChildren()>0) { UnloadTagFile((FXMenuCommand*)pane->getFirst()); }
622 return true;
623 } else {
624 FXWindow*w;
625 FXString fn=FXPath::simplify(FXPath::absolute(filename));
626 for ( w=pane->getFirst(); w; w=w->getNext() ) {
627 if (strcmp(fn.text(),((FXMenuCaption*)w)->getText().text())==0) {
628 UnloadTagFile((FXMenuCommand*)w);
629 return true; /* we found it */
630 }
631 }
632 return false; /* we did not find the filename in the menu */
633 }
634 }
635
636
637
TagsMenu() const638 FXMenuCascade*MainMenu::TagsMenu() const
639 {
640 return unloadtagsmenu;
641 }
642
643
644
SetLanguageCheckmark(LangStyle * ls)645 void MainMenu::SetLanguageCheckmark(LangStyle*ls)
646 {
647 for (FXWindow*wmc=langmenu->getFirst(); wmc; wmc=wmc->getNext()) {
648 FXPopup*pu=((FXMenuCascade*)wmc)->getMenu();
649 for (FXWindow*wmr=pu->getFirst(); wmr; wmr=wmr->getNext()) {
650 FXMenuRadio*mr=(FXMenuRadio*)wmr;
651 mr->setCheck(mr->getUserData()==ls);
652 }
653 }
654 }
655
656
657
GetMenuForLanguage(const FXString & name) const658 FXMenuRadio*MainMenu::GetMenuForLanguage(const FXString &name) const
659 {
660 for (FXWindow*grp=langmenu->getFirst(); grp; grp=grp->getNext()) {
661 for (FXWindow*mnu=((FXMenuCascade*)grp)->getMenu()->getFirst(); mnu; mnu=mnu->getNext()) {
662 if (compare(((FXMenuCommand*)mnu)->getText(),name)==0) { return (FXMenuRadio*)mnu; }
663 }
664 }
665 return NULL;
666 }
667
668
669
Recording(bool recording,bool recorded)670 void MainMenu::Recording(bool recording, bool recorded)
671 {
672 FXToggleButton*tbar_rec_btn=dynamic_cast<FXToggleButton*>((FXObject*)recorderstartmenu->getUserData());
673 recorderstartmenu->setText(recording?_("Stop re&cording"):_("Re&cord macro"));
674 SetMenuEnabled(playbackmenu,recorded && !recording);
675 SetMenuEnabled(showmacromenu,recorded && !recording);
676 if (tbar_rec_btn) { tbar_rec_btn->setState(recording); }
677 }
678
679
680
AppendDocList(const FXString & filename,FXTabItem * tab)681 void MainMenu::AppendDocList(const FXString &filename, FXTabItem*tab)
682 {
683 FXMenuCommand* cmd = new FXMenuCommand( doclistmenu, filename.empty()?tab->getText():filename,
684 NULL, tw, TW::ID_TAB_ACTIVATE, 0 );
685 if (shown()) { cmd->create(); }
686 RemoveRecentFile(filename);
687 cmd->setUserData(tab);
688 tab->setUserData(cmd);
689 }
690
691
692
PrependRecentFile(const FXString & filename)693 void MainMenu::PrependRecentFile(const FXString &filename)
694 {
695 recent_files->prepend(filename);
696 }
697
698
699
RemoveRecentFile(const FXString & filename)700 void MainMenu::RemoveRecentFile(const FXString &filename)
701 {
702 recent_files->remove(filename);
703 }
704
705
706
SyncCheck(FXMenuCheck * chk,bool checked)707 static inline void SyncCheck(FXMenuCheck *chk, bool checked)
708 {
709 chk->setCheck(checked);
710 FXToggleButton*btn=dynamic_cast<FXToggleButton*>((FXObject*)chk->getUserData());
711 if (btn) { btn->setState(chk->getCheck()); }
712 }
713
714
715
SyncPrefsCheckmarks()716 void MainMenu::SyncPrefsCheckmarks()
717 {
718 SyncCheck(linenums_chk, prefs->ShowLineNumbers);
719 SyncCheck(status_chk, prefs->ShowStatusBar);
720 SyncCheck(outpane_chk, prefs->ShowOutputPane);
721 SyncCheck(white_chk, prefs->ShowWhiteSpace);
722 SyncCheck(toolbar_chk, prefs->ShowToolbar);
723 SyncCheck(margin_chk, prefs->ShowRightEdge);
724 SyncCheck(guides_chk, prefs->ShowIndentGuides);
725 SyncCheck(caretline_chk, prefs->ShowCaretLine);
726 SyncCheck(invert_chk, prefs->InvertColors);
727 }
728
729
SetReadOnlyCheckmark(bool rdonly)730 void MainMenu::SetReadOnlyCheckmark(bool rdonly)
731 {
732 SyncCheck(readonly_chk,rdonly);
733 if (rdonly) { fileformatcasc->disable(); } else { fileformatcasc->enable(); }
734 SetMenuEnabled(fmt_dos_mnu,!rdonly);
735 SetMenuEnabled(fmt_mac_mnu,!rdonly);
736 SetMenuEnabled(fmt_unx_mnu,!rdonly);
737 }
738
739
740
SetWordWrapCheckmark(bool wrapped)741 void MainMenu::SetWordWrapCheckmark(bool wrapped)
742 {
743 SyncCheck(wordwrap_chk,wrapped);
744 }
745
746
747
UpdateDocTabSettings()748 void MainMenu::UpdateDocTabSettings()
749 {
750 switch (prefs->DocTabPosition) {
751 case 'T': MenuMgr::RadioUpdate(TW::ID_TABS_TOP, TW::ID_TABS_TOP, TW::ID_TABS_RIGHT); break;
752 case 'B': MenuMgr::RadioUpdate(TW::ID_TABS_BOTTOM, TW::ID_TABS_TOP, TW::ID_TABS_RIGHT); break;
753 case 'L': MenuMgr::RadioUpdate(TW::ID_TABS_LEFT, TW::ID_TABS_TOP, TW::ID_TABS_RIGHT); break;
754 case 'R': MenuMgr::RadioUpdate(TW::ID_TABS_RIGHT, TW::ID_TABS_TOP, TW::ID_TABS_RIGHT); break;
755 }
756 switch (prefs->DocTabsPacked) {
757 case 'U':MenuMgr::RadioUpdate(TW::ID_TABS_UNIFORM,TW::ID_TABS_UNIFORM,TW::ID_TABS_BY_POS); break;
758 case 'P':MenuMgr::RadioUpdate(TW::ID_TABS_COMPACT,TW::ID_TABS_UNIFORM,TW::ID_TABS_BY_POS); break;
759 case 'A':MenuMgr::RadioUpdate(TW::ID_TABS_BY_POS,TW::ID_TABS_UNIFORM,TW::ID_TABS_BY_POS); break;
760 }
761 }
762
763