]> git.lyx.org Git - features.git/blob - src/lyxfunc.C
Initial revision
[features.git] / src / lyxfunc.C
1 /* This file is part of
2 * ======================================================
3
4 *           LyX, The Document Processor
5 *        
6 *           Copyright (C) 1995 Matthias Ettrich
7 *           Copyright (C) 1995-1998 The LyX Team.
8 *
9 *======================================================*/
10
11 #include <config.h>
12
13 #include <stdlib.h>
14 #include <ctype.h>
15 #include <string.h>
16
17 #ifdef __GNUG__
18 #pragma implementation
19 #endif
20
21 #include "definitions.h"
22 #include "lyxlookup.h"
23 #include "kbmap.h"
24 #include "lyxfunc.h"
25 #include "bufferlist.h"
26 #include "lyxserver.h"
27 #include "lyx.h"
28 #include "intl.h"
29 #include "lyx_main.h"
30 #include "lyx_cb.h"
31 #include "insets/insetlatex.h"
32 #include "insets/inseturl.h"
33 #include "insets/insetlatexaccent.h"
34 #include "insets/insettoc.h"
35 #include "insets/insetlof.h"
36 #include "insets/insetloa.h"
37 #include "insets/insetlot.h"
38 #include "insets/insetref.h"
39 #include "insets/insetparent.h"
40 #include "mathed/formulamacro.h"
41 #include "toolbar.h"
42 #include "spellchecker.h" // RVDK_PATCH_5
43 #include "minibuffer.h"
44 #include "vspace.h"
45 #include "insets/insetbib.h"
46 #include "LyXView.h"
47 #include "insets/insetindex.h"
48 #include "insets/insetinclude.h"
49 #include "filedlg.h"
50 #include "lyx_gui_misc.h"
51 #include "filetools.h"
52 #include "FileInfo.h"
53 #include "lyxscreen.h"
54 #include "error.h"
55 #include "lyxrc.h"
56 #include "lyxtext.h"
57 #include "gettext.h"
58 #include "trans_mgr.h"
59 #include "ImportLaTeX.h"
60 #include "ImportNoweb.h"
61
62 //      $Id: lyxfunc.C,v 1.1 1999/09/27 18:44:37 larsbj Exp $   
63
64 #if !defined(lint) && !defined(WITH_WARNINGS)
65 static char vcid[] = "$Id: lyxfunc.C,v 1.1 1999/09/27 18:44:37 larsbj Exp $";
66 #endif /* lint */
67
68 extern bool cursor_follows_scrollbar;
69
70 extern void InsertAsciiFile(LString const &, bool);
71 extern void math_insert_symbol(char const*);
72 extern Bool math_insert_greek(char const); // why "Bool"?
73 extern BufferList bufferlist;
74 extern LyXServer *lyxserver;
75 extern short greek_kb_flag;
76 extern FD_form_toc *fd_form_toc;
77 extern bool selection_possible;
78
79 extern kb_keymap *toplevel_keymap;
80
81 extern void BeforeChange();
82 extern void MenuWrite(Buffer*);
83 extern void MenuWriteAs(Buffer*);
84 extern int  MenuRunLaTeX(Buffer*);
85 extern int  MenuBuildProg(Buffer*);
86 extern int  MenuRunChktex(Buffer*);
87 extern bool MenuRunDvips(Buffer *,bool);
88 extern void MenuPrint(Buffer*);
89 extern void MenuSendto();
90 extern void QuitLyX();
91 extern void MenuFax(Buffer *);
92 extern void MenuMakeLaTeX(Buffer *);
93 extern void MenuMakeLinuxDoc(Buffer *);
94 extern void MenuMakeDocBook(Buffer *);
95 extern void MenuMakeAscii(Buffer *);
96 extern void MenuPasteSelection(char at);
97 extern LyXAction lyxaction;
98 // (alkis)
99 extern tex_accent_struct get_accent(kb_action action);
100
101 extern void AutoSave();
102 extern void MenuSearch();
103 extern void CopyCB();
104 extern void CopyEnvironmentCB();
105 extern void PasteEnvironmentCB();
106 extern void GotoNote();
107 extern void NoteCB();
108 extern void OpenStuff();
109 extern void HyphenationPoint();
110 extern void Ldots();
111 extern void EndOfSentenceDot();
112 extern void MenuSeparator();
113 extern void HFill();
114 extern void MenuUndo();
115 extern void MenuRedo();
116 extern void SmallUpdate(signed char);
117 extern void SetUpdateTimer(float timer= 0.3);
118 extern void FreeUpdateTimer();
119 extern bool MenuPreview(Buffer*);
120 extern bool MenuPreviewPS(Buffer*);
121 extern void MenuInsertLabel(const char *);
122 extern void MenuInsertRef();
123 extern void MenuLayoutCharacter();
124 extern void MenuLayoutParagraph();
125 extern void MenuLayoutDocument();
126 extern void MenuLayoutPaper();
127 extern void MenuLayoutTable(int flag);
128 extern void MenuLayoutQuotes();
129 extern void MenuLayoutPreamble();
130 extern void MenuLayoutSave();
131 extern void bulletForm();
132
133 extern Buffer * NewLyxFile(LString const &);
134 extern void LoadLyXFile(LString const &);
135 extern void Reconfigure();
136
137 extern int current_layout;
138 extern int getISOCodeFromLaTeX(char *);
139
140 extern int UnlockInset(UpdatableInset*);
141
142 extern void ShowLatexLog();
143
144 extern void UpdateInset(Inset* inset, bool mark_dirty = true);
145
146 /* === globals =========================================================== */
147
148 bool LyXFunc::show_sc = true;
149
150
151 LyXFunc::LyXFunc(LyXView *o)
152         :owner(o)
153 {
154         meta_fake_bit = 0;
155         lyx_dead_action = LFUN_NOACTION;
156         lyx_calling_dead_action = LFUN_NOACTION;
157         setupLocalKeymap();
158 }
159
160
161 LyXFunc::~LyXFunc()
162 {
163 }
164
165
166 LString LyXFunc::argAsString(char const *const argument)
167 {
168         LString tmp(argument);
169
170         if (tmp.empty()) {
171                 // get the arg from somewhere else, a popup, or ask for
172                 // it in the minibuffer.
173         }
174         lyxerr.debug("argAsString: <" + tmp + '>');
175         return tmp;
176 }
177
178
179 // I changed this func slightly. I commented out the ...FinishUndo(),
180 // this means that all places that used to have a moveCursorUpdate, now
181 // have a ...FinishUndo() as the preceeding statement. I have also added
182 // a moveCursorUpdate to some of the functions that updated the cursor, but
183 // that did not show its new position.
184 inline
185 void LyXFunc::moveCursorUpdate(bool selecting)
186 {
187         if (selecting || owner->currentBuffer()->text->mark_set) {
188                 owner->currentBuffer()->text->SetSelection();
189                 owner->currentView()->getScreen()->ToggleToggle();
190                 owner->currentBuffer()->update(0);
191         } else {
192                 owner->currentBuffer()->update(-2); // this IS necessary
193                 // (Matthias) 
194         }
195         owner->currentView()->getScreen()->ShowCursor();
196         
197         /* ---> Everytime the cursor is moved, show the current font state. */
198         // should this too me moved out of this func?
199         //owner->getMiniBuffer()->Set(CurrentState());
200 }
201
202
203 int LyXFunc::processKeyEvent(XEvent *ev)
204 {
205         char s_r[10];
206         s_r[9] = '\0';
207         int num_bytes;
208         int action; 
209         char *argument = 0;
210         XKeyEvent *keyevent = &ev->xkey;
211         KeySym keysym_return;
212
213         num_bytes = LyXLookupString(ev, s_r, 10, &keysym_return);
214
215         if (lyxerr.debugging(Error::KEY)) {
216                 lyxerr.print(LString("KeySym is ")
217                              + XKeysymToString(keysym_return)
218                              + "["
219                              + int(keysym_return) + "]"
220                              + " and num_bytes is "
221                              + num_bytes
222                              + " the string returned is \""
223                              + LString(s_r) + '\"');
224         }
225         // Do nothing if we have nothing (JMarc)
226         if (num_bytes == 0 && keysym_return == NoSymbol) {
227                 lyxerr.debug("Empty kbd action (probably composing)",
228                              Error::KEY);
229                 return 0;
230         }
231         
232         // this function should be used always [asierra060396]
233         if (owner->currentView()->available() &&
234             owner->currentBuffer()->the_locking_inset &&
235             keysym_return == XK_Escape) {
236                 UnlockInset(owner->currentBuffer()->the_locking_inset);
237                 owner->currentBuffer()->text->CursorRight();
238                 return 0;
239         }
240
241         // Can we be sure that this will work for all X-Windows
242         // implementations? (Lgb)
243         // This code snippet makes lyx ignore some keys. Perhaps
244         // all of them should be explictly mentioned?
245         if((keysym_return >= XK_Shift_L && keysym_return <= XK_Hyper_R)
246            || keysym_return == XK_Mode_switch || keysym_return == 0x0)
247                 return 0;
248
249         // Do a one-deep top-level lookup for
250         // cancel and meta-fake keys. RVDK_PATCH_5
251         cancel_meta_seq.reset();
252
253         action = cancel_meta_seq.addkey(keysym_return, keyevent->state
254                                         &(ShiftMask|ControlMask
255                                           |Mod1Mask)); 
256
257         // When not cancel or meta-fake, do the normal lookup. 
258         // Note how the meta_fake Mod1 bit is OR-ed in and reset afterwards.
259         // Mostly, meta_fake_bit = 0. RVDK_PATCH_5.
260         if ( (action != LFUN_CANCEL) && (action != LFUN_META_FAKE) ) {
261
262                 // remove Caps Lock and Mod2 as a modifiers
263                 action = keyseq.addkey(keysym_return,
264                                        (keyevent->state | meta_fake_bit)
265                                        &(ShiftMask|ControlMask
266                                          |Mod1Mask));      
267         }
268         // Dont remove this unless you know what you are doing.
269         meta_fake_bit = 0;
270                 
271         if (action == 0) action = LFUN_PREFIX;
272
273         if (lyxerr.debugging(Error::KEY)) {
274                 char buf[100];
275                 keyseq.print(buf,100);
276                 lyxerr.print(LString("Key [")
277                              + int(action) + "]["
278                              + buf + "]["
279                              + num_bytes +"]");
280         }
281
282         // already here we know if it any point in going further
283         // why not return already here if action == -1 and
284         // num_bytes == 0? (Lgb)
285
286         if(keyseq.length>1 || keyseq.length<-1){
287                 char buf[100];
288                 keyseq.print(buf,100);
289                 owner->getMiniBuffer()->Set(buf);
290         }
291
292         if (action==-1) {
293                 if (keyseq.length<-1) { // unknown key sequence...
294                         char buf[100];
295                         LyXBell();
296                         keyseq.print(buf,100);
297                         owner->getMiniBuffer()->Set(_("Unknown sequence:"),buf);
298                         return 0;
299                 }
300         
301                 char isochar = keyseq.getiso();
302                 if (!(keyevent->state&ControlMask) &&
303                     !(keyevent->state&Mod1Mask) &&
304                     (isochar && keysym_return < 0xF000)) {
305                         argument = &s_r[0]; // shall this be here
306                         argument[0] = isochar;
307                         argument[1] = 0;
308                 }
309                 if (!argument) {
310                         lyxerr.debug("Empty argument!");
311                         // This can`t possibly be of any use
312                         // so we`ll skip the dispatch.
313                         return 0;
314                 }
315         } else
316                 if (action==LFUN_SELFINSERT) {
317                         argument = &s_r[0];
318                         argument[1] = 0;
319                 }
320     
321         bool tmp_sc = show_sc;
322         show_sc = false;
323         Dispatch(action, argument);
324         show_sc = tmp_sc;
325         
326         // Need this for deadkeys (alkis)
327         //keyseq.length=0;
328         // ...but that breaks the minibuffer's display of "M-"...
329 #ifdef WITH_WARNINGS
330 #warning How does the deadkeys react to this?
331 #endif
332         return 0;
333
334
335
336 LString LyXFunc::Dispatch(LString const &cmd, LString const &arg)
337 {
338         return Dispatch(lyxaction.LookupFunc(cmd.c_str()),
339                         arg.c_str());
340 }
341
342
343 LString LyXFunc::Dispatch(int ac,
344                           char const *do_not_use_this_arg)
345 {
346         char const * argument = 0;
347         kb_action action;
348         
349
350         FL_OBJECT *ob = 0;  // This will disapear soon
351     
352         // we have not done anything wrong yet.
353         errorstat = false;
354         dispatch_buffer = LString();
355         
356         // if action is a pseudo-action, we need the real action
357         if (lyxaction.isPseudoAction(ac)) {
358                 char const *tmparg = 0;
359                 action = (kb_action)lyxaction.retrieveActionArg(ac, &tmparg);
360                 if (tmparg)
361                         argument = tmparg;
362         } else {
363                 action = (kb_action)ac;
364                 argument = do_not_use_this_arg; // except here
365         }
366     
367         selection_possible = false;
368         
369         if (owner->currentView()->available() 
370             && owner->currentView()->getScreen())
371                 owner->currentView()->getScreen()->HideCursor();
372
373         if(!owner->currentView()->available()) {
374                 // This lists the allowed funcs when we have no
375                 // buffer loaded
376                 switch(action){
377                 case LFUN_MENU_OPEN_BY_NAME:
378                 case LFUN_PREFIX:
379                 case LFUN_MENUNEW:
380                 case LFUN_MENUNEWTMPLT:
381                 case LFUN_MENUOPEN:
382                 case LFUN_QUIT:
383                 case LFUN_PUSH_TOOLBAR:
384                 case LFUN_ADD_TO_TOOLBAR:
385                 case LFUN_EXEC_COMMAND:
386                 case LFUN_DROP_LAYOUTS_CHOICE:
387                 case LFUN_FILE_NEW:
388                 case LFUN_FILE_OPEN:
389                 case LFUN_IMPORT:
390                 case LFUN_RECONFIGURE:
391                 case LFUN_CANCEL:
392                 case LFUN_APROPOS:
393                 case LFUN_META_FAKE:
394
395                         break;
396                 case LFUN_UNKNOWN_ACTION:
397                         setErrorMessage(N_("Unknown action"));
398                         goto exit_with_message;
399                 default:
400                         setErrorMessage(N_("Command not allowed with"
401                                         "out any document open"));
402                         goto exit_with_message;  // action not allowed
403                 }
404         }
405         
406         commandshortcut = LString();
407         
408         if (lyxrc->display_shortcuts && show_sc) {
409                 if (action != LFUN_SELFINSERT) {
410                         // Put name of command and list of shortcuts
411                         // for it in minibuffer
412                         LString comname = lyxaction.getActionName(action);
413
414                         int pseudoaction = action;
415                         bool argsadded = false;
416
417                         LString argu = argument;
418                         if (!argu.empty()) {
419                                 // If we have the command with argument, 
420                                 // this is better
421                                 pseudoaction = 
422                                         lyxaction.searchActionArg(action,
423                                                                   argument);
424
425                                 if (pseudoaction == -1) {
426                                         pseudoaction = action;
427                                 } else {
428                                         comname += " " + argu;
429                                         argsadded = true;
430                                 }
431                         }
432
433                         LString shortcuts = toplevel_keymap->findbinding(pseudoaction);
434
435                         if (!shortcuts.empty()) {
436                                 comname += ": " + shortcuts;
437                         } else if (!argsadded) {
438                                 comname += " " + argu;
439                         }
440
441                         if (!comname.empty()) {
442                                 comname.strip();
443                                 commandshortcut = "(" + comname + ')';
444                                 owner->getMiniBuffer()->Set(commandshortcut);
445                                 // Here we could even add a small pause,
446                                 // to annoy the user and make him learn
447                                 // the shortcuts.
448                                 // No! That will just annoy, not teach
449                                 // anything. The user will read the messages
450                                 // if they are interested. (Asger)
451                         }
452                 }
453         }
454
455         // Now that we know which action, if the buffer is RO let's check 
456         // whether the action is legal.  Alejandro 970603
457         if (owner->currentView()->available() && 
458             owner->currentBuffer()->isReadonly() && 
459             lyxaction.isFuncRO(action)) {
460                 setErrorMessage(N_("Document is read-only"));
461                 lyxerr.debug("Error: Document is read-only.");
462                 goto exit_with_message;
463         }
464
465         // If in math mode pass the control to
466         // the math inset [asierra060396]
467         if (owner->currentView()->available() &&
468             owner->currentBuffer()->the_locking_inset) {
469                 if (action>1 || (action==LFUN_UNKNOWN_ACTION && keyseq.length>=-1)) {
470                         char s[8]="";
471                         if (action==LFUN_UNKNOWN_ACTION && !argument) {
472                                 sprintf(s, "%c", keyseq.getiso());
473                                 argument = &s[0];
474                         }
475                         // Undo/Redo pre 0.13 is a bit tricky for insets.                   
476                         if (action==LFUN_UNDO) {
477                                 int slx, sly;
478                                 UpdatableInset* inset =
479                                         owner->currentBuffer()->the_locking_inset;
480                                 inset->GetCursorPos(slx, sly);
481                                 UnlockInset(inset);
482                                 MenuUndo();
483                                 inset = (UpdatableInset*)owner->currentBuffer()->text->cursor.par->GetInset(owner->currentBuffer()->text->cursor.pos);
484                                 if (inset) 
485                                         inset->Edit(slx, sly);
486                                 return LString();
487                         } else 
488                                 if (action==LFUN_REDO) {
489                                         int slx, sly;
490                                         UpdatableInset* inset = owner->currentBuffer()->the_locking_inset;
491                                         inset->GetCursorPos(slx, sly);
492                                         UnlockInset(inset);
493                                         MenuRedo();
494                                         inset = (UpdatableInset*)owner->currentBuffer()->text->cursor.par->GetInset(owner->currentBuffer()->text->cursor.pos);
495                                         if (inset)
496                                                 inset->Edit(slx, sly);
497                                         return LString();
498                                 } else
499                                         if (owner->currentBuffer()->the_locking_inset->LocalDispatch(action, argument))
500                                                 return LString();
501                                         else {
502                                                 setMessage(N_("Text mode"));
503                                                 if (action==LFUN_RIGHT || action==-1)
504                                                         owner->currentBuffer()->text->CursorRight();
505                                                 if (action==LFUN_LEFT || action==LFUN_RIGHT)
506                                                         return LString();
507                                         }
508                 }
509         }
510
511         switch(action) {
512                 // --- Misc -------------------------------------------
513         case LFUN_WORDFINDFORWARD  : 
514         case LFUN_WORDFINDBACKWARD : { 
515                 LyXText *ltCur;
516                 static LString last_search;
517                 LString searched_string;
518             
519                 LString arg = argAsString(argument);
520                         
521                 if (!arg.empty()) {
522                         last_search = arg;
523                         searched_string = arg;
524                 } else {
525                         searched_string = last_search;
526                 }
527
528                 ltCur =  owner->currentView()->currentBuffer()->text ;   
529
530                 if (!searched_string.empty() &&
531                     (    (action == LFUN_WORDFINDBACKWARD) ? 
532                          ltCur->SearchBackward( searched_string.c_str() ) :
533                          ltCur->SearchForward(  searched_string.c_str() ) 
534                          )){
535
536                         // ??? What is that ???
537                         owner->currentView()->currentBuffer()->update(-2);
538
539                         // ??? Needed ???
540                         // clear the selection (if there is any) 
541                         owner->currentView()->getScreen()->ToggleSelection();
542                         owner->currentView()->currentBuffer()->text->ClearSelection();
543
544                         // Move cursor so that successive C-s 's will not stand in place. 
545                         if( action == LFUN_WORDFINDFORWARD ) 
546                                 owner->currentBuffer()->text->CursorRightOneWord();
547                         owner->currentBuffer()->text->FinishUndo();
548                         moveCursorUpdate(false);
549
550                         // ??? Needed ???
551                         // set the new selection 
552                         // SetSelectionOverLenChars(owner->currentView()->currentBuffer()->text, iLenSelected);
553                         owner->currentView()->getScreen()->ToggleSelection(false);
554                 } else 
555                         LyXBell();      
556          
557                 // REMOVED : if (owner->currentView()->getWorkArea()->focus)
558                 owner->currentView()->getScreen()->ShowCursor();
559         }
560         break;
561
562         case LFUN_PREFIX:
563         {
564                 if (owner->currentView()->available()
565                     && owner->currentView()->getScreen()) {
566                         owner->currentBuffer()->update(-2);
567                 }
568                 char buf[100];
569                 keyseq.print(buf,100, true);
570                 owner->getMiniBuffer()->Set(buf, LString(), LString(), 1);
571         }
572         break;
573
574         // --- Misc -------------------------------------------
575         case LFUN_EXEC_COMMAND:
576                 owner->getMiniBuffer()->ExecCommand(); 
577                 break;
578                 
579         case LFUN_CANCEL:                   // RVDK_PATCH_5
580                 keyseq.reset();
581                 meta_fake_bit = 0;
582                 if(owner->currentView()->available())
583                         // cancel any selection
584                         Dispatch(int(LFUN_MARK_OFF), NULL);
585                 setMessage(N_("Cancel"));
586                 break;
587
588         case LFUN_META_FAKE:                                 // RVDK_PATCH_5
589         {
590                 meta_fake_bit = Mod1Mask;
591                 char buf[100];
592                 keyseq.print(buf, 98, true);
593                 LString res = LString("M-") + buf;
594                 setMessage(buf); // RVDK_PATCH_5
595         }
596         break;  
597
598         case LFUN_READ_ONLY_TOGGLE:
599                 if (owner->currentBuffer()->lyxvc.inUse()) {
600                         owner->currentBuffer()->lyxvc.toggleReadOnly();
601                 } else {
602                         owner->currentBuffer()->setReadonly(
603                                 !owner->currentBuffer()->isReadonly());
604                 }
605                 break;
606                 
607         case LFUN_CENTER: // this is center and redraw.
608                 BeforeChange();
609                 if (owner->currentBuffer()->text->cursor.y >
610                     owner->currentView()->getWorkArea()->h / 2) {
611                         owner->currentView()->getScreen()->
612                                 Draw(owner->currentBuffer()->text->cursor.y -
613                                      owner->currentView()->getWorkArea()->h/2);
614                 } else { // <=
615                         owner->currentView()->getScreen()->
616                                 Draw(0);
617                 }
618                 owner->currentBuffer()->update(0);
619                 owner->currentView()->redraw();
620                 break;
621                 
622         case LFUN_APPENDIX:
623                 if (owner->currentView()->available()) {
624                         owner->currentBuffer()->text->toggleAppendix();
625                         owner->currentBuffer()->update(1);
626                 }
627                 break;
628
629         // --- Menus -----------------------------------------------
630         case LFUN_MENUNEW:
631                 MenuNew(false);
632                 break;
633                 
634         case LFUN_MENUNEWTMPLT:
635                 MenuNew(true);
636                 break;
637                 
638         case LFUN_MENUOPEN:
639                 MenuOpen();
640                 break;
641                 
642         case LFUN_CLOSEBUFFER:
643                 CloseBuffer();
644                 break;
645                 
646         case LFUN_MENUWRITE:
647                 MenuWrite(owner->currentBuffer());
648                 break;
649                 
650         case LFUN_MENUWRITEAS:
651                 MenuWriteAs(owner->currentBuffer());
652                 break;
653                 
654         case LFUN_MENURELOAD:
655                 reloadBuffer();
656                 break;
657                 
658         case LFUN_PREVIEW:
659                 MenuPreview(owner->currentBuffer());
660                 break;
661                         
662         case LFUN_PREVIEWPS:
663                 MenuPreviewPS(owner->currentBuffer());
664                 break;
665                 
666         case LFUN_RUNLATEX:
667                 MenuRunLaTeX(owner->currentBuffer());
668                 break;
669                 
670         case LFUN_BUILDPROG:
671                 MenuBuildProg(owner->currentBuffer());
672                 break;
673                 
674         case LFUN_RUNCHKTEX:
675                 MenuRunChktex(owner->currentBuffer());
676                 break;
677                 
678         case LFUN_RUNDVIPS:
679                 MenuRunDvips(owner->currentBuffer(), false);
680                 break;
681                 
682         case LFUN_MENUPRINT:
683                 MenuPrint(owner->currentBuffer());
684                 break;
685                 
686         case LFUN_FAX:
687                 MenuFax(owner->currentBuffer());
688                 break;
689                         
690         case LFUN_EXPORT:
691         {
692                 //needs argument as string
693                 LString extyp=argAsString(argument);
694                 
695                 // latex
696                 if (extyp == "latex") {
697                         // make sure that this buffer is not linuxdoc
698                         MenuMakeLaTeX(owner->currentBuffer());
699                 }
700                 // linuxdoc
701                 else if (extyp == "linuxdoc") {
702                         // make sure that this buffer is not latex
703                         MenuMakeLinuxDoc(owner->currentBuffer());
704                 }
705                 // docbook
706                 else if (extyp == "docbook") {
707                         // make sure that this buffer is not latex or linuxdoc
708                         MenuMakeDocBook(owner->currentBuffer());
709                 }
710                 // dvi
711                 else if (extyp == "dvi") {
712                         // Run LaTeX as "Update dvi..." Bernhard.
713                         // We want the dvi in the current directory. This
714                         // is achieved by temporarily disabling use of
715                         // temp directory. As a side-effect, we get
716                         // *.log and *.aux files also. (Asger)
717                         bool flag = lyxrc->use_tempdir;
718                         lyxrc->use_tempdir = false;
719                         MenuRunLaTeX(owner->currentBuffer());
720                         lyxrc->use_tempdir = flag;
721                 }
722                 // postscript
723                 else if (extyp == "postscript") {
724                         // Start Print-dialog. Not as good as dvi... Bernhard.
725                         MenuPrint(owner->currentBuffer());
726                         // Since the MenuPrint is a pop-up, we can't use
727                         // the same trick as above. (Asger)
728                         // MISSING: Move of ps-file :-(
729                 }
730                 // ascii
731                 else if (extyp == "ascii") {
732                         MenuMakeAscii(owner->currentBuffer());
733                 }
734                 else if (extyp == "custom") {
735                         MenuSendto();
736                         break;
737                 }
738                 else {
739                         setErrorMessage(LString(N_("Unknown export type: "))
740                                         + extyp);
741                 }
742         }
743         break;
744
745         case LFUN_IMPORT:
746         {
747                 //needs argument as string
748                 LString imtyp=argAsString(argument);
749                 
750                 // latex
751                 if (imtyp == "latex") {
752                         doImportLaTeX(false);
753                 }
754                 // ascii
755                 else if (imtyp == "ascii") {
756                         doImportASCII(false);
757                 } else if (imtyp == "asciiparagraph") {
758                         doImportASCII(true);
759                 // noweb
760                 } else if (imtyp == "noweb") {
761                         doImportLaTeX(true);
762                 } else {
763                         setErrorMessage(LString(N_("Unknown import type: "))
764                                         + imtyp);
765                 }
766                 break;
767         }
768                 
769         case LFUN_QUIT:
770                 QuitLyX();
771                 break;
772                 
773         case LFUN_TOCVIEW:
774                 TocUpdateCB(ob, 0);
775                 if (fd_form_toc->form_toc->visible) {
776                         fl_raise_form(fd_form_toc->form_toc);
777                 } else {
778                         fl_show_form(fd_form_toc->form_toc,
779                                      FL_PLACE_MOUSE |
780                                      FL_FREE_SIZE, FL_FULLBORDER,
781                                      _("Table of Contents"));
782                 }
783                 break;
784                 
785         case LFUN_TOC_INSERT:
786         {
787                 Inset *new_inset =
788                         new InsetTOC(owner->currentBuffer());
789                 owner->currentBuffer()->insertInset(new_inset,
790                                                     "Standard", true);
791                 break;
792         }
793         
794         case LFUN_LOF_INSERT:
795         {
796                 Inset *new_inset =
797                         new InsetLOF(owner->currentBuffer());
798                 owner->currentBuffer()->insertInset(new_inset,
799                                                     "Standard", true);
800                 break;
801         }
802         
803         case LFUN_LOA_INSERT:
804         {
805                 Inset *new_inset =
806                         new InsetLOA(owner->currentBuffer());
807                 owner->currentBuffer()->insertInset(new_inset,
808                                                     "Standard", true);
809                 break;
810         }
811
812         case LFUN_LOT_INSERT:
813         {
814                 Inset *new_inset =
815                         new InsetLOT(owner->currentBuffer());
816                 owner->currentBuffer()->insertInset(new_inset,
817                                                     "Standard", true);
818                 break;
819         }
820                 
821         case LFUN_TABLE:
822                 TableCB(ob, 0);
823                 break;
824                 
825         case LFUN_FIGURE:
826                 FigureCB(ob, 0);
827                 break;
828                 
829         case LFUN_AUTOSAVE:
830                 AutoSave();
831                 break;
832                 
833         case LFUN_UNDO:
834                 MenuUndo();
835                 break;
836                 
837         case LFUN_REDO:
838                 MenuRedo();
839                 break;
840                 
841         case LFUN_MENUSEARCH:
842                 MenuSearch();
843                 break;
844                 
845         case LFUN_PASTE:
846                 PasteCB();
847                 break;
848                 
849         case LFUN_PASTESELECTION:
850         {
851                 bool asPara = false;
852                 if (LString(argument) == "paragraph") asPara = true;
853                 MenuPasteSelection(asPara);
854                 break;
855         }
856
857         case LFUN_CUT:
858                 CutCB();
859                 break;
860                 
861         case LFUN_COPY:
862                 CopyCB();
863                 break;
864                 
865         case LFUN_LAYOUT_COPY:
866                 CopyEnvironmentCB();
867                 break;
868                 
869         case LFUN_LAYOUT_PASTE:
870                 PasteEnvironmentCB();
871                 break;
872                 
873         case LFUN_GOTOERROR:
874                 owner->currentView()->gotoError();
875                 break;
876                 
877         case LFUN_REMOVEERRORS:
878                 if (owner->currentBuffer()->removeAutoInsets()) {
879                         owner->currentView()->redraw();
880                         owner->currentView()->fitCursor();
881                         owner->currentView()->updateScrollbar();
882                 }
883                 break;
884                 
885         case LFUN_GOTONOTE:
886                 GotoNote();
887                 break;
888                 
889         case LFUN_OPENSTUFF:
890                 OpenStuff();
891                 break;
892                 
893         case LFUN_HYPHENATION:
894                 HyphenationPoint();
895                 break;
896                 
897         case LFUN_LDOTS:
898                 Ldots();
899                 break;
900                 
901         case LFUN_END_OF_SENTENCE:
902                 EndOfSentenceDot();
903                 break;
904
905         case LFUN_MENU_SEPARATOR:
906                 MenuSeparator();
907                 break;
908                 
909         case LFUN_HFILL:
910                 HFill();
911                 break;
912                 
913         case LFUN_DEPTH:
914                 DepthCB(ob, 0);
915                 break;
916                 
917         case LFUN_DEPTH_MIN:
918                 DepthCB(ob, -1);
919                 break;
920                 
921         case LFUN_DEPTH_PLUS:
922                 DepthCB(ob, 1);
923                 break;
924                 
925         case LFUN_FREE:
926                 FreeCB();
927                 break;
928                 
929         case LFUN_TEX:
930                 TexCB();
931                 break;
932                 
933         case LFUN_MELT:
934                 MeltCB(ob, 0);
935                 break;
936                 
937         case LFUN_RECONFIGURE:
938                 Reconfigure();
939                 break;
940
941         case LFUN_FOOTMELT:
942                 if (owner->currentView()->available()
943                     && !owner->currentBuffer()->text->selection
944                     && owner->currentBuffer()->text->cursor.par->footnoteflag
945                     != LyXParagraph::NO_FOOTNOTE)
946                 { // only melt footnotes with FOOTMELT, not margins etc
947                   if(owner->currentBuffer()->text->cursor.par->footnotekind == LyXParagraph::FOOTNOTE)
948                         MeltCB(ob,0);
949                 }
950                 else
951                         FootCB(ob, 0); 
952                 break;
953
954         case LFUN_MARGINMELT:
955                 if (owner->currentView()->available()
956                     && !owner->currentBuffer()->text->selection
957                     && owner->currentBuffer()->text->cursor.par->footnoteflag
958                     != LyXParagraph::NO_FOOTNOTE)
959                 { // only melt margins
960                   if(owner->currentBuffer()->text->cursor.par->footnotekind == LyXParagraph::MARGIN)
961                         MeltCB(ob,0);
962                 }
963                 else
964                         MarginCB(ob, 0); 
965                 break;
966                 
967                 // --- version control -------------------------------
968         case LFUN_VC_REGISTER:
969         {
970                 if (!owner->currentBuffer()->lyxvc.inUse())
971                         owner->currentBuffer()->lyxvc.registrer();
972         }
973         break;
974                 
975         case LFUN_VC_CHECKIN:
976         {
977                 if (owner->currentBuffer()->lyxvc.inUse()
978                     && !owner->currentBuffer()->isReadonly())
979                         owner->currentBuffer()->lyxvc.checkIn();
980         }
981         break;
982                 
983         case LFUN_VC_CHECKOUT:
984         {
985                 if (owner->currentBuffer()->lyxvc.inUse()
986                     && owner->currentBuffer()->isReadonly())
987                         owner->currentBuffer()->lyxvc.checkOut();
988         }
989         break;
990         
991         case LFUN_VC_REVERT:
992         {
993                 owner->currentBuffer()->lyxvc.revert();
994         }
995         break;
996                 
997         case LFUN_VC_UNDO:
998         {
999                 owner->currentBuffer()->lyxvc.undoLast();
1000         }
1001         break;
1002                 
1003         case LFUN_VC_HISTORY:
1004         {
1005                 owner->currentBuffer()->lyxvc.showLog();
1006                 break;
1007         }
1008         
1009         // --- buffers ----------------------------------------
1010         case LFUN_PREVBUFFER:
1011 #ifdef WITH_WARNINGS
1012 #warning fix this please
1013 #endif
1014                 // it is the LyXView or the BufferView that should
1015                 // remember the previous buffer, not bufferlist.
1016 //                      if (owner->currentView()->available()){   
1017 //                              BeforeChange();
1018 //                              owner->currentBuffer()->update(-2);
1019 //                      }
1020 //                      owner->currentView()->setBuffer(bufferlist.prev());
1021
1022 //                      owner->currentView()->
1023 //                              resizeCurrentBufferPseudoExpose();
1024                 break;
1025                         
1026         case LFUN_FILE_INSERT:
1027         {
1028                 // needs argument as string
1029                 LString fil = argAsString(argument);
1030                 MenuInsertLyXFile(fil);
1031         }
1032         break;
1033         
1034         case LFUN_FILE_INSERT_ASCII:
1035         {
1036                 bool asPara = false;
1037                 asPara = (LString(argument) == "paragraph");
1038                 InsertAsciiFile(LString(), asPara);
1039         }
1040         break;
1041         
1042         case LFUN_FILE_NEW:
1043         {
1044                 // servercmd: argument must be <file>:<template>
1045                 Buffer * tmpbuf = 0;
1046                 tmpbuf = NewLyxFile(argument);
1047                 if (tmpbuf)
1048                         owner->currentView()->setBuffer(tmpbuf);
1049         }
1050                 break;
1051                         
1052         case LFUN_FILE_OPEN:
1053                 owner->currentView()->setBuffer(
1054                         bufferlist.loadLyXFile(argument));
1055                 break;
1056
1057         case LFUN_LATEX_LOG:
1058                 ShowLatexLog();
1059                 break;
1060                 
1061         case LFUN_LAYOUTNO:
1062         {
1063                 lyxerr.debug("LFUN_LAYOUTNO: (arg) " + LString(argument));
1064                 int sel = atoi(argument);
1065                 lyxerr.debug(LString("LFUN_LAYOUTNO: (sel) ") + int(sel));
1066                 
1067                 // Should this give a setMessage instead?
1068                 if (sel == 0) 
1069                         return LString(); // illegal argument
1070
1071                 sel--; // sel 1..., but layout 0...
1072
1073                 // Pretend we got the name instead.
1074                 Dispatch(int(LFUN_LAYOUT), 
1075                          lyxstyle.NameOfLayout(owner->currentBuffer()->
1076                                                text->parameters->
1077                                                textclass,
1078                                                sel).c_str());
1079                 return LString();
1080         }
1081                 
1082         case LFUN_LAYOUT:
1083         {
1084                 lyxerr.debug("LFUN_LAYOUT: (arg) "
1085                              + LString(argument));
1086                 
1087                 // Derive layout number from given argument (string)
1088                 // and current buffer's textclass (number). */    
1089                 int layoutno = -1;
1090                 layoutno =
1091                         lyxstyle.NumberOfLayout(owner->
1092                                                 currentBuffer()->
1093                                                 text->parameters->
1094                                                 textclass,
1095                                                 argument);
1096
1097                 // see if we found the layout number:
1098                 if (layoutno == -1) {
1099                         setErrorMessage(LString(N_("Layout ")) + argument + 
1100                                         N_(" not known"));
1101                         break;
1102                 }
1103                         
1104                 if (current_layout != layoutno) {
1105                         owner->currentView()->getScreen()->HideCursor();
1106                         current_layout = layoutno;
1107                         owner->currentBuffer()->update(-2);
1108                         owner->currentBuffer()->text->
1109                                 SetLayout(layoutno);
1110                         owner->getToolbar()->combox->
1111                                 select(owner->currentBuffer()->
1112                                        text->cursor.par->
1113                                        GetLayout() + 1);
1114                         owner->currentBuffer()->update(1);
1115                 }
1116         }
1117         break;
1118
1119         case LFUN_LAYOUT_DOCUMENT:
1120                 MenuLayoutDocument();
1121                 break;
1122                 
1123         case LFUN_LAYOUT_PARAGRAPH:
1124                 MenuLayoutParagraph();
1125                 break;
1126                 
1127         case LFUN_LAYOUT_CHARACTER:
1128                 MenuLayoutCharacter();
1129                 break;
1130                 
1131         case LFUN_LAYOUT_TABLE:
1132         {
1133                 int flag = 0;
1134                 if (LString(argument) == "true") flag = 1;
1135                 MenuLayoutTable(flag);
1136         }
1137         break;
1138                 
1139         case LFUN_LAYOUT_PAPER:
1140                 MenuLayoutPaper();
1141                 break;
1142                 
1143         case LFUN_LAYOUT_QUOTES:
1144                 MenuLayoutQuotes();
1145                 break;
1146                 
1147         case LFUN_LAYOUT_PREAMBLE:
1148                 MenuLayoutPreamble();
1149                 break;
1150                 
1151         case LFUN_LAYOUT_SAVE_DEFAULT:
1152                 MenuLayoutSave();
1153                 break;
1154                 
1155         case LFUN_DROP_LAYOUTS_CHOICE:
1156                 owner->getToolbar()->combox->Show();
1157                 break;
1158
1159         case LFUN_EMPH:
1160                 EmphCB();
1161                 break;
1162                 
1163         case LFUN_BOLD:
1164                 BoldCB();
1165                 break;
1166                 
1167         case LFUN_NOUN:
1168                 NounCB();
1169                 break;
1170                 
1171         case LFUN_CODE:
1172                 CodeCB();
1173                 break;
1174                 
1175         case LFUN_SANS:
1176                 SansCB();
1177                 break;
1178                 
1179         case LFUN_ROMAN:
1180                 RomanCB();
1181                 break;
1182                 
1183         case LFUN_DEFAULT:
1184                 StyleResetCB();
1185                 break;
1186                 
1187         case LFUN_UNDERLINE:
1188                 UnderlineCB();
1189                 break;
1190                 
1191         case LFUN_FONT_SIZE:
1192                 FontSizeCB(argument);
1193                 break;
1194                 
1195         case LFUN_FONT_STATE:
1196                 setMessage(CurrentState());
1197                 break;
1198                 
1199         case LFUN_UPCASE_WORD:
1200                 owner->currentBuffer()->update(-2);
1201                 FreeUpdateTimer();
1202                 owner->currentBuffer()->text->ChangeWordCase(2);
1203                 owner->currentBuffer()->update(1);
1204                 SetUpdateTimer();
1205                 break;
1206                 
1207         case LFUN_LOWCASE_WORD:
1208                 owner->currentBuffer()->update(-2);
1209                 FreeUpdateTimer();
1210                 owner->currentBuffer()->text->ChangeWordCase(0);
1211                 owner->currentBuffer()->update(1);
1212                 SetUpdateTimer();
1213                 break;
1214                 
1215         case LFUN_CAPITALIZE_WORD:
1216                 owner->currentBuffer()->update(-2);
1217                 FreeUpdateTimer();
1218                 owner->currentBuffer()->text->ChangeWordCase(1);
1219                 owner->currentBuffer()->update(1);
1220                 SetUpdateTimer();
1221                 break;
1222                 
1223         case LFUN_INSERT_LABEL:
1224                 MenuInsertLabel(argument);
1225                 break;
1226                 
1227         case LFUN_INSERT_REF:
1228                 MenuInsertRef();
1229                 break;
1230                 
1231         case LFUN_REFTOGGLE:
1232         {
1233                 InsetRef *inset =
1234                         (InsetRef*)getInsetByCode(Inset::REF_CODE);
1235                 if (inset) {
1236                         if (inset->getFlag()==InsetRef::REF)
1237                                 inset->setFlag(InsetRef::PAGE_REF);
1238                         else
1239                                 inset->setFlag(InsetRef::REF);
1240                         UpdateInset(inset);
1241                 } else {
1242                         setErrorMessage(N_("No cross-reference to toggle"));
1243                 }
1244         }
1245         break;
1246         
1247         case LFUN_REFBACK:
1248         {
1249                 owner->currentView()->restorePosition();
1250         }
1251         break;
1252
1253         case LFUN_REFGOTO:
1254         {
1255                 LString label(argument);
1256                 if (label.empty()) {
1257                         InsetRef *inset =
1258                                 (InsetRef*)getInsetByCode(Inset::REF_CODE);
1259                         if (inset)
1260                                 label = inset->getContents();
1261                 }
1262                 
1263                 if (!label.empty()) {
1264                         owner->currentView()->savePosition();
1265                         owner->currentBuffer()->gotoLabel(label.c_str());
1266                 }
1267         }
1268         break;
1269                 
1270         case LFUN_MENU_OPEN_BY_NAME:
1271                 owner->getMenus()->openByName(argument);
1272                 break; // RVDK_PATCH_5
1273                 
1274         case LFUN_SPELLCHECK:
1275                 if (lyxrc->isp_command != "none")
1276                         ShowSpellChecker();
1277                 break; // RVDK_PATCH_5
1278                 
1279                 // --- Cursor Movements -----------------------------
1280         case LFUN_RIGHT:
1281         {
1282                 Buffer *tmpbuffer = owner->currentBuffer();
1283                 LyXText *tmptext = owner->currentBuffer()->text;
1284                 if(!tmptext->mark_set)
1285                         BeforeChange();
1286                 tmpbuffer->update(-2);
1287                 if (tmptext->cursor.pos < tmptext->cursor.par->Last()
1288                     && tmptext->cursor.par->GetChar(tmptext->cursor.pos)
1289                     == LYX_META_INSET
1290                     && tmptext->cursor.par->GetInset(tmptext->cursor.pos)
1291                     && tmptext->cursor.par->GetInset(tmptext->cursor.pos)->Editable()==2){
1292                         Inset* tmpinset = tmptext->cursor.par->GetInset(tmptext->cursor.pos);
1293                         setMessage(tmpinset->EditMessage());
1294                         tmpinset->Edit(0,0);
1295                         break;
1296                 }
1297                 tmptext->CursorRight();
1298                 owner->currentBuffer()->text->FinishUndo();
1299                 moveCursorUpdate(false);
1300                 owner->getMiniBuffer()->Set(CurrentState());
1301         }
1302         break;
1303                 
1304         case LFUN_LEFT:
1305         {
1306                 // This is soooo ugly. Isn`t it possible to make
1307                 // it simpler? (Lgb)
1308                 LyXText *txt= owner->currentBuffer()->text;
1309                 if(!txt->mark_set) BeforeChange();
1310                 owner->currentBuffer()->update(-2);
1311                 txt->CursorLeft();
1312                 if (txt->cursor.pos < txt->cursor.par->Last()
1313                     && txt->cursor.par->GetChar(txt->cursor.pos)
1314                     == LYX_META_INSET
1315                     && txt->cursor.par->GetInset(txt->cursor.pos)
1316                     && txt->cursor.par->GetInset(txt->cursor.pos)->Editable()==2) {
1317                         Inset* tmpinset = txt->cursor.par->GetInset(txt->cursor.pos);
1318                         setMessage(tmpinset->EditMessage());
1319                         tmpinset->Edit(tmpinset->Width(txt->GetFont(txt->cursor.par,
1320                                                                     txt->cursor.pos)),0);
1321                         //                      tmpinset->Edit(-1, 0);  // -1 means go rightmost
1322                         break;
1323                 }
1324                 owner->currentBuffer()->text->FinishUndo();
1325                 moveCursorUpdate(false);
1326                 owner->getMiniBuffer()->Set(CurrentState());
1327         }
1328         break;
1329                 
1330         case LFUN_UP:
1331                 if(!owner->currentBuffer()->text->mark_set) BeforeChange();
1332                 owner->currentBuffer()->update(-3);
1333                 owner->currentBuffer()->text->CursorUp();
1334                 owner->currentBuffer()->text->FinishUndo();
1335                 moveCursorUpdate(false);
1336                 owner->getMiniBuffer()->Set(CurrentState());
1337                 break;
1338                 
1339         case LFUN_DOWN:
1340                 if(!owner->currentBuffer()->text->mark_set)
1341                         BeforeChange();
1342                 owner->currentBuffer()->update(-3);
1343                 owner->currentBuffer()->text->CursorDown();
1344                 owner->currentBuffer()->text->FinishUndo();
1345                 moveCursorUpdate(false);
1346                 owner->getMiniBuffer()->Set(CurrentState());
1347                 break;
1348
1349         case LFUN_UP_PARAGRAPH:
1350                 if(!owner->currentBuffer()->text->mark_set)
1351                         BeforeChange();
1352                 owner->currentBuffer()->update(-3);
1353                 owner->currentBuffer()->text->CursorUpParagraph();
1354                 owner->currentBuffer()->text->FinishUndo();
1355                 moveCursorUpdate(false);
1356                 owner->getMiniBuffer()->Set(CurrentState());
1357                 break;
1358                 
1359         case LFUN_DOWN_PARAGRAPH:
1360                 if(!owner->currentBuffer()->text->mark_set)
1361                         BeforeChange();
1362                 owner->currentBuffer()->update(-3);
1363                 owner->currentBuffer()->text->CursorDownParagraph();
1364                 owner->currentBuffer()->text->FinishUndo();
1365                 moveCursorUpdate(false);
1366                 owner->getMiniBuffer()->Set(CurrentState());
1367                 break;
1368                 
1369         case LFUN_PRIOR:
1370                 if(!owner->currentBuffer()->text->mark_set)
1371                         BeforeChange();
1372                 owner->currentBuffer()->update(-3);
1373                 owner->currentView()->cursorPrevious();
1374                 owner->currentBuffer()->text->FinishUndo();
1375                 moveCursorUpdate(false);
1376                 owner->getMiniBuffer()->Set(CurrentState());
1377                 break;
1378                 
1379         case LFUN_NEXT:
1380                 if(!owner->currentBuffer()->text->mark_set)
1381                         BeforeChange();
1382                 owner->currentBuffer()->update(-3);
1383                 owner->currentView()->cursorNext();
1384                 owner->currentBuffer()->text->FinishUndo();
1385                 moveCursorUpdate(false);
1386                 owner->getMiniBuffer()->Set(CurrentState());
1387                 break;
1388                 
1389         case LFUN_HOME:
1390                 if(!owner->currentBuffer()->text->mark_set)
1391                         BeforeChange();
1392                 owner->currentBuffer()->update(-2);
1393                 owner->currentBuffer()->text->CursorHome();
1394                 owner->currentBuffer()->text->FinishUndo();
1395                 moveCursorUpdate(false);
1396                 owner->getMiniBuffer()->Set(CurrentState());
1397                 break;
1398                 
1399         case LFUN_END:
1400                 if(!owner->currentBuffer()->text->mark_set)
1401                         BeforeChange();
1402                 owner->currentBuffer()->update(-2);
1403                 owner->currentBuffer()->text->CursorEnd();
1404                 owner->currentBuffer()->text->FinishUndo();
1405                 moveCursorUpdate(false);
1406                 owner->getMiniBuffer()->Set(CurrentState());
1407                 break;
1408                 
1409         case LFUN_TAB:
1410                 if(!owner->currentBuffer()->text->mark_set)
1411                         BeforeChange();
1412                 owner->currentBuffer()->update(-2);
1413                 owner->currentBuffer()->text->CursorTab();
1414                 owner->currentBuffer()->text->FinishUndo();
1415                 moveCursorUpdate(false);
1416                 owner->getMiniBuffer()->Set(CurrentState());
1417                 break;
1418                 
1419         case LFUN_WORDRIGHT:
1420                 if(!owner->currentBuffer()->text->mark_set)
1421                         BeforeChange();
1422                 owner->currentBuffer()->update(-2);
1423                 owner->currentBuffer()->text->CursorRightOneWord();
1424                 owner->currentBuffer()->text->FinishUndo();
1425                 moveCursorUpdate(false);
1426                 owner->getMiniBuffer()->Set(CurrentState());
1427                 break;
1428                 
1429         case LFUN_WORDLEFT:
1430                 if(!owner->currentBuffer()->text->mark_set)
1431                         BeforeChange();
1432                 owner->currentBuffer()->update(-2);
1433                 owner->currentBuffer()->text->CursorLeftOneWord();
1434                 owner->currentBuffer()->text->FinishUndo();
1435                 moveCursorUpdate(false);
1436                 owner->getMiniBuffer()->Set(CurrentState());
1437                 break;
1438                 
1439         case LFUN_BEGINNINGBUF:
1440                 if(!owner->currentBuffer()->text->mark_set)
1441                         BeforeChange();
1442                 owner->currentBuffer()->update(-2);
1443                 owner->currentBuffer()->text->CursorTop();
1444                 owner->currentBuffer()->text->FinishUndo();
1445                 moveCursorUpdate(false);
1446                 owner->getMiniBuffer()->Set(CurrentState());
1447                 break;
1448                 
1449         case LFUN_ENDBUF:
1450                 if(!owner->currentBuffer()->text->mark_set)
1451                         BeforeChange();
1452                 owner->currentBuffer()->update(-2);
1453                 owner->currentBuffer()->text->CursorBottom();
1454                 owner->currentBuffer()->text->FinishUndo();
1455                 moveCursorUpdate(false);
1456                 owner->getMiniBuffer()->Set(CurrentState());
1457                 break;
1458
1459       
1460                 /* cursor selection ---------------------------- */
1461         case LFUN_RIGHTSEL:
1462                 owner->currentBuffer()->update(-2);
1463                 owner->currentBuffer()->text->CursorRight();
1464                 owner->currentBuffer()->text->FinishUndo();
1465                 moveCursorUpdate(true);
1466                 owner->getMiniBuffer()->Set(CurrentState());
1467                 break;
1468                 
1469         case LFUN_LEFTSEL:
1470                 owner->currentBuffer()->update(-2);
1471                 owner->currentBuffer()->text->CursorLeft();
1472                 owner->currentBuffer()->text->FinishUndo();
1473                 moveCursorUpdate(true);
1474                 owner->getMiniBuffer()->Set(CurrentState());
1475                 break;
1476                 
1477         case LFUN_UPSEL:
1478                 owner->currentBuffer()->update(-2);
1479                 owner->currentBuffer()->text->CursorUp();
1480                 owner->currentBuffer()->text->FinishUndo();
1481                 moveCursorUpdate(true);
1482                 owner->getMiniBuffer()->Set(CurrentState());
1483                 break;
1484                 
1485         case LFUN_DOWNSEL:
1486                 owner->currentBuffer()->update(-2);
1487                 owner->currentBuffer()->text->CursorDown();
1488                 owner->currentBuffer()->text->FinishUndo();
1489                 moveCursorUpdate(true);
1490                 owner->getMiniBuffer()->Set(CurrentState());
1491                 break;
1492
1493         case LFUN_UP_PARAGRAPHSEL:
1494                 owner->currentBuffer()->update(-2);
1495                 owner->currentBuffer()->text->CursorUpParagraph();
1496                 owner->currentBuffer()->text->FinishUndo();
1497                 moveCursorUpdate(true);
1498                 owner->getMiniBuffer()->Set(CurrentState());
1499                 break;
1500                 
1501         case LFUN_DOWN_PARAGRAPHSEL:
1502                 owner->currentBuffer()->update(-2);
1503                 owner->currentBuffer()->text->CursorDownParagraph();
1504                 owner->currentBuffer()->text->FinishUndo();
1505                 moveCursorUpdate(true);
1506                 owner->getMiniBuffer()->Set(CurrentState());
1507                 break;
1508                 
1509         case LFUN_PRIORSEL:
1510                 owner->currentBuffer()->update(-2);
1511                 owner->currentView()->cursorPrevious();
1512                 owner->currentBuffer()->text->FinishUndo();
1513                 moveCursorUpdate(true);
1514                 owner->getMiniBuffer()->Set(CurrentState());
1515                 break;
1516                 
1517         case LFUN_NEXTSEL:
1518                 owner->currentBuffer()->update(-2);
1519                 owner->currentView()->cursorNext();
1520                 owner->currentBuffer()->text->FinishUndo();
1521                 moveCursorUpdate(true);
1522                 owner->getMiniBuffer()->Set(CurrentState());
1523                 break;
1524                 
1525         case LFUN_HOMESEL:
1526                 owner->currentBuffer()->update(-2);
1527                 owner->currentBuffer()->text->CursorHome();
1528                 owner->currentBuffer()->text->FinishUndo();
1529                 moveCursorUpdate(true);
1530                 owner->getMiniBuffer()->Set(CurrentState());
1531                 break;
1532                 
1533         case LFUN_ENDSEL:
1534                 owner->currentBuffer()->update(-2);
1535                 owner->currentBuffer()->text->CursorEnd();
1536                 owner->currentBuffer()->text->FinishUndo();
1537                 moveCursorUpdate(true);
1538                 owner->getMiniBuffer()->Set(CurrentState());
1539                 break;
1540                 
1541         case LFUN_WORDRIGHTSEL:
1542                 owner->currentBuffer()->update(-2);
1543                 owner->currentBuffer()->text->CursorRightOneWord();
1544                 owner->currentBuffer()->text->FinishUndo();
1545                 moveCursorUpdate(true);
1546                 owner->getMiniBuffer()->Set(CurrentState());
1547                 break;
1548                 
1549         case LFUN_WORDLEFTSEL:
1550                 owner->currentBuffer()->update(-2);
1551                 owner->currentBuffer()->text->CursorLeftOneWord();
1552                 owner->currentBuffer()->text->FinishUndo();
1553                 moveCursorUpdate(true);
1554                 owner->getMiniBuffer()->Set(CurrentState());
1555                 break;
1556                 
1557         case LFUN_BEGINNINGBUFSEL:
1558                 owner->currentBuffer()->update(-2);
1559                 owner->currentBuffer()->text->CursorTop();
1560                 owner->currentBuffer()->text->FinishUndo();
1561                 moveCursorUpdate(true);
1562                 owner->getMiniBuffer()->Set(CurrentState());
1563                 break;
1564                 
1565         case LFUN_ENDBUFSEL:
1566                 owner->currentBuffer()->update(-2);
1567                 owner->currentBuffer()->text->CursorBottom();
1568                 owner->currentBuffer()->text->FinishUndo();
1569                 moveCursorUpdate(true);
1570                 owner->getMiniBuffer()->Set(CurrentState());
1571                 break;
1572
1573                 // --- text changing commands ------------------------
1574         case LFUN_BREAKLINE:
1575                 BeforeChange();
1576                 owner->currentBuffer()->text->InsertChar(LYX_META_NEWLINE);
1577                 SmallUpdate(1);
1578                 SetUpdateTimer(0.01);
1579                 moveCursorUpdate(false);
1580                 break;
1581                 
1582         case LFUN_PROTECTEDSPACE:
1583                 BeforeChange();
1584                 owner->currentBuffer()->text->
1585                         InsertChar(LYX_META_PROTECTED_SEPARATOR);
1586                 SmallUpdate(1);
1587                 SetUpdateTimer();
1588                 moveCursorUpdate(false);
1589                 break;
1590                 
1591         case LFUN_SETMARK:
1592                 if(owner->currentBuffer()->text->mark_set) {
1593                         BeforeChange();
1594                         owner->currentBuffer()->update(0);
1595                         setMessage(N_("Mark removed"));
1596                 } else {
1597                         BeforeChange();
1598                         owner->currentBuffer()->text->mark_set = 1;
1599                         owner->currentBuffer()->update(0);
1600                         setMessage(N_("Mark set"));
1601                 }
1602                 owner->currentBuffer()->text->sel_cursor =
1603                         owner->currentBuffer()->text->cursor;
1604                 break;
1605                 
1606         case LFUN_DELETE:
1607                 FreeUpdateTimer();
1608                 if (!owner->currentBuffer()->text->selection) {
1609                         owner->currentBuffer()->text->Delete();
1610                         owner->currentBuffer()->text->sel_cursor =
1611                                 owner->currentBuffer()->text->cursor;
1612                         SmallUpdate(1);
1613                         // It is possible to make it a lot faster still
1614                         // just comment out the lone below...
1615                         owner->currentView()->getScreen()->ShowCursor();
1616                 } else {
1617                         CutCB();
1618                 }
1619                 SetUpdateTimer();
1620                 break;
1621
1622         case LFUN_DELETE_SKIP:
1623         {
1624                 // Reverse the effect of LFUN_BREAKPARAGRAPH_SKIP.
1625                 
1626                 LyXCursor cursor = owner->currentBuffer()->text->cursor;
1627
1628                 FreeUpdateTimer();
1629                 if (!owner->currentBuffer()->text->selection) {
1630                         if (cursor.pos == cursor.par->Last()) {
1631                                 owner->currentBuffer()->text->CursorRight();
1632                                 cursor = owner->currentBuffer()->text->cursor;
1633                                 if (cursor.pos == 0
1634                                     && !(cursor.par->added_space_top 
1635                                          == VSpace (VSpace::NONE))) {
1636                                         owner->currentBuffer()->text->SetParagraph
1637                                                 (cursor.par->line_top,
1638                                                  cursor.par->line_bottom,
1639                                                  cursor.par->pagebreak_top, 
1640                                                  cursor.par->pagebreak_bottom,
1641                                                  VSpace(VSpace::NONE), 
1642                                                  cursor.par->added_space_bottom,
1643                                                  cursor.par->align, 
1644                                                  cursor.par->labelwidthstring, 0);
1645                                         owner->currentBuffer()->text->CursorLeft();
1646                                         owner->currentBuffer()->update (1);
1647                                 } else {
1648                                         owner->currentBuffer()->text->CursorLeft();
1649                                         owner->currentBuffer()->text->Delete();
1650                                         owner->currentBuffer()->text->sel_cursor =
1651                                                 owner->currentBuffer()->text->cursor;
1652                                         SmallUpdate(1);
1653                                 }
1654                         } else {
1655                                 owner->currentBuffer()->text->Delete();
1656                                 owner->currentBuffer()->text->sel_cursor =
1657                                         owner->currentBuffer()->text->cursor;
1658                                 SmallUpdate(1);
1659                         }
1660                 } else {
1661                         CutCB();
1662                 }
1663                 SetUpdateTimer();
1664         }
1665         break;
1666
1667         /* -------> Delete word forward. */
1668         case LFUN_DELETE_WORD_FORWARD:
1669                 owner->currentBuffer()->update(-2);
1670                 FreeUpdateTimer();
1671                 owner->currentBuffer()->text->DeleteWordForward();
1672                 owner->currentBuffer()->update( 1 );
1673                 SetUpdateTimer();
1674                 moveCursorUpdate(false);
1675                 break;
1676
1677                 /* -------> Delete word backward. */
1678         case LFUN_DELETE_WORD_BACKWARD:
1679                 owner->currentBuffer()->update(-2);
1680                 FreeUpdateTimer();
1681                 owner->currentBuffer()->text->DeleteWordBackward();
1682                 owner->currentBuffer()->update( 1 );
1683                 SetUpdateTimer();
1684                 moveCursorUpdate(false);
1685                 break;
1686                 
1687                 /* -------> Kill to end of line. */
1688         case LFUN_DELETE_LINE_FORWARD:
1689                 FreeUpdateTimer();
1690                 owner->currentBuffer()->update(-2);
1691                 owner->currentBuffer()->text->DeleteLineForward();
1692                 owner->currentBuffer()->update( 1 );
1693                 SetUpdateTimer();
1694                 moveCursorUpdate(false);
1695                 break;
1696                 
1697                 /* -------> Set mark off. */
1698         case LFUN_MARK_OFF:
1699                 BeforeChange();
1700                 owner->currentBuffer()->update(0);
1701                 owner->currentBuffer()->text->sel_cursor =
1702                         owner->currentBuffer()->text->cursor;
1703                 setMessage(N_("Mark off"));
1704                 break;
1705
1706                 /* -------> Set mark on. */
1707         case LFUN_MARK_ON:
1708                 BeforeChange();
1709                 owner->currentBuffer()->text->mark_set = 1;
1710                 owner->currentBuffer()->update( 0 );
1711                 owner->currentBuffer()->text->sel_cursor =
1712                         owner->currentBuffer()->text->cursor;
1713                 setMessage(N_("Mark on"));
1714                 break;
1715                 
1716         case LFUN_BACKSPACE:
1717         {
1718                 FreeUpdateTimer();
1719                 if (!owner->currentBuffer()->text->selection) {
1720                         if (owner->getIntl()->getTrans()->backspace()) {
1721                                 owner->currentBuffer()->text->Backspace();
1722                                 owner->currentBuffer()->text->sel_cursor =
1723                                         owner->currentBuffer()->text->cursor;
1724                                 SmallUpdate(1);
1725                                 // It is possible to make it a lot faster still
1726                                 // just comment out the lone below...
1727                                 owner->currentView()->getScreen()->ShowCursor();
1728                         }
1729                 } else {
1730                         CutCB();
1731                 }
1732                 SetUpdateTimer();
1733         }
1734         break;
1735
1736         case LFUN_BACKSPACE_SKIP:
1737         {
1738                 // Reverse the effect of LFUN_BREAKPARAGRAPH_SKIP.
1739                 
1740                 LyXCursor cursor = owner->currentBuffer()->text->cursor;
1741                 
1742                 FreeUpdateTimer();
1743                 if (!owner->currentBuffer()->text->selection) {
1744                         if (cursor.pos == 0 
1745                             && !(cursor.par->added_space_top 
1746                                  == VSpace (VSpace::NONE))) {
1747                                 owner->currentBuffer()->text->SetParagraph 
1748                                         (cursor.par->line_top,      
1749                                          cursor.par->line_bottom,
1750                                          cursor.par->pagebreak_top, 
1751                                          cursor.par->pagebreak_bottom,
1752                                          VSpace(VSpace::NONE), cursor.par->added_space_bottom,
1753                                          cursor.par->align, 
1754                                          cursor.par->labelwidthstring, 0);
1755                                 owner->currentBuffer()->update (1);
1756                         } else {
1757                                 owner->currentBuffer()->text->Backspace();
1758                                 owner->currentBuffer()->text->sel_cursor 
1759                                         = cursor;
1760                                 SmallUpdate (1);
1761                         }
1762                 } else
1763                         CutCB();
1764                 SetUpdateTimer();
1765         }
1766         break;
1767
1768         case LFUN_BREAKPARAGRAPH:
1769         {
1770                 BeforeChange();
1771                 owner->currentBuffer()->text->BreakParagraph(0);
1772                 SmallUpdate(1);
1773                 SetUpdateTimer(0.01);
1774                 owner->currentBuffer()->text->sel_cursor =
1775                         owner->currentBuffer()->text->cursor;
1776                 break;
1777         }
1778
1779         case LFUN_BREAKPARAGRAPHKEEPLAYOUT:
1780         {
1781                 BeforeChange();
1782                 owner->currentBuffer()->text->BreakParagraph(1);
1783                 SmallUpdate(1);
1784                 SetUpdateTimer(0.01);
1785                 owner->currentBuffer()->text->sel_cursor =
1786                         owner->currentBuffer()->text->cursor;
1787                 break;
1788         }
1789         
1790         case LFUN_BREAKPARAGRAPH_SKIP:
1791         {
1792                 // When at the beginning of a paragraph, remove
1793                 // indentation and add a "defskip" at the top.
1794                 // Otherwise, do the same as LFUN_BREAKPARAGRAPH.
1795                 
1796                 LyXCursor cursor = owner->currentBuffer()->text->cursor;
1797                 
1798                 BeforeChange();
1799                 if (cursor.pos == 0) {
1800                         if (cursor.par->added_space_top == VSpace(VSpace::NONE)) {
1801                                 owner->currentBuffer()->text->SetParagraph
1802                                         (cursor.par->line_top,      
1803                                          cursor.par->line_bottom,
1804                                          cursor.par->pagebreak_top, 
1805                                          cursor.par->pagebreak_bottom,
1806                                          VSpace(VSpace::DEFSKIP), cursor.par->added_space_bottom,
1807                                          cursor.par->align, 
1808                                          cursor.par->labelwidthstring, 1);
1809                                 owner->currentBuffer()->update(1);
1810                         } 
1811                 }
1812                 else {
1813                         owner->currentBuffer()->text->BreakParagraph(0);
1814                         SmallUpdate(1);
1815                 }
1816                 SetUpdateTimer(0.01);
1817                 owner->currentBuffer()->text->sel_cursor = cursor;
1818         }
1819         break;
1820         
1821         case LFUN_QUOTE:
1822                 BeforeChange();
1823                 owner->currentBuffer()->text->InsertChar('\"');  // This " matches the single quote in the code
1824                 SmallUpdate(1);
1825                 SetUpdateTimer();
1826                 moveCursorUpdate(false);
1827                 break;
1828
1829         case LFUN_HTMLURL:
1830         case LFUN_URL:
1831         {
1832                 InsetCommand *new_inset;
1833                 if (action == LFUN_HTMLURL)
1834                         new_inset = new InsetUrl("htmlurl", "", "");
1835                 else
1836                         new_inset = new InsetUrl("url", "", "");
1837                 owner->currentBuffer()->insertInset(new_inset);
1838                 new_inset->Edit(0, 0);
1839         }
1840         break;
1841
1842         // --- lyxserver commands ----------------------------
1843
1844         case LFUN_CHARATCURSOR:
1845         {
1846                 int pos = owner->currentBuffer()->text->cursor.pos;
1847                 if(pos < owner->currentBuffer()->text->cursor.par->last)
1848                         dispatch_buffer = owner->currentBuffer()->text->
1849                                 cursor.par->text[pos];
1850                 else
1851                         dispatch_buffer = "EOF";
1852         }
1853         break;
1854         
1855         case LFUN_GETXY:
1856                 dispatch_buffer = LString()
1857                         + owner->currentBuffer()->text->cursor.x + ' '
1858                         + owner->currentBuffer()->text->cursor.y;
1859                 break;
1860                 
1861         case LFUN_SETXY:
1862         {
1863                 int  x;
1864                 long y;
1865                 sscanf(argument, " %d %ld", &x, &y);
1866                 owner->currentBuffer()->text->SetCursorFromCoordinates(x, y);
1867         }
1868         break;
1869         
1870         case LFUN_GETLAYOUT:
1871                 dispatch_buffer = LString() + 
1872                         int(owner->currentBuffer()->text->cursor.par->layout);
1873                 break;
1874                         
1875         case LFUN_GETFONT:
1876         {
1877                 LyXFont *font = &(owner->currentBuffer()->text->current_font);
1878                 if(font->shape() == LyXFont::ITALIC_SHAPE)
1879                         dispatch_buffer = 'E';
1880                 else if(font->shape() == LyXFont::SMALLCAPS_SHAPE)
1881                         dispatch_buffer = 'N';
1882                 else
1883                         dispatch_buffer = '0';
1884
1885         }
1886         break;
1887
1888         case LFUN_GETLATEX:
1889         {
1890                 LyXFont *font = &(owner->currentBuffer()->text->current_font);
1891                 if(font->latex() == LyXFont::ON)
1892                         dispatch_buffer = 'L';
1893                 else
1894                         dispatch_buffer = '0';
1895         }
1896         break;
1897
1898         case LFUN_GETNAME:
1899                 setMessage(owner->currentBuffer()->getFileName());
1900                 lyxerr.debug(LString("FNAME[") +
1901                              owner->currentBuffer()->getFileName() +
1902                              "] ");
1903                 break;
1904                 
1905         case LFUN_NOTIFY:
1906         {
1907                 char buf[100];
1908                 keyseq.print(buf,100);
1909                 dispatch_buffer = buf;
1910                 lyxserver->notifyClient(dispatch_buffer);
1911         }
1912         break;
1913
1914         case LFUN_GOTOFILEROW:
1915         {
1916                 char file_name[100];
1917                 int  row;
1918                 sscanf(argument, " %s %d", file_name, &row);
1919
1920                 // Must replace extension of the file to be .lyx and get full path
1921                 LString s = ChangeExtension(LString(file_name), ".lyx", false);
1922
1923                 // Either change buffer or load the file
1924                 if (bufferlist.exists(s))
1925                         owner->currentView()->setBuffer(bufferlist.getBuffer(s));
1926                 else
1927                         owner->currentView()->setBuffer(bufferlist.loadLyXFile(s));
1928
1929                 // Set the cursor  
1930                 owner->currentBuffer()->setCursorFromRow(row);
1931
1932                 // Recenter screen
1933                 BeforeChange();
1934                 if (owner->currentBuffer()->text->cursor.y >
1935                     owner->currentView()->getWorkArea()->h / 2) {
1936                         owner->currentView()->getScreen()->
1937                                 Draw(owner->currentBuffer()->text->cursor.y -
1938                                      owner->currentView()->getWorkArea()->h/2);
1939                 } else { // <=
1940                         owner->currentView()->getScreen()->
1941                                 Draw(0);
1942                 }
1943                 owner->currentBuffer()->update(0);
1944                 owner->currentView()->redraw();
1945         }
1946         break;
1947
1948         case LFUN_APROPOS:
1949         case LFUN_GETTIP:
1950         {
1951                 int qa = lyxaction.LookupFunc((const char*)argument);
1952                 setMessage(lyxaction.helpText((kb_action)qa));
1953         }
1954         break;
1955
1956         // --- accented characters ---------------------------
1957                 
1958         case LFUN_UMLAUT:
1959         case LFUN_CIRCUMFLEX:
1960         case LFUN_GRAVE:
1961         case LFUN_ACUTE:
1962         case LFUN_TILDE:
1963         case LFUN_CEDILLA:
1964         case LFUN_MACRON:
1965         case LFUN_DOT:
1966         case LFUN_UNDERDOT:
1967         case LFUN_UNDERBAR:
1968         case LFUN_CARON:
1969         case LFUN_SPECIAL_CARON:
1970         case LFUN_BREVE:
1971         case LFUN_TIE:
1972         case LFUN_HUNG_UMLAUT:
1973         case LFUN_CIRCLE:
1974         case LFUN_OGONEK:
1975         {
1976                 char c;
1977                 
1978                 if (keyseq.length==-1 && keyseq.getiso()!=0) 
1979                         c=keyseq.getiso();
1980                 else
1981                         c=0;
1982                 
1983                 owner->getIntl()->getTrans()->
1984                         deadkey(c, get_accent(action).accent, 
1985                                 owner->currentBuffer()->text);
1986                 
1987                 // Need to reset, in case the minibuffer calls these
1988                 // actions
1989                 keyseq.reset();
1990                 keyseq.length=0;
1991                 
1992                 // copied verbatim from do_accent_char
1993                 SmallUpdate(1);
1994                 SetUpdateTimer();
1995                 owner->currentBuffer()->text->sel_cursor = 
1996                         owner->currentBuffer()->text->cursor;
1997         }   
1998         break;
1999         
2000         // --- toolbar ----------------------------------
2001         case LFUN_PUSH_TOOLBAR:
2002         {
2003                 int nth = atoi(argument);
2004                 if (lyxerr.debugging(Error::TOOLBAR)) {
2005                         lyxerr.print(LString("LFUN_PUSH_TOOLBAR: argument = `")
2006                                      + argument + "'");
2007                         lyxerr.print(LString("LFUN_PUSH_TOOLBAR: nth = `")
2008                                      + nth + "'");
2009                 }
2010                 
2011                 if (nth <= 0) {
2012                         LyXBell();
2013                         setErrorMessage(N_("Push-toolbar needs argument > 0"));
2014                 } else {
2015                         owner->getToolbar()->push(nth);
2016                 }
2017         }
2018         break;
2019         
2020         case LFUN_ADD_TO_TOOLBAR:
2021         {
2022                 if (lyxerr.debugging(Error::TOOLBAR)) {
2023                         lyxerr.print(LString("LFUN_ADD_TO_TOOLBAR:"
2024                                              "argument = `")+ argument + '\'');
2025                 }
2026                 LString tmp(argument);
2027                 //lyxerr.print(LString("Argument: ") + argument);
2028                 //lyxerr.print(LString("Tmp     : ") + tmp);
2029                 if (tmp.empty()) {
2030                         LyXBell();
2031                         setErrorMessage(N_("Usage: toolbar-add-to <LyX command>"));
2032                 } else {
2033                         owner->getToolbar()->add(argument, false);
2034                         owner->getToolbar()->set();
2035                 }
2036         }
2037         break;
2038         
2039         // --- insert characters ----------------------------------------
2040
2041         case LFUN_INSERT_INSET_LATEX:
2042         {
2043                 Inset *new_inset = new InsetLatex(argument);
2044                 owner->currentBuffer()->insertInset(new_inset);
2045         }
2046         break;
2047
2048         // ---  Mathed stuff. If we are here, there is no locked inset yet.
2049         
2050         // Greek mode     
2051         case LFUN_GREEK:
2052         {
2053                 if (!greek_kb_flag) {
2054                         greek_kb_flag = 1;
2055                         setMessage(N_("Math greek mode on"));
2056                 } else
2057                         greek_kb_flag = 0;
2058         }  
2059         break;
2060       
2061         // Greek keyboard      
2062         case LFUN_GREEK_TOGGLE:
2063         {
2064                 greek_kb_flag = (greek_kb_flag) ? 0: 2;
2065                 if (greek_kb_flag) {
2066                         setMessage(N_("Math greek keyboard on"));
2067                 } else {
2068                         setMessage(N_("Math greek keyboard off"));
2069                 }
2070         }
2071         break;
2072         
2073         case LFUN_MATH_DELIM:     
2074         case LFUN_INSERT_MATRIX:
2075         {          
2076                 if (owner->currentView()->available()) { 
2077                         owner->currentBuffer()->
2078                                 open_new_inset(new InsetFormula(false));
2079                         owner->currentBuffer()->
2080                                 the_locking_inset->LocalDispatch(action, argument);
2081                 }
2082         }          
2083         break;
2084                
2085         case LFUN_INSERT_MATH:
2086         {
2087                 math_insert_symbol(argument);
2088         }
2089         break;
2090         
2091         case LFUN_MATH_DISPLAY:
2092         {
2093                 if (owner->currentView()->available())
2094                         owner->currentBuffer()->open_new_inset(new InsetFormula(true));
2095                 break;
2096         }
2097                     
2098         case LFUN_MATH_MACRO:
2099         {
2100                 if (owner->currentView()->available()) {
2101                         LString s(argument);
2102                         if (s.empty())
2103                             setErrorMessage(N_("Missing argument"));
2104                         else {
2105                             LString s1 = s.token(' ', 1);
2106                             int na = s1.empty() ? 0: atoi(s1.c_str());
2107                             owner->currentBuffer()->
2108                               open_new_inset(new InsetFormulaMacro(s.token(' ', 0), na));
2109                         }
2110                 }
2111         }
2112         break;
2113
2114         case LFUN_MATH_MODE:   // Open or create a math inset
2115         {
2116                 
2117                 if (owner->currentView()->available())
2118                         owner->currentBuffer()->open_new_inset(new InsetFormula);
2119                 setMessage(N_("Math editor mode"));
2120         }
2121         break;
2122           
2123         case LFUN_MATH_NUMBER:
2124         case LFUN_MATH_LIMITS:
2125         {
2126                 setErrorMessage(N_("This is only allowed in math mode!"));
2127         }
2128         break;
2129         
2130         case LFUN_INSERT_CITATION:
2131         {   
2132                 InsetCitation *new_inset = new InsetCitation();
2133                 // ale970405
2134                 // The note, if any, must be after the key, delimited
2135                 // by a | so both key and remark can have spaces.
2136                 if (argument) {
2137                         LString lsarg(argument);
2138                         if (lsarg.contains("|")) {
2139                                 new_inset->setContents(lsarg.token('|', 0));
2140                                 new_inset->setOptions(lsarg.token('|', 1));
2141                         } else
2142                                 new_inset->setContents(lsarg);
2143                         owner->currentBuffer()->insertInset(new_inset);
2144                 } else {
2145                         owner->currentBuffer()->insertInset(new_inset);
2146                         new_inset->Edit(0,0);
2147                 }
2148         }
2149         break;
2150                     
2151         case LFUN_INSERT_BIBTEX:
2152         {   
2153                 // ale970405+lasgoutt970425
2154                 // The argument can be up to two tokens separated 
2155                 // by a space. The first one is the bibstyle.
2156                 LString lsarg(argument);
2157                 LString bibstyle = lsarg.token(' ', 1);
2158                 if (bibstyle.empty())
2159                         bibstyle = "plain";
2160                 InsetBibtex *new_inset 
2161                         = new InsetBibtex(lsarg.token(' ', 0),
2162                                           bibstyle,
2163                                           owner->currentBuffer());
2164                 
2165                 owner->currentBuffer()->insertInset(new_inset);
2166                 if (lsarg.empty()) {
2167                         new_inset->Edit(0,0);
2168                 }
2169         }
2170         break;
2171                 
2172         // BibTeX data bases
2173         case LFUN_BIBDB_ADD:
2174         {
2175                 InsetBibtex *inset =
2176                         (InsetBibtex*)getInsetByCode(Inset::BIBTEX_CODE);
2177                 if (inset) {
2178                         inset->addDatabase(argument);
2179                 }
2180         }
2181         break;
2182                     
2183         case LFUN_BIBDB_DEL:
2184         {
2185                 InsetBibtex *inset =
2186                         (InsetBibtex*)getInsetByCode(Inset::BIBTEX_CODE);
2187                 if (inset) {
2188                         inset->delDatabase(argument);
2189                 }
2190         }
2191         break;
2192         
2193         case LFUN_BIBTEX_STYLE:
2194         {
2195                 InsetBibtex *inset =
2196                         (InsetBibtex*)getInsetByCode(Inset::BIBTEX_CODE);
2197                 if (inset) {
2198                         inset->setOptions(argument);
2199                 }
2200         }
2201         break;
2202                 
2203         case LFUN_INDEX_INSERT:
2204         case LFUN_INDEX_INSERT_LAST:
2205         {
2206                 InsetIndex *new_inset = new InsetIndex();
2207                 if (argument) {
2208                         LString lsarg(argument);
2209                         new_inset->setContents(lsarg);
2210                         owner->currentBuffer()->insertInset(new_inset);
2211                 } else {
2212                   //reh 98/09/21
2213                   //get the current word for an argument
2214                   
2215                   
2216                   // grab a word
2217
2218                   int lastpos =owner->currentBuffer()->text->cursor.pos-1;
2219
2220                   //this shouldn't happen, but let's be careful
2221                   if (lastpos < 0) lastpos=0;
2222                   
2223                   // get the current word
2224                   // note that this must be done before 
2225                   // inserting the inset, or the inset will break
2226                   // the word
2227                   LString curstring(owner->currentBuffer()->text->cursor.par->GetWord(lastpos));
2228
2229                   //make the new inset and write the current word into it
2230                   InsetIndex *new_inset = new InsetIndex();
2231
2232                   new_inset->setContents(curstring);
2233
2234                   //don't edit it if the call was to INSERT_LAST
2235                   if(action!=LFUN_INDEX_INSERT_LAST) {
2236                       new_inset->Edit(0,0);
2237                   } else {
2238                       //it looks blank on the screen unless
2239                       //we do  something.  put it here.
2240
2241                       // move the cursor to the returned value of lastpos
2242                       // but only for the auto-insert
2243                       owner->currentBuffer()->text->cursor.pos=lastpos;
2244                   }
2245
2246                   //put the new inset into the buffer.
2247                   // there should be some way of knowing the user
2248                   //cancelled & avoiding this, but i don't know how
2249                   owner->currentBuffer()->insertInset(new_inset);
2250                 }
2251         }
2252         break;
2253
2254         case LFUN_INDEX_PRINT:
2255         {
2256                 Inset *new_inset = new InsetPrintIndex(owner->currentBuffer());
2257                 owner->currentBuffer()->insertInset(new_inset, "Standard", true);
2258         }
2259         break;
2260
2261         case LFUN_PARENTINSERT:
2262         {
2263                 lyxerr.print(LString("arg ") + argument);
2264                 Inset *new_inset = new InsetParent(argument, owner->currentBuffer());
2265                 owner->currentBuffer()->insertInset(new_inset, "Standard", true);
2266         }
2267         break;
2268
2269         case LFUN_CHILDINSERT:
2270         {
2271                 Inset *new_inset = new InsetInclude(argument,owner->currentBuffer());
2272                 owner->currentBuffer()->insertInset(new_inset, "Standard", true);
2273                 new_inset->Edit(0,0);
2274         }
2275         break;
2276
2277         case LFUN_CHILDOPEN:
2278         {
2279                 LString filename = MakeAbsPath(argument, 
2280                                                OnlyPath(owner->currentBuffer()->getFileName()));
2281                 setMessage(N_("Opening child document ") +
2282                            MakeDisplayPath(filename) + "...");
2283                 owner->currentView()->savePosition();
2284                 if (bufferlist.exists(filename))
2285                   owner->currentView()->setBuffer(bufferlist.getBuffer(filename));
2286                 else
2287                   owner->currentView()->setBuffer(bufferlist.loadLyXFile(filename));
2288         }
2289         break;
2290
2291         case LFUN_INSERT_NOTE:
2292                 NoteCB();
2293                 break;
2294                 
2295         case LFUN_INSERTFOOTNOTE: 
2296         {
2297                 LyXParagraph::footnote_kind kind;
2298                 LString arg = argument;
2299                 if (arg == "footnote")
2300                         { kind = LyXParagraph::FOOTNOTE; }
2301                 else if (arg == "margin")
2302                         { kind = LyXParagraph::MARGIN; }
2303                 else if (arg == "figure")
2304                         { kind = LyXParagraph::FIG; }
2305                 else if (arg == "table")
2306                         { kind = LyXParagraph::TAB; }
2307                 else if (arg == "wide-fig")
2308                         { kind = LyXParagraph::WIDE_FIG; }
2309                 else if (arg == "wide-tab")
2310                         { kind = LyXParagraph::WIDE_TAB; }
2311                 else if (arg == "algorithm")
2312                         { kind = LyXParagraph::ALGORITHM; }
2313                 else {
2314                         setErrorMessage(N_("Unknown kind of footnote"));
2315                         break;
2316                 }
2317                 owner->currentBuffer()->text->InsertFootnoteEnvironment(kind);
2318                 owner->currentBuffer()->update(1);
2319         }
2320         break;
2321         
2322         case LFUN_BUFFERBULLETSSELECT:
2323                 bulletForm();
2324                 break;
2325                 
2326         case LFUN_TOGGLECURSORFOLLOW:
2327                 cursor_follows_scrollbar = !cursor_follows_scrollbar;
2328                 break;
2329                 
2330         case LFUN_KMAP_OFF:             // keymap off
2331                 owner->getIntl()->KeyMapOn(false);
2332                 break;
2333                 
2334         case LFUN_KMAP_PRIM:    // primary keymap
2335                 owner->getIntl()->KeyMapPrim();
2336                 break;
2337                 
2338         case LFUN_KMAP_SEC:             // secondary keymap
2339                 owner->getIntl()->KeyMapSec();
2340                 break;
2341                 
2342         case LFUN_KMAP_TOGGLE:  // toggle keymap
2343                 owner->getIntl()->ToggleKeyMap();
2344                 break;
2345
2346         case LFUN_SELFINSERT:
2347         {
2348                 LString const text = argument;
2349                 for (int i=0; i<text.length(); i++) {
2350                         owner->currentBuffer()->text->InsertChar(text[i]);
2351                         // This needs to be in the loop, or else we
2352                         // won't break lines correctly. (Asger)
2353                         SmallUpdate(1);
2354                 }
2355                 SetUpdateTimer();
2356                 owner->currentBuffer()->text->sel_cursor =
2357                         owner->currentBuffer()->text->cursor;
2358                 moveCursorUpdate(false);
2359         }
2360         break;
2361
2362         case LFUN_UNKNOWN_ACTION:
2363         {
2364                 if (owner->currentBuffer()->isReadonly()) {
2365                         LyXBell();
2366                         setErrorMessage(N_("Document is read only"));
2367                         break;
2368                 }
2369                          
2370                 if (argument) {
2371                         
2372                         /* Automatically delete the currently selected
2373                          * text and replace it with what is being
2374                          * typed in now. Depends on lyxrc settings
2375                          * "auto_region_delete", which defaults to
2376                          * true (on). */
2377                 
2378                         if ( lyxrc->auto_region_delete ) {
2379                                 if (owner->currentBuffer()->text->selection){
2380                                         owner->currentBuffer()->text->CutSelection(false);
2381                                         owner->currentBuffer()->update(-1);
2382                                 }
2383                         }
2384                         
2385                         BeforeChange();
2386                         for(char const *p = argument; *p; p++) {
2387                                 if (greek_kb_flag) {
2388                                         if (!math_insert_greek(*p))
2389                                                 owner->getIntl()->getTrans()->TranslateAndInsert(*p, owner->currentBuffer()->text);
2390                                 } else
2391                                         owner->getIntl()->getTrans()->TranslateAndInsert(*p, owner->currentBuffer()->text);
2392                         }
2393                         
2394                         SmallUpdate(1);
2395                         SetUpdateTimer();
2396
2397                         owner->currentBuffer()->text->sel_cursor =
2398                                 owner->currentBuffer()->text->cursor;
2399                         moveCursorUpdate(false);
2400                         return LString();
2401                 } else {
2402                         // why is an "Unknown action" with empty
2403                         // argument even dispatched in the first
2404                         // place? I`ll probably change that. (Lgb)
2405                         LyXBell();
2406                         setErrorMessage(N_("Unknown action"));
2407                 }
2408                 break;
2409         default:
2410                 lyxerr.print("A truly unknown func!");
2411                 break;
2412         }
2413         } // end of switch
2414   exit_with_message:
2415
2416         LString res=getMessage();
2417
2418         if (res.empty()) {
2419                 if (!commandshortcut.empty()) {
2420                         LString newbuf = owner->getMiniBuffer()->GetText();
2421                         if (newbuf != commandshortcut) {
2422                                 owner->getMiniBuffer()->Set(newbuf
2423                                                             + " " +
2424                                                             commandshortcut);
2425                         }
2426                 }
2427         } else {
2428                 owner->getMiniBuffer()->Set(LString(_(res.c_str()))
2429                                             + " " + commandshortcut);
2430         }
2431
2432         return getMessage();
2433 }
2434             
2435
2436 void LyXFunc::setupLocalKeymap()
2437 {
2438         keyseq.stdmap = keyseq.curmap = toplevel_keymap;
2439         cancel_meta_seq.stdmap = cancel_meta_seq.curmap = toplevel_keymap;
2440 }
2441
2442
2443 void LyXFunc::MenuNew(bool fromTemplate)
2444 {
2445         LString fname, initpath = lyxrc->document_path;
2446         LyXFileDlg fileDlg;
2447
2448         if (owner->currentView()->available()) {
2449                 LString trypath = owner->currentBuffer()->filepath;
2450                 // If directory is writeable, use this as default.
2451                 if (IsDirWriteable(trypath) == 1)
2452                         initpath = trypath;
2453         }
2454
2455         ProhibitInput();
2456         fileDlg.SetButton(0, _("Documents"), lyxrc->document_path);
2457         fileDlg.SetButton(1, _("Templates"), lyxrc->template_path);
2458         fname = fileDlg.Select(_("Enter Filename for new document"), 
2459                                initpath, "*.lyx", _("newfile"));
2460         AllowInput();
2461         
2462         if (fname.empty()) {
2463                 owner->getMiniBuffer()->Set(_("Canceled."));
2464                 lyxerr.debug("New Document Cancelled.");
2465                 return;
2466         }
2467         
2468         // get absolute path of file and make sure the filename ends
2469         // with .lyx
2470         LString s = MakeAbsPath(fname);
2471         if (!IsLyXFilename(s))
2472                 s += ".lyx";
2473
2474         // Check if the document already is open
2475         if (bufferlist.exists(s)){
2476                 switch(AskConfirmation(_("Document is already open:"), 
2477                                        MakeDisplayPath(s,50),
2478                                        _("Do you want to close that document now?\n"
2479                                          "('No' will just switch to the open version)")))
2480                 {
2481                 case 1: // Yes: close the document
2482                         if (!bufferlist.close(bufferlist.getBuffer(s)))
2483                                 // If close is canceled, we cancel here too.
2484                                 return;
2485                         break;
2486                 case 2: // No: switch to the open document
2487                         owner->currentView()->setBuffer(bufferlist.getBuffer(s));
2488                         return;
2489                 case 3: // Cancel: Do nothing
2490                         owner->getMiniBuffer()->Set(_("Canceled."));
2491                         return;
2492                 }
2493         }
2494         
2495         // Check whether the file already exists
2496         if (IsLyXFilename(s)) {
2497                 FilePtr myfile(s, FilePtr::read);
2498                 if (myfile() &&
2499                     AskQuestion(_("File already exists:"), 
2500                                 MakeDisplayPath(s,50),
2501                                 _("Do you want to open the document?"))) {
2502                         // loads document
2503                         owner->getMiniBuffer()->Set(_("Opening document"), 
2504                                                     MakeDisplayPath(s), "...");
2505                         XFlush(fl_display);
2506                         owner->currentView()->setBuffer(
2507                                 bufferlist.loadLyXFile(s));
2508                         owner->getMiniBuffer()->Set(_("Document"),
2509                                                     MakeDisplayPath(s),
2510                                                     _("opened."));
2511                         return;
2512                 }
2513         }
2514
2515         // The template stuff
2516         LString templname;
2517         if (fromTemplate) {
2518                 ProhibitInput();
2519                 fname = fileDlg.Select(_("Choose template"),
2520                                        lyxrc->template_path,
2521                                        "*.lyx");
2522                 templname = fname;
2523                 AllowInput();
2524         }
2525   
2526         // find a free buffer
2527         lyxerr.debug("Find a free buffer.");
2528         owner->currentView()->setBuffer(bufferlist.newFile(s,templname));
2529 }
2530
2531
2532 void LyXFunc::MenuOpen()
2533 {
2534         LString initpath = lyxrc->document_path;
2535         LyXFileDlg fileDlg;
2536   
2537         if (owner->currentView()->available()) {
2538                 LString trypath = owner->currentBuffer()->filepath;
2539                 // If directory is writeable, use this as default.
2540                 if (IsDirWriteable(trypath) == 1)
2541                         initpath = trypath;
2542         }
2543
2544         // launches dialog
2545         ProhibitInput();
2546         fileDlg.SetButton(0, _("Documents"), lyxrc->document_path);
2547         fileDlg.SetButton(1, _("Examples"), 
2548                           AddPath(system_lyxdir, "examples"));
2549         LString filename = fileDlg.Select(_("Select Document to Open"),
2550                                           initpath, "*.lyx");
2551         AllowInput();
2552  
2553         // check selected filename
2554         if (filename.empty()) {
2555                 owner->getMiniBuffer()->Set(_("Canceled."));
2556                 return;
2557         }
2558
2559         // get absolute path of file and make sure the filename ends
2560         // with .lyx
2561         filename = MakeAbsPath(filename);
2562         if (!IsLyXFilename(filename))
2563                 filename += ".lyx";
2564
2565         // loads document
2566         owner->getMiniBuffer()->Set(_("Opening document"),
2567                                     MakeDisplayPath(filename), "...");
2568         Buffer * openbuf = bufferlist.loadLyXFile(filename);
2569         if (openbuf) {
2570                 owner->currentView()->setBuffer(openbuf);
2571                 owner->getMiniBuffer()->Set(_("Document"),
2572                                             MakeDisplayPath(filename),
2573                                             _("opened."));
2574         } else {
2575                 owner->getMiniBuffer()->Set(_("Could not open document"),
2576                                             MakeDisplayPath(filename));
2577         }
2578 }
2579
2580
2581 void LyXFunc::doImportASCII(bool linorpar)
2582 {
2583         LString initpath = lyxrc->document_path;
2584         LyXFileDlg fileDlg;
2585   
2586         if (owner->currentView()->available()) {
2587                 LString trypath = owner->currentBuffer()->filepath;
2588                 // If directory is writeable, use this as default.
2589                 if (IsDirWriteable(trypath) == 1)
2590                         initpath = trypath;
2591         }
2592
2593         // launches dialog
2594         ProhibitInput();
2595         fileDlg.SetButton(0, _("Documents"), lyxrc->document_path);
2596         fileDlg.SetButton(1, _("Examples"), 
2597                           AddPath(system_lyxdir, "examples"));
2598         LString filename = fileDlg.Select(_("Select ASCII file to Import"),
2599                                           initpath, "*.txt");
2600         AllowInput();
2601  
2602         // check selected filename
2603         if (filename.empty()) {
2604                 owner->getMiniBuffer()->Set(_("Canceled."));
2605                 return;
2606         }
2607
2608         // get absolute path of file
2609         filename = MakeAbsPath(filename);
2610
2611         LString s = ChangeExtension(filename, ".lyx", false);
2612
2613         // Check if the document already is open
2614         if (bufferlist.exists(s)){
2615                 switch(AskConfirmation(_("Document is already open:"), 
2616                                        MakeDisplayPath(s,50),
2617                                        _("Do you want to close that document now?\n"
2618                                          "('No' will just switch to the open version)")))
2619                 {
2620                 case 1: // Yes: close the document
2621                         if (!bufferlist.close(bufferlist.getBuffer(s)))
2622                                 // If close is canceled, we cancel here too.
2623                                 return;
2624                         break;
2625                 case 2: // No: switch to the open document
2626                         owner->currentView()->setBuffer(bufferlist.getBuffer(s));
2627                         return;
2628                 case 3: // Cancel: Do nothing
2629                         owner->getMiniBuffer()->Set(_("Canceled."));
2630                         return;
2631                 }
2632         }
2633
2634         // Check if a LyX document by the same root exists in filesystem
2635         FileInfo f(s, true);
2636         if (f.exist() && !AskQuestion(_("A document by the name"), 
2637                                       MakeDisplayPath(s),
2638                                       _("already exists. Overwrite?"))) {
2639                 owner->getMiniBuffer()->Set(_("Canceled."));
2640                 return;
2641         }
2642
2643         owner->currentView()->setBuffer(bufferlist.newFile(s,LString()));
2644         owner->getMiniBuffer()->Set(_("Importing ASCII file"),
2645                                     MakeDisplayPath(filename), "...");
2646         // Insert ASCII file
2647         InsertAsciiFile(filename,linorpar);
2648         owner->getMiniBuffer()->Set(_("ASCII file "),
2649                                     MakeDisplayPath(filename),
2650                                     _("imported."));
2651 }
2652
2653
2654 void LyXFunc::doImportLaTeX(bool isnoweb)
2655 {
2656         LString initpath = lyxrc->document_path;
2657         LyXFileDlg fileDlg;
2658   
2659         if (owner->currentView()->available()) {
2660                 LString trypath = owner->currentBuffer()->filepath;
2661                 // If directory is writeable, use this as default.
2662                 if (IsDirWriteable(trypath) == 1)
2663                         initpath = trypath;
2664         }
2665
2666         // launches dialog
2667         ProhibitInput();
2668         fileDlg.SetButton(0, _("Documents"), lyxrc->document_path);
2669         fileDlg.SetButton(1, _("Examples"), 
2670                           AddPath(system_lyxdir, "examples"));
2671         LString filename;
2672         if (isnoweb) {
2673                 filename = fileDlg.Select(_("Select Noweb file to Import"),
2674                                           initpath, "*.nw");
2675         } else {
2676                 filename = fileDlg.Select(_("Select LaTeX file to Import"),
2677                                           initpath, "*.tex");
2678         }
2679         
2680         AllowInput();
2681  
2682         // check selected filename
2683         if (filename.empty()) {
2684                 owner->getMiniBuffer()->Set(_("Canceled."));
2685                 return;
2686         }
2687
2688         // get absolute path of file
2689         filename = MakeAbsPath(filename);
2690
2691         // Check if the document already is open
2692         LString LyXfilename = ChangeExtension(filename, ".lyx", false);
2693         if (bufferlist.exists(LyXfilename)){
2694                 switch(AskConfirmation(_("Document is already open:"), 
2695                                        MakeDisplayPath(LyXfilename,50),
2696                                        _("Do you want to close that document now?\n"
2697                                          "('No' will just switch to the open version)")))
2698                 {
2699                 case 1: // Yes: close the document
2700                         if (!bufferlist.close(bufferlist.getBuffer(LyXfilename)))
2701                                 // If close is canceled, we cancel here too.
2702                                 return;
2703                         break;
2704                 case 2: // No: switch to the open document
2705                         owner->currentView()->setBuffer(
2706                                 bufferlist.getBuffer(LyXfilename));
2707                         return;
2708                 case 3: // Cancel: Do nothing
2709                         owner->getMiniBuffer()->Set(_("Canceled."));
2710                         return;
2711                 }
2712         }
2713
2714         // Check if a LyX document by the same root exists in filesystem
2715         FileInfo f(LyXfilename, true);
2716         if (f.exist() && !AskQuestion(_("A document by the name"), 
2717                                       MakeDisplayPath(LyXfilename),
2718                                       _("already exists. Overwrite?"))) {
2719                 owner->getMiniBuffer()->Set(_("Canceled."));
2720                 return;
2721         }
2722
2723         // loads document
2724         Buffer * openbuf;
2725         if (!isnoweb) {
2726                 owner->getMiniBuffer()->Set(_("Importing LaTeX file"),
2727                                             MakeDisplayPath(filename), "...");
2728                 ImportLaTeX myImport(filename);
2729                 openbuf = myImport.run();
2730         } else {
2731                 owner->getMiniBuffer()->Set(_("Importing Noweb file"),
2732                                             MakeDisplayPath(filename), "...");
2733                 ImportNoweb myImport(filename);
2734                 openbuf = myImport.run();
2735         }
2736         if (openbuf) {
2737                 owner->currentView()->setBuffer(openbuf);
2738                 owner->getMiniBuffer()->Set(isnoweb ?
2739                                             _("Noweb file ") : _("LateX file "),
2740                                             MakeDisplayPath(filename),
2741                                             _("imported."));
2742         } else {
2743                 owner->getMiniBuffer()->Set(isnoweb ?
2744                                             _("Could not import Noweb file") :
2745                                             _("Could not import LaTeX file"),
2746                                             MakeDisplayPath(filename));
2747         }
2748 }
2749
2750
2751 void LyXFunc::MenuInsertLyXFile(LString const & filen)
2752 {
2753         LString filename = filen;
2754
2755         if (filename.empty()) {
2756                 // Launch a file browser
2757                 LString initpath = lyxrc->document_path;
2758                 LyXFileDlg fileDlg;
2759
2760                 if (owner->currentView()->available()) {
2761                         LString trypath = owner->currentBuffer()->filepath;
2762                         // If directory is writeable, use this as default.
2763                         if (IsDirWriteable(trypath) == 1)
2764                                 initpath = trypath;
2765                 }
2766
2767                 // launches dialog
2768                 ProhibitInput();
2769                 fileDlg.SetButton(0, _("Documents"), lyxrc->document_path);
2770                 fileDlg.SetButton(1, _("Examples"), 
2771                                   AddPath(system_lyxdir, "examples"));
2772                 filename = fileDlg.Select(_("Select Document to Insert"),
2773                                           initpath, "*.lyx");
2774                 AllowInput();
2775
2776                 // check selected filename
2777                 if (filename.empty()) {
2778                         owner->getMiniBuffer()->Set(_("Canceled."));
2779                         return;
2780                 }
2781         } 
2782
2783         // get absolute path of file and make sure the filename ends
2784         // with .lyx
2785         filename = MakeAbsPath(filename);
2786         if (!IsLyXFilename(filename))
2787                 filename += ".lyx";
2788
2789         // Inserts document
2790         owner->getMiniBuffer()->Set(_("Inserting document"),
2791                                     MakeDisplayPath(filename), "...");
2792         bool res = owner->currentBuffer()->insertLyXFile(filename);
2793         if (res) {
2794                 owner->getMiniBuffer()->Set(_("Document"),
2795                                             MakeDisplayPath(filename),
2796                                             _("inserted."));
2797         } else {
2798                 owner->getMiniBuffer()->Set(_("Could not insert document"),
2799                                             MakeDisplayPath(filename));
2800         }
2801 }
2802
2803
2804 void LyXFunc::reloadBuffer()
2805 {
2806         LString fn = owner->currentBuffer()->getFileName();
2807         if (bufferlist.close(owner->currentBuffer()))
2808                 owner->currentView()->setBuffer(bufferlist.loadLyXFile(fn));
2809 }
2810
2811
2812 void LyXFunc::CloseBuffer()
2813 {
2814         if (bufferlist.close(owner->currentBuffer()) && !quitting) {
2815                 if (bufferlist.isEmpty()) {
2816                         // need this otherwise SEGV may occur while trying to
2817                         // set variables that don't exist
2818                         // since there's no current buffer
2819                         CloseAllBufferRelatedPopups();
2820                 }
2821                 else {
2822                         owner->currentView()->setBuffer(bufferlist.first());
2823                 }
2824         }
2825 }
2826
2827
2828 Inset* LyXFunc::getInsetByCode(Inset::Code code)
2829 {
2830         bool found = false;
2831         Inset* inset = 0;
2832         LyXCursor cursor = owner->currentBuffer()->text->cursor;
2833         int pos = cursor.pos;
2834         LyXParagraph *par = cursor.par;
2835         
2836         while (par && !found) {
2837                 while ((inset = par->ReturnNextInsetPointer(pos))){
2838                         if (inset->LyxCode()==code) {
2839                                 found = true;
2840                                 break;
2841                         }
2842                         pos++;
2843                 } 
2844                 par = par->next;
2845         }
2846         return (found) ? inset: 0;
2847 }
2848
2849
2850 // Each "owner" should have it's own message method. lyxview and
2851 // the minibuffer would use the minibuffer, but lyxserver would
2852 // send an ERROR signal to its client.  Alejandro 970603
2853 // This func is bit problematic when it comes to NLS, to make the
2854 // lyx servers client be language indepenent we must not translate
2855 // strings sent to this func.
2856 void LyXFunc::setErrorMessage(LString const &m) 
2857 {
2858         dispatch_buffer = m;
2859         errorstat = true;
2860 }
2861
2862
2863 void LyXFunc::setMessage(LString const & m)
2864 {
2865         dispatch_buffer = m;
2866 }