]> git.lyx.org Git - features.git/blob - src/lyx_cb.C
Nuked the SpaceLess function. Read ChangeLog.
[features.git] / src / lyx_cb.C
1 /* This file is part of
2  * ====================================================== 
3  * 
4  *           LyX, The Document Processor
5  *       
6  *          Copyright 1995 Matthias Ettrich,
7  *          Copyright 1995-1999 The LyX Team.
8  *
9  * ====================================================== */
10
11 #include <config.h>
12
13 #include <cctype>
14 #include <unistd.h>
15 #include <csignal>
16 #include <cstring>
17 #include <cstdlib>
18
19 #include "LString.h"
20 #include "support/lstrings.h"
21 #include "lyx_main.h"
22 #include FORMS_H_LOCATION
23 #include "lyx.h"
24 #include "layout_forms.h"
25 #include "bullet_forms.h"
26 #include "print_form.h"
27 #include "form1.h"
28 #include "spellchecker.h"
29 #include "version.h"
30 #include "lyx_cb.h"
31 #include "credits.h"
32 #include "insets/insetref.h"
33 #include "insets/insetquotes.h"
34 #if 0
35 #include "insets/insetlatex.h"
36 #endif
37 #include "insets/insetlabel.h"
38 #include "insets/insetinfo.h"
39 #include "insets/insetspecialchar.h"
40 #include "insets/figinset.h"
41 #include "lyxfunc.h"
42 #include "latexoptions.h"
43 #include "lyxfont.h"
44 #include "minibuffer.h"
45 #include "combox.h"
46 #include "bufferlist.h"
47 #include "support/filetools.h"
48 #include "support/path.h"
49 #include "filedlg.h"
50 #include "lyx_gui_misc.h"
51 #include "LyXView.h" // only because of form_main
52 #include "lastfiles.h"
53 #include "support/FileInfo.h"
54 #include "lyxscreen.h"
55 #include "debug.h"
56 #include "support/syscall.h"
57 #include "support/lyxlib.h"
58 #include "lyxserver.h"
59 #include "FontLoader.h"
60 #include "lyxrc.h"
61 #include "lyxtext.h"
62 #include "gettext.h"
63 #include "layout.h"
64
65 extern MiniBuffer * minibuffer;
66 extern Combox * combo_language;
67 extern BufferList bufferlist;
68 extern void show_symbols_form();
69 extern FD_form_main * fd_form_main;
70 extern FD_form_title * fd_form_title;
71 extern FD_form_paragraph * fd_form_paragraph;
72 extern FD_form_character * fd_form_character;
73 extern FD_form_document * fd_form_document;
74 extern FD_form_quotes * fd_form_quotes;
75 extern FD_form_preamble * fd_form_preamble;
76 extern FD_form_table * fd_form_table;
77 extern FD_form_print * fd_form_print;
78 extern FD_form_figure * fd_form_figure;
79 extern FD_form_screen * fd_form_screen;
80 extern FD_form_toc * fd_form_toc;
81 extern FD_form_ref * fd_form_ref;
82 extern FD_LaTeXOptions * fd_latex_options;
83 extern FD_form_bullet * fd_form_bullet;
84
85 extern BufferView * current_view; // called too many times in this file...
86
87 extern void DeleteSimpleCutBuffer(); /* for the cleanup when exiting */
88
89 extern bool send_fax(string const & fname, string const & sendcmd);
90
91 extern LyXServer * lyxserver;
92 extern FontLoader fontloader;
93
94 // this should be static, but I need it in buffer.C
95 bool quitting;  // flag, that we are quitting the program
96 extern bool finished; // all cleanup done just let it run through now.
97
98 char ascii_type; /* for selection notify callbacks */
99
100 bool scrolling = false;
101
102 char updatetimer = 0;
103
104 /* whether the work area should get callbacks */ 
105 bool input_prohibited = false;
106
107 /* the selection possible is needed, that only motion events are 
108 * used, where the bottom press event was on the drawing area too */
109 bool selection_possible = false;
110
111 // This is used to make the dreaded font toggle problem hopefully go
112 // away. Definitely not the best solution, but I think it sorta works.
113 bool toggleall = true;
114
115 void InsertCorrectQuote();
116
117
118 /* 
119    This is the inset locking stuff needed for mathed --------------------
120
121    an inset can simple call LockInset in it's edit call and *ONLY* in it's
122    edit call.
123    Inset::Edit() can only be called by the main lyx module.
124
125    Then the inset may modify the menu's and/or iconbars. 
126
127    Unlocking is either done by LyX or the inset itself with a UnlockInset-call
128
129    During the lock, all button and keyboard events will be modified
130    and send to the inset through the following inset-features. Note that
131    Inset::InsetUnlock will be called from inside UnlockInset. It is meant
132    to contain the code for restoring the menus and things like this.
133
134    
135    virtual void InsetButtonPress(int x, int y, int button);
136    virtual void InsetButtonRelease(int x, int y, int button);
137    virtual void InsetKeyPress(XKeyEvent *ev);
138    virtual void InsetMotionNotify(int x, int y, int state);
139    virtual void InsetUnlock();
140
141    If a inset wishes any redraw and/or update it just has to call
142    UpdateInset(this).
143    It's is completly irrelevant, where the inset is. UpdateInset will
144    find it in any paragraph in any buffer. 
145    Of course the_locking_inset and the insets in the current paragraph/buffer
146    are checked first, so no performance problem should occur.
147    
148    Hope that's ok for the beginning, Alejandro,
149    sorry that I needed so much time,
150
151                   Matthias
152    */
153
154 void UpdateInset(Inset * inset, bool mark_dirty = true);
155 /* these functions return 1 if an error occured, 
156    otherwise 0 */
157 // Now they work only for updatable insets. [Alejandro 080596]
158 int LockInset(UpdatableInset * inset);
159 void ToggleLockedInsetCursor(long x, long y, int asc, int desc);
160 void FitLockedInsetCursor(long x, long y, int asc, int desc);
161 int UnlockInset(UpdatableInset * inset);
162 void LockedInsetStoreUndo(Undo::undo_kind kind);
163
164 /* this is for asyncron updating. UpdateInsetUpdateList will be called
165    automatically from LyX. Just insert the Inset into the Updatelist */
166 void UpdateInsetUpdateList();
167 void PutInsetIntoInsetUpdateList(Inset * inset);
168
169 InsetUpdateStruct * InsetUpdateList = 0;
170
171
172 /*
173   -----------------------------------------------------------------------
174  */
175
176 /* some function prototypes */
177
178 void GotoNote();
179 void OpenStuff();
180 void ToggleFloat();
181 void MenuUndo();
182 void MenuRedo();
183 void HyphenationPoint();
184 void MenuSeparator();
185 void HFill();
186 void Newline();
187 void ProtectedBlank();
188 void CopyCB();
189 int RunLinuxDoc(int, string const &);
190 int RunDocBook(int, string const &);
191 void MenuWrite(Buffer * buf);
192 void MenuWriteAs(Buffer * buffer);
193 void MenuReload(Buffer * buf);
194 void MenuLayoutSave();
195
196 unsigned char GetCurrentTextClass()
197         // Who are we asking?
198         // Shouldn't this question be directed to the buffer?
199         // Indeed it should. Asger.
200 {
201         return current_view->buffer()->params.textclass;
202 }
203
204
205 // How should this actually work? Should it prohibit input in all BufferViews,
206 // or just in the current one? If "just the current one", then it should be
207 // placed in BufferView. If "all BufferViews" then LyXGUI (I think) should
208 // run "ProhibitInput" on all LyXViews which will run prohibitInput on all
209 // BufferViews. Or is it perhaps just the (input in) BufferViews in the
210 // current LyxView that should be prohibited (Lgb) (This applies to
211 // "AllowInput" as well.)
212 void ProhibitInput()
213 {
214         input_prohibited = true;
215         if (current_view->getScreen())
216                 current_view->getScreen()->HideCursor();
217
218         static Cursor cursor;
219         static bool cursor_undefined = true;
220    
221         if (cursor_undefined){
222                 cursor = XCreateFontCursor(fl_display, XC_watch);
223                 XFlush(fl_display);
224                 cursor_undefined = false;
225         }
226    
227         /* set the cursor to the watch for all forms and the canvas */ 
228         XDefineCursor(fl_display, fd_form_main->form_main->window, cursor);
229         if (fd_form_paragraph->form_paragraph->visible)
230                 XDefineCursor(fl_display,
231                               fd_form_paragraph->form_paragraph->window,
232                               cursor);
233         if (fd_form_character->form_character->visible)
234                 XDefineCursor(fl_display,
235                               fd_form_character->form_character->window,
236                               cursor);
237
238         XFlush(fl_display);
239         fl_deactivate_all_forms();
240 }
241
242
243 // Should find a way to move this into BufferView.C
244 void SetXtermCursor(Window win)
245 {
246         static Cursor cursor;
247         static bool cursor_undefined = true;
248         if (cursor_undefined){
249                 cursor = XCreateFontCursor(fl_display, XC_xterm);
250                 XFlush(fl_display);
251                 cursor_undefined = false;
252         }
253         XDefineCursor(fl_display, win, cursor);
254         XFlush(fl_display);
255 }
256
257
258 void AllowInput()
259 {
260         input_prohibited = false;
261
262         /* reset the cursor from the watch for all forms and the canvas */
263    
264         XUndefineCursor(fl_display, fd_form_main->form_main->window);
265         if (fd_form_paragraph->form_paragraph->visible)
266                 XUndefineCursor(fl_display,
267                                 fd_form_paragraph->form_paragraph->window);
268         if (fd_form_character->form_character->visible)
269                 XUndefineCursor(fl_display,
270                                 fd_form_character->form_character->window);
271         if (current_view->getWorkArea()->belowmouse)
272                 SetXtermCursor(fd_form_main->form_main->window);
273
274         XFlush(fl_display);
275         fl_activate_all_forms();
276 }
277
278
279 void FreeUpdateTimer()
280 {
281         /* a real free timer would be better but I don't know 
282          * how to do this with xforms */
283         updatetimer = 0;
284 }
285
286
287 void SetUpdateTimer(float time)
288 {
289         fl_set_timer(fd_form_main->timer_update, time);
290         updatetimer = 1;
291 }
292
293
294 void BeforeChange()
295 {
296         current_view->getScreen()->ToggleSelection();
297         current_view->buffer()->text->ClearSelection();
298         FreeUpdateTimer();
299 }
300
301
302 void SmallUpdate(signed char f)
303 {
304         current_view->getScreen()->SmallUpdate();
305         if (current_view->getScreen()->TopCursorVisible()
306             != current_view->getScreen()->first){
307                 current_view->buffer()->update(f);
308                 return;
309         }
310
311         current_view->fitCursor();
312         current_view->updateScrollbar();
313    
314         if (!current_view->buffer()->text->selection)
315                 current_view->buffer()->text->sel_cursor = 
316                         current_view->buffer()->text->cursor;
317
318         if (f == 1 || f == -1) {
319                 if (current_view->buffer()->isLyxClean()) {
320                         current_view->buffer()->markDirty();
321                         minibuffer->setTimer(4);
322                 }
323                 else {
324                         current_view->buffer()->markDirty();
325                 }
326         }
327 }
328
329
330 //
331 // Menu callbacks
332 //
333
334 //
335 // File menu
336 //
337
338 // should be moved to lyxfunc.C
339 void MenuWrite(Buffer * buf)
340 {
341         XFlush(fl_display);
342         if (!bufferlist.write(buf)) {
343                 string fname = buf->getFileName();
344                 string s = MakeAbsPath(fname);
345                 if (AskQuestion(_("Save failed. Rename and try again?"),
346                                  MakeDisplayPath(s, 50),
347                                  _("(If not, document is not saved.)"))) {
348                         MenuWriteAs(buf);
349                 }
350         } else {
351                 lastfiles->newFile(buf->getFileName());
352         }
353 }
354
355
356 // should be moved to BufferView.C
357 void MenuWriteAs(Buffer * buffer)
358 {
359         if (!buffer->text) return;
360
361         string fname = buffer->getFileName();
362         string oldname = fname;
363         LyXFileDlg fileDlg;
364
365         ProhibitInput();
366         fileDlg.SetButton(0, _("Documents"), lyxrc->document_path);
367         fileDlg.SetButton(1, _("Templates"), lyxrc->template_path);
368
369         if (!IsLyXFilename(fname))
370                 fname += ".lyx";
371
372         fname = fileDlg.Select(_("Enter Filename to Save Document as"), 
373                                OnlyPath(fname),
374                                "*.lyx", 
375                                OnlyFilename(fname));
376         AllowInput();
377
378         if (fname.empty()) {
379                 minibuffer->Set(_("Canceled."));
380                 return;
381         }
382
383         // Make sure the absolute filename ends with appropriate suffix
384         string s = MakeAbsPath(fname);
385         if (!IsLyXFilename(s))
386                 s += ".lyx";
387
388         // Same name as we have already?
389         if (s == oldname) {
390                 if (!AskQuestion(_("Same name as document already has:"),
391                                  MakeDisplayPath(s, 50),
392                                  _("Save anyway?")))
393                         return;
394                 // Falls through to name change and save
395         } 
396         // No, but do we have another file with this name open?
397         else if (bufferlist.exists(s)) {
398                 if (AskQuestion(_("Another document with same name open!"),
399                                 MakeDisplayPath(s, 50),
400                                 _("Replace with current document?")))
401                         {
402                                 bufferlist.close(bufferlist.getBuffer(s));
403
404                                 // Ok, change the name of the buffer, but don't save!
405                                 buffer->setFileName(s);
406                                 buffer->markDirty();
407
408                                 minibuffer->Set(_("Document renamed to '"),
409                                                 MakeDisplayPath(s),
410                                                 _("', but not saved..."));
411                         }
412                 return;
413         } // Check whether the file exists
414         else {
415                 FileInfo myfile(s);
416                 if (myfile.isOK() && !AskQuestion(_("Document already exists:"), 
417                                                   MakeDisplayPath(s, 50),
418                                                   _("Replace file?")))
419                         return;
420         }
421
422         // Ok, change the name of the buffer
423         buffer->setFileName(s);
424         buffer->markDirty();
425         // And save
426         // Small bug: If the save fails, we have irreversible changed the name
427         // of the document.
428         MenuWrite(buffer);
429 }    
430
431
432 int MenuRunLaTeX(Buffer * buffer)
433 {
434         int ret = 0;
435
436         if (buffer->isLinuxDoc())
437                 ret = RunLinuxDoc(1, buffer->getFileName());
438         else if (buffer->isLiterate())
439                 ret = buffer->runLiterate();
440         else if (buffer->isDocBook())
441                 ret = RunDocBook(1, buffer->getFileName());
442         else
443                 ret = buffer->runLaTeX();
444    
445         if (ret > 0) {
446                 string s;
447                 string t;
448                 if (ret == 1) {
449                         s = _("One error detected");
450                         t = _("You should try to fix it.");
451                 } else {
452                         s += tostr(ret);
453                         s += _(" errors detected.");
454                         t = _("You should try to fix them.");
455                 }
456                 WriteAlert(_("There were errors during the LaTeX run."), s, t);
457         }
458         return ret;
459 }
460
461
462 int MenuBuildProg(Buffer * buffer)
463 {
464         int ret = 0;
465         
466         if (buffer->isLiterate())
467                 ret = buffer->buildProgram();
468         else {
469                 string s = _("Wrong type of document");
470                 string t = _("The Build operation is not allowed in this document");
471                 WriteAlert(_("There were errors during the Build process."), s, t);
472                 return 1;
473         }
474         
475         if (ret > 0) {
476                 string s;
477                 string t;
478                 if (ret == 1) {
479                         s = _("One error detected");
480                         t = _("You should try to fix it.");
481                 } else {
482                         s += tostr(ret);
483                         s += _(" errors detected.");
484                         t = _("You should try to fix them.");
485                 }
486                 WriteAlert(_("There were errors during the Build process."), s, t);
487         }
488         return ret;
489 }
490
491
492 int MenuRunChktex(Buffer * buffer)
493 {
494         int ret;
495
496         if (buffer->isSGML()) {
497                 WriteAlert(_("Chktex does not work with SGML derived documents."));
498                 return 0;
499         } else 
500                 ret = buffer->runChktex();
501    
502         if (ret >= 0) {
503                 string s;
504                 string t;
505                 if (ret == 0) {
506                         s = _("No warnings found.");
507                 } else if (ret == 1) {
508                         s = _("One warning found.");
509                         t = _("Use 'Edit->Go to Error' to find it.");
510                 } else {
511                         s += tostr(ret);
512                         s += _(" warnings found.");
513                         t = _("Use 'Edit->Go to Error' to find them.");
514                 }
515                 WriteAlert(_("Chktex run successfully"), s, t);
516         } else {
517                 WriteAlert(_("Error!"), _("It seems chktex does not work."));
518         }
519         return ret;
520 }
521
522  
523 int MakeDVIOutput(Buffer * buffer)
524 {
525         if (!(buffer->text))
526                 return 1;
527
528         int ret = 0;
529
530         string path = OnlyPath(buffer->getFileName());
531         if (lyxrc->use_tempdir || (IsDirWriteable(path) < 1)) {
532                 path = buffer->tmppath;
533         }
534         if (!buffer->isDviClean()) {
535                 Path p(path);
536                 ret = MenuRunLaTeX(buffer);
537         }
538         return ret;
539 }
540
541
542 /* wait == false means don't wait for termination */
543 /* wait == true means wait for termination       */
544 // The bool should be placed last on the argument line. (Lgb)
545 // Returns false if we fail.
546 bool RunScript(Buffer * buffer, bool wait,
547                string const & command,
548                string const & orgname = string(),
549                bool need_shell = true)
550 {
551         string path;
552         string cmd;
553         string name = orgname;
554         int result = 0;
555         
556         if (MakeDVIOutput(buffer) > 0)
557                 return false;
558         /* get DVI-Filename */
559         if (name.empty())
560                 name = ChangeExtension(buffer->getLatexName(),
561                                        ".dvi", true);
562
563         path = OnlyPath(name);
564         if (lyxrc->use_tempdir || (IsDirWriteable(path) < 1)) {
565                 path = buffer->tmppath;
566         }
567         Path p(path);
568
569         cmd = command + ' ' + QuoteName(name);
570
571         Systemcalls one;
572
573         if (need_shell) {
574 #ifndef __EMX__
575                 if (!wait)
576                         cmd += " &";
577 #else
578                 // OS/2 cmd.exe has another use for '&'
579                 if (!wait) {
580                         // This is not NLS safe, but it's OK, I think.
581                         string sh = OnlyFilename(GetEnvPath("EMXSHELL"));
582                         if (sh.empty()) {
583                                 // COMSPEC is set, unless user unsets 
584                                 sh = OnlyFilename(GetEnvPath("COMSPEC"));
585                                 if (sh.empty())
586                                         sh = "cmd.exe";
587                         }
588                         sh = lowercase(sh);
589                         if (contains(sh, "cmd.exe")
590                             || contains(sh, "4os2.exe"))
591                                 cmd = "start /min/n " + cmd;
592                         else
593                                 cmd += " &";
594                 }
595 #endif
596                 // It seems that, if wait is false, we never get back
597                 // the return code of the command. This means that all
598                 // the code I added in PrintApplyCB is currently
599                 // useless...
600 #ifdef WITH_WARNINGS
601 #warning What should we do here?
602 #endif          
603                 minibuffer->Set(_("Executing command:"), cmd);
604                 result = one.startscript(Systemcalls::System, cmd);
605         } else {
606                 minibuffer->Set(_("Executing command:"), cmd);
607                 result = one.startscript(wait ? Systemcalls::Wait
608                                         : Systemcalls::DontWait, cmd);
609         }
610         return (result == 0);
611 }
612
613
614 // Returns false if we fail
615 bool MenuRunDvips(Buffer * buffer, bool wait = false)
616 {
617         if (!buffer->text)
618                 return false;
619
620         ProhibitInput();
621
622         // Generate dvi file
623         if (MakeDVIOutput(buffer) > 0) {
624                 AllowInput();
625                 return false;
626         }
627         // Generate postscript file
628         string psname = ChangeExtension (buffer->getFileName(),
629                                       ".ps_tmp", true);
630
631         string paper;
632         
633         char real_papersize = buffer->params.papersize;
634         if (real_papersize == BufferParams::PAPER_DEFAULT)
635                 real_papersize = lyxrc->default_papersize;
636
637         switch (real_papersize) {
638         case BufferParams::PAPER_USLETTER:
639                 paper = "letter";
640                 break;
641         case BufferParams::PAPER_A3PAPER:
642                 paper = "a3";
643                 break;
644         case BufferParams::PAPER_A4PAPER:
645                 paper = "a4";
646                 break;
647         case BufferParams::PAPER_A5PAPER:
648                 paper = "a5";
649                 break;
650         case BufferParams::PAPER_B5PAPER:
651                 paper = "b5";
652                 break;
653         case BufferParams::PAPER_EXECUTIVEPAPER:
654                 paper = "foolscap";
655                 break;
656         case BufferParams::PAPER_LEGALPAPER:
657                 paper = "legal";
658                 break;
659         default: /* If nothing else fits, keep an empty value... */
660                 break;
661         }
662
663         // Make postscript file.
664         string command = "dvips " + lyxrc->print_to_file + ' ';
665         command += QuoteName(psname);
666         if (buffer->params.use_geometry
667             && buffer->params.papersize2 == BufferParams::VM_PAPER_CUSTOM
668             && !lyxrc->print_paper_dimension_flag.empty()
669             && !buffer->params.paperwidth.empty()
670             && !buffer->params.paperheight.empty()) {
671                 // using a custom papersize
672                 command += ' ';
673                 command += lyxrc->print_paper_dimension_flag + ' ';
674                 command += buffer->params.paperwidth + ',';
675                 command += buffer->params.paperheight;
676         } else if (!paper.empty()
677                    && (real_papersize != BufferParams::PAPER_USLETTER ||
678                        buffer->params.orientation == BufferParams::ORIENTATION_PORTRAIT)) {
679                 // dvips won't accept -t letter -t landscape.  In all other
680                 // cases, include the paper size explicitly.
681                 command += ' ';
682                 command += lyxrc->print_paper_flag + ' ' + paper;
683         }
684         if (buffer->params.orientation == BufferParams::ORIENTATION_LANDSCAPE) {
685                 command += ' ';
686                 command += lyxrc->print_landscape_flag;
687         }
688         // push directorypath, if necessary 
689         string path = OnlyPath(buffer->getFileName());
690         if (lyxrc->use_tempdir || (IsDirWriteable(path) < 1)){
691                 path = buffer->tmppath;
692         }
693         Path p(path);
694         bool ret = RunScript(buffer, wait, command);
695         AllowInput();
696         return ret;
697 }
698
699
700 // Returns false if we fail
701 bool MenuPreviewPS(Buffer * buffer)
702 {
703         if (!buffer->text)
704                 return false;
705
706         // Generate postscript file
707         if (!MenuRunDvips(buffer, true)) {
708                 return false;
709         }
710
711         // Start postscript viewer
712         ProhibitInput();
713         string ps = ChangeExtension (buffer->getFileName(),
714                                       ".ps_tmp", true);
715         // push directorypath, if necessary 
716         string path = OnlyPath(buffer->getFileName());
717         if (lyxrc->use_tempdir || (IsDirWriteable(path) < 1)){
718                 path = buffer->tmppath;
719         }
720         Path p(path);
721         bool ret = RunScript(buffer, false, lyxrc->view_ps_command, ps);
722         AllowInput();
723         return ret;
724 }
725
726
727 void MenuFax(Buffer * buffer)
728 {
729         if (!buffer->text)
730                 return;
731
732         // Generate postscript file
733         if (!MenuRunDvips(buffer, true)) {
734                 return;
735         }
736
737         // Send fax
738         string ps = ChangeExtension (buffer->getFileName(), ".ps_tmp", true);
739         string path = OnlyPath (buffer->getFileName());
740         if (lyxrc->use_tempdir || (IsDirWriteable(path) < 1)) {
741                 path = buffer->tmppath;
742         }
743         Path p(path);
744         if (!lyxrc->fax_program.empty()) {
745                 string help2 = subst(lyxrc->fax_program, "$$FName", ps);
746                 help2 += " &";
747                 Systemcalls one(Systemcalls::System, help2);
748         } else
749                 send_fax(ps, lyxrc->fax_command);
750 }
751
752
753 // Returns false if we fail
754 bool MenuPreview(Buffer * buffer)
755 {
756         if (!buffer->text)
757                 return false;
758    
759         string paper;
760         
761         char real_papersize = buffer->params.papersize;
762         if (real_papersize == BufferParams::PAPER_DEFAULT)
763                 real_papersize = lyxrc->default_papersize;
764    
765         switch (real_papersize) {
766         case BufferParams::PAPER_USLETTER:
767                 paper = "us";
768                 break;
769         case BufferParams::PAPER_A3PAPER:
770                 paper = "a3";
771                 break;
772         case BufferParams::PAPER_A4PAPER:
773                 paper = "a4";
774                 break;
775         case BufferParams::PAPER_A5PAPER:
776                 paper = "a5";
777                 break;
778         case BufferParams::PAPER_B5PAPER:
779                 paper = "b5";
780                 break;
781         case BufferParams::PAPER_EXECUTIVEPAPER:
782                 paper = "foolscap";
783                 break;
784         case BufferParams::PAPER_LEGALPAPER:
785                 paper = "legal";
786                 break;
787         default: /* If nothing else fits, keep the empty value */
788                 break;
789         }
790    
791         if (paper.empty()) {
792                 if (buffer->params.orientation == BufferParams::ORIENTATION_LANDSCAPE)
793                         // we HAVE to give a size when the page is in
794                         // landscape, so use USletter.          
795                         paper = " -paper usr";
796         } else {
797                 paper = " -paper " + paper;
798                 if (buffer->params.orientation == BufferParams::ORIENTATION_LANDSCAPE)
799                         paper+= 'r';
800         }
801
802         // push directorypath, if necessary 
803         string path = OnlyPath(buffer->getFileName());
804         if (lyxrc->use_tempdir || (IsDirWriteable(path) < 1)){
805                 path = buffer->tmppath;
806         }
807         Path p(path);
808         // Run dvi-viewer
809         string command = lyxrc->view_dvi_command + paper ;
810         bool ret = RunScript(buffer, false, command);
811         return ret;
812 }
813
814
815 void MenuMakeLaTeX(Buffer * buffer)
816 {
817         if (buffer->text) {
818                 // Get LaTeX-Filename
819           string s = buffer->getLatexName();
820
821                 FileInfo fi(s);
822                 if (fi.readable() &&
823                     !AskQuestion(_("File already exists:"), 
824                                 MakeDisplayPath(s, 50),
825                                 _("Do you want to overwrite the file?"))) {
826                         minibuffer->Set(_("Canceled"));
827                         return;
828                 }
829
830                 if (buffer->isDocBook())
831                         minibuffer->Set(_("DocBook does not have a latex backend"));
832                 else {
833                         if (buffer->isLinuxDoc())
834                                 RunLinuxDoc(0, buffer->getFileName());
835                         else
836                                 buffer->makeLaTeXFile(s, string(), true);
837                         minibuffer->Set(_("Nice LaTeX file saved as"),
838                                         MakeDisplayPath(s));
839                         buffer->markDviDirty();
840                 }
841         }
842 }
843
844
845 void MenuMakeLinuxDoc(Buffer * buffer)
846 {
847         if (buffer->text) {
848                 if (!buffer->isLinuxDoc()) {
849                         WriteAlert(_("Error!"), _("Document class must be linuxdoc."));
850                         return;
851                 }
852
853                 // Get LinuxDoc-Filename
854                 string s = ChangeExtension (buffer->getFileName(), 
855                                              ".sgml", false);
856
857                 FileInfo fi(s);
858                 if (fi.readable() &&
859                     !AskQuestion(_("File already exists:"), 
860                                 MakeDisplayPath(s, 50),
861                                 _("Do you want to overwrite the file?"))) {
862                         minibuffer->Set(_("Canceled"));
863                         return;
864                 }
865
866                 minibuffer->Set(_("Building LinuxDoc SGML file `"),
867                                 MakeDisplayPath(s), "'..."); 
868
869                 buffer->makeLinuxDocFile(s, 65);
870                 buffer->redraw();
871                 minibuffer->Set(_("LinuxDoc SGML file save as"),
872                                 MakeDisplayPath(s)); 
873         }
874 }
875
876
877 void MenuMakeDocBook(Buffer * buffer)
878 {
879         if (buffer->text) {
880                 if (!buffer->isDocBook()) {
881                         WriteAlert(_("Error!"),
882                                    _("Document class must be docbook."));
883                         return;
884                 }
885
886                 // Get DocBook-Filename
887                 string s = ChangeExtension (buffer->getFileName(), 
888                                              ".sgml", false);
889
890                 FileInfo fi(s);
891                 if (fi.readable() &&
892                     !AskQuestion(_("File already exists:"), 
893                                 MakeDisplayPath(s, 50),
894                                 _("Do you want to overwrite the file?"))) {
895                         minibuffer->Set(_("Canceled"));
896                         return;
897                 }
898
899                 minibuffer->Set(_("Building DocBook SGML file `"),
900                                 MakeDisplayPath(s), "'..."); 
901
902                 buffer->makeDocBookFile(s, 65);
903                 buffer->redraw();
904                 minibuffer->Set(_("DocBook SGML file save as"),
905                                 MakeDisplayPath(s)); 
906         }
907 }
908
909
910 void MenuMakeAscii(Buffer * buffer)
911 {
912         if (buffer->text) {
913                 /* get LaTeX-Filename */
914                 string s = ChangeExtension (buffer->getFileName(),
915                                              ".txt", false);
916
917                 FileInfo fi(s);
918                 if (fi.readable() &&
919                     !AskQuestion(_("File already exists:"), 
920                                 MakeDisplayPath(s, 50),
921                                 _("Do you want to overwrite the file?"))) {
922                         minibuffer->Set(_("Canceled"));
923                         return;
924                 }
925
926                 buffer->writeFileAscii(s, lyxrc->ascii_linelen);
927
928                 minibuffer->Set(_("Ascii file saved as"), MakeDisplayPath(s));
929         }
930 }
931
932
933 void MenuPrint(Buffer * buffer)
934 {
935         if (!buffer->text) 
936                 return;
937         
938         string input_file = ChangeExtension(buffer->getFileName(),
939                                      lyxrc->print_file_extension,
940                                      true);
941         fl_set_input(fd_form_print->input_file, input_file.c_str());
942         
943         if (fd_form_print->form_print->visible) {
944                 fl_raise_form(fd_form_print->form_print);
945         } 
946         else {
947                 fl_show_form(fd_form_print->form_print,
948                              FL_PLACE_MOUSE, FL_FULLBORDER,
949                              _("Print"));
950         }
951 }
952
953
954 void QuitLyX()
955 {
956         lyxerr.debug() << "Running QuitLyX." << endl;
957
958         if (!bufferlist.QwriteAll())
959                 return;
960
961         lastfiles->writeFile(lyxrc->lastfiles);
962
963         // Set a flag that we do quitting from the program,
964         // so no refreshes are necessary.
965         quitting = true;
966
967         // close buffers first
968         bufferlist.closeAll();
969
970         // do any other cleanup procedures now
971         lyxerr.debug() << "Deleting tmp dir " << system_tempdir << endl;
972
973         DestroyLyXTmpDir(system_tempdir);
974
975         finished = true;
976 }
977
978
979
980 void AutoSave()
981         // should probably be moved into BufferList (Lgb)
982         // Perfect target for a thread...
983 {
984         if (!current_view->getScreen() || !current_view->available())
985                 return;
986
987         if (current_view->buffer()->isBakClean()
988             || current_view->buffer()->isReadonly()) {
989                 // We don't save now, but we'll try again later
990                 current_view->owner()->resetAutosaveTimer();
991                 return;
992         }
993
994         minibuffer->Set(_("Autosaving current document..."));
995         
996         // create autosave filename
997         string fname =  OnlyPath(current_view->buffer()->getFileName());
998         fname += "#";
999         fname += OnlyFilename(current_view->buffer()->getFileName());
1000         fname += "#";
1001         
1002         // tmp_ret will be located (usually) in /tmp
1003         // will that be a problem?
1004         string tmp_ret = tmpnam(0);
1005         
1006         pid_t pid = fork(); // If you want to debug the autosave
1007         // you should set pid to -1, and comment out the
1008         // fork.
1009         if (pid == 0 || pid == -1) {
1010                 // pid = -1 signifies that lyx was unable
1011                 // to fork. But we will do the save
1012                 // anyway.
1013                 bool failed = false;
1014                 if (!tmp_ret.empty()) {
1015                         current_view->buffer()->writeFile(tmp_ret, 1);
1016                         // assume successful write of tmp_ret
1017                         if (rename(tmp_ret.c_str(), fname.c_str()) == -1) {
1018                                 failed = true;
1019                                 // most likely couldn't move between filesystems
1020                                 // unless write of tmp_ret failed
1021                                 // so remove tmp file (if it exists)
1022                                 remove(tmp_ret.c_str());
1023                         }
1024                 } else {
1025                         failed = true;
1026                 }
1027                 
1028                 if (failed) {
1029                         // failed to write/rename tmp_ret so try writing direct
1030                         if (!current_view->buffer()->writeFile(fname, 1)) {
1031                                 // It is dangerous to do this in the child,
1032                                 // but safe in the parent, so...
1033                                 if (pid == -1)
1034                                         minibuffer->Set(_("Autosave Failed!"));
1035                         }
1036                 }
1037                 if (pid == 0) { // we are the child so...
1038                         _exit(0);
1039                 }
1040         }
1041         
1042         current_view->buffer()->markBakClean();
1043         current_view->owner()->resetAutosaveTimer();
1044 }
1045
1046
1047 //
1048 // (c) CHT Software Service GmbH
1049 // Uwe C. Schroeder
1050 //
1051 // create new file with template
1052 // SERVERCMD !
1053 //
1054 Buffer * NewLyxFile(string const & filename)
1055 {
1056         // Split argument by :
1057         string name;
1058         string tmpname = split(filename, name, ':');
1059 #ifdef __EMX__ // Fix me! lyx_cb.C may not be low level enough to allow this.
1060         if (name.length() == 1
1061             && isalpha(static_cast<unsigned char>(name[0]))
1062             && (prefixIs(tmpname, "/") || prefixIs(tmpname, "\\"))) {
1063                 name += ':';
1064                 name += token(tmpname, ':', 0);
1065                 tmpname = split(tmpname, ':');
1066         }
1067 #endif
1068         lyxerr.debug() << "Arg is " << filename
1069                        << "\nName is " << name
1070                        << "\nTemplate is " << tmpname << endl;
1071
1072         // find a free buffer 
1073         Buffer * tmpbuf = bufferlist.newFile(name, tmpname);
1074         if (tmpbuf)
1075                 lastfiles->newFile(tmpbuf->getFileName());
1076         return tmpbuf;
1077 }
1078
1079
1080 // Insert ascii file (if filename is empty, prompt for one)
1081 void InsertAsciiFile(string const & f, bool asParagraph)
1082 {
1083         string fname = f;
1084         LyXFileDlg fileDlg;
1085  
1086         if (!current_view->getScreen()) return;
1087      
1088         if (fname.empty()) {
1089                 ProhibitInput();
1090                 fname = fileDlg.Select(_("File to Insert"), 
1091                                        current_view->owner()->buffer()->filepath,
1092                                        "*");
1093                 AllowInput();
1094                 if (fname.empty()) return;
1095         }
1096
1097         FileInfo fi(fname);
1098
1099         if (!fi.readable()) {
1100                 WriteFSAlert(_("Error! Specified file is unreadable: "),
1101                              MakeDisplayPath(fname, 50));
1102                 return;
1103         }
1104
1105         FilePtr myfile(fname, FilePtr::read);
1106         if (!myfile()) {
1107                 WriteFSAlert(_("Error! Cannot open specified file: "),
1108                              MakeDisplayPath(fname, 50));
1109                 return;
1110         }
1111         LyXParagraph * tmppar = new LyXParagraph;
1112         tmppar->readSimpleWholeFile(myfile);
1113         
1114         // set the end of the string
1115 #ifdef WITH_WARNINGS
1116 #warning why do we do this?
1117 #endif
1118         // I don't think this is needed. Actually it might be plain wrong.
1119         tmppar->InsertChar(tmppar->text.size() - 1, '\0');
1120
1121         // insert the string
1122         current_view->getScreen()->HideCursor();
1123         
1124         // clear the selection
1125         BeforeChange();
1126         if (!asParagraph)
1127                 current_view->buffer()->text->InsertStringA(tmppar->text);
1128         else
1129                 current_view->buffer()->text->InsertStringB(tmppar->text);
1130         delete tmppar;
1131         current_view->buffer()->update(1);
1132 }
1133
1134
1135 void MenuShowTableOfContents()
1136 {
1137         static int ow = -1, oh;
1138
1139         TocUpdateCB(0, 0);
1140         if (fd_form_toc->form_toc->visible) {
1141                 fl_raise_form(fd_form_toc->form_toc);
1142         } else {
1143                 fl_show_form(fd_form_toc->form_toc,
1144                              FL_PLACE_MOUSE | FL_FREE_SIZE, FL_FULLBORDER,
1145                              _("Table Of Contents"));
1146                 if (ow < 0) {
1147                         ow = fd_form_toc->form_toc->w;
1148                         oh = fd_form_toc->form_toc->h;
1149                 }
1150                 fl_set_form_minsize(fd_form_toc->form_toc, ow, oh);
1151         }
1152 }
1153
1154
1155 void MenuInsertLabel(char const * arg)
1156 {
1157         string label = arg;
1158         ProhibitInput();
1159         //string label = fl_show_input(_("Enter new label to insert:"), "");
1160         if (label.empty())
1161                 label = frontStrip(strip(askForText(_("Enter new label to insert:"))));
1162         if (!label.empty()) {
1163                 InsetLabel * new_inset = new InsetLabel;
1164                 new_inset->setContents(label);
1165                 current_view->buffer()->insertInset(new_inset);
1166         }
1167         AllowInput();
1168 }
1169
1170
1171 void MenuInsertRef()
1172 {
1173         static int ow = -1, oh;
1174
1175         RefUpdateCB(0, 0);
1176         if (fd_form_ref->form_ref->visible) {
1177                 fl_raise_form(fd_form_ref->form_ref);
1178         } else {
1179                 fl_show_form(fd_form_ref->form_ref,
1180                              FL_PLACE_MOUSE | FL_FREE_SIZE, FL_FULLBORDER,
1181                              _("Insert Reference"));
1182                 if (ow < 0) {
1183                         ow = fd_form_ref->form_ref->w;
1184                         oh = fd_form_ref->form_ref->h;
1185                 }
1186                 fl_set_form_minsize(fd_form_ref->form_ref, ow, oh);
1187         }
1188 }
1189
1190
1191 void MenuPasteSelection(char at)
1192 {
1193         if (!current_view->getScreen())
1194                 return;
1195
1196         ascii_type = at;
1197   
1198         Atom data_prop = XInternAtom(fl_display, 
1199                                      "LyX_Primary",
1200                                      false);
1201         if (data_prop == None) 
1202                 return;
1203         XConvertSelection(fl_display,
1204                           XA_PRIMARY, XA_STRING, data_prop, 
1205                           fd_form_main->form_main->window, 0);
1206         XFlush(fl_display);
1207 }
1208
1209
1210 extern "C" void FootCB(FL_OBJECT *, long)
1211 {
1212         if (!current_view->available()) 
1213                 return;
1214         
1215         minibuffer->Set(_("Inserting Footnote..."));
1216         current_view->getScreen()->HideCursor();
1217         current_view->buffer()->update(-2);
1218         current_view->buffer()->text->InsertFootnoteEnvironment(LyXParagraph::FOOTNOTE);
1219         current_view->buffer()->update(1);
1220 }
1221
1222
1223 void LayoutsCB(int sel, void *)
1224 {
1225         string tmp = tostr(sel);
1226         current_view->owner()->getLyXFunc()->Dispatch(LFUN_LAYOUTNO,
1227                                                          tmp.c_str());
1228 }
1229
1230
1231 /*
1232  * SGML Linuxdoc support:
1233  * (flag == -1) import SGML file
1234  * (flag == 0) make TeX output
1235  * (flag == 1) make dvi output
1236  */
1237 int RunLinuxDoc(int flag, string const & filename)
1238 {
1239         string name;
1240         string s2;
1241         string path;
1242         string add_flags;
1243
1244         int errorcode = 0;
1245
1246         /* generate a path-less extension name */
1247         name = ChangeExtension (filename, ".sgml", true);
1248         path = OnlyPath (filename);
1249         if (lyxrc->use_tempdir || (IsDirWriteable(path) < 1)) {
1250                 path = current_view->buffer()->tmppath;
1251         }
1252         Path p(path);
1253         
1254         if (flag != -1) {
1255                 if (!current_view->available())
1256                         return 0;
1257                 current_view->buffer()->makeLinuxDocFile(name, 0);
1258 #ifdef WITH_WARNINGS
1259 #warning remove this once we have a proper geometry class
1260 #endif
1261                 BufferParams::PAPER_SIZE ps = static_cast<BufferParams::PAPER_SIZE>(current_view->buffer()->params.papersize);
1262                 switch (ps) {
1263                 case BufferParams::PAPER_A4PAPER:
1264                         add_flags = "-p a4";
1265                         break;
1266                 case BufferParams::PAPER_USLETTER:
1267                         add_flags = "-p letter";
1268                         break;
1269                 default: /* nothing to be done yet ;-) */     break; 
1270                 }
1271         }
1272         
1273         ProhibitInput();
1274         
1275         Systemcalls one;
1276         switch (flag) {
1277         case -1: /* Import file */
1278                 minibuffer->Set(_("Importing LinuxDoc SGML file `"), 
1279                                 MakeDisplayPath(filename), "'...");
1280                 s2 = "sgml2lyx " + lyxrc->sgml_extra_options + ' ' 
1281                         + name;
1282                 if (one.startscript(Systemcalls::System, s2)) 
1283                         errorcode = 1;
1284                 break;
1285         case 0: /* TeX output asked */
1286                 minibuffer->Set(_("Converting LinuxDoc SGML to TeX file..."));
1287                 s2 = "sgml2latex " + add_flags + " -o tex "
1288                         + lyxrc->sgml_extra_options + ' ' + name;
1289                 if (one.startscript(Systemcalls::System, s2)) 
1290                         errorcode = 1;
1291                 break;
1292         case 1: /* dvi output asked */
1293                 minibuffer->Set(_("Converting LinuxDoc SGML to dvi file..."));
1294                 s2 = "sgml2latex " + add_flags + " -o dvi "
1295                         + lyxrc->sgml_extra_options + ' ' + name;
1296                 if (one.startscript(Systemcalls::System, s2)) {
1297                         errorcode = 1;
1298                 } else
1299                         current_view->buffer()->markDviClean();
1300                 break;
1301         default: /* unknown output */
1302                 break;
1303         }
1304         
1305         AllowInput();
1306
1307         current_view->buffer()->redraw();
1308         return errorcode;
1309 }
1310
1311
1312 /*
1313  * SGML DocBook support:
1314  * (flag == 1) make dvi output
1315  */
1316 int RunDocBook(int flag, string const & filename)
1317 {
1318         /* generate a path-less extension name */
1319         string name = ChangeExtension (filename, ".sgml", true);
1320         string path = OnlyPath (filename);
1321         if (lyxrc->use_tempdir || (IsDirWriteable(path) < 1)) {
1322                 path = current_view->buffer()->tmppath;
1323         }
1324         Path p(path);
1325
1326         if (!current_view->available())
1327                 return 0;
1328         
1329         current_view->buffer()->makeDocBookFile(name, 0);
1330
1331         // Shall this code go or should it stay? (Lgb)
1332 //      string add_flags;
1333 //      LYX_PAPER_SIZE ps = (LYX_PAPER_SIZE) current_view->buffer()->params.papersize;
1334 //      switch (ps) {
1335 //      case BufferParams::PAPER_A4PAPER:  add_flags = "-p a4";     break;
1336 //      case BufferParams::PAPER_USLETTER: add_flags = "-p letter"; break;
1337 //      default: /* nothing to be done yet ;-) */     break; 
1338 //      }
1339         ProhibitInput();
1340         
1341         int errorcode = 0;
1342         Systemcalls one;
1343         switch (flag) {
1344         case 1: /* dvi output asked */
1345         {
1346                 minibuffer->Set(_("Converting DocBook SGML to dvi file..."));
1347                 string s2 = "sgmltools --backend dvi " + name;
1348                 if (one.startscript(Systemcalls::System, s2)) {
1349                         errorcode = 1;
1350                 } else
1351                         current_view->buffer()->markDviClean();
1352         }
1353         break;
1354         default: /* unknown output */
1355                 break;
1356         }
1357         
1358         AllowInput();
1359
1360         current_view->buffer()->redraw();
1361         return errorcode;
1362 }
1363
1364
1365 void AllFloats(char flag, char figmar)
1366 {
1367         if (!current_view->available())
1368                 return;
1369    
1370         LyXCursor cursor = current_view->buffer()->text->cursor;
1371
1372         if (!flag && cursor.par->footnoteflag != LyXParagraph::NO_FOOTNOTE
1373             && ((figmar 
1374                  && cursor.par->footnotekind != LyXParagraph::FOOTNOTE 
1375                  && cursor.par->footnotekind != LyXParagraph::MARGIN)
1376                 || (!figmar
1377                     && cursor.par->footnotekind != LyXParagraph::FIG 
1378                     && cursor.par->footnotekind != LyXParagraph::TAB
1379                     && cursor.par->footnotekind != LyXParagraph::WIDE_FIG 
1380                     && cursor.par->footnotekind != LyXParagraph::WIDE_TAB
1381                     && cursor.par->footnotekind != LyXParagraph::ALGORITHM)))
1382                 ToggleFloat();
1383         else
1384                 BeforeChange();
1385
1386         LyXCursor tmpcursor = cursor;
1387         cursor.par = tmpcursor.par->ParFromPos(tmpcursor.pos);
1388         cursor.pos = tmpcursor.par->PositionInParFromPos(tmpcursor.pos);
1389
1390         LyXParagraph *par = current_view->buffer()->paragraph;
1391         while (par) {
1392                 if (flag) {
1393                         if (par->footnoteflag == LyXParagraph::CLOSED_FOOTNOTE
1394                             && ((figmar 
1395                                  && par->footnotekind != LyXParagraph::FOOTNOTE 
1396                                  && par->footnotekind !=  LyXParagraph::MARGIN)
1397                                 || (!figmar
1398                                     && par->footnotekind != LyXParagraph::FIG 
1399                                     && par->footnotekind != LyXParagraph::TAB
1400                                     && par->footnotekind != LyXParagraph::WIDE_FIG 
1401                                     && par->footnotekind != LyXParagraph::WIDE_TAB
1402                                     && par->footnotekind != LyXParagraph::ALGORITHM
1403                                         )
1404                                     )
1405                                 ) {
1406                                 if (par->previous
1407                                     && par->previous->footnoteflag != 
1408                                     LyXParagraph::CLOSED_FOOTNOTE){ /* should be */ 
1409                                         current_view->buffer()->text->SetCursorIntern(par->previous,
1410                                                                       0);
1411                                         current_view->buffer()->text->OpenFootnote();
1412                                 }
1413                         }
1414                 }
1415                 else  {
1416                         if (par->footnoteflag == LyXParagraph::OPEN_FOOTNOTE
1417                             && (
1418                                     (figmar 
1419                                      &&
1420                                      par->footnotekind != LyXParagraph::FOOTNOTE 
1421                                      &&
1422                                      par->footnotekind !=  LyXParagraph::MARGIN
1423                                             )
1424                                     ||
1425                                     (!figmar
1426                                      &&
1427                                      par->footnotekind != LyXParagraph::FIG 
1428                                      &&
1429                                      par->footnotekind != LyXParagraph::TAB
1430                                      &&
1431                                      par->footnotekind != LyXParagraph::WIDE_FIG 
1432                                      &&
1433                                      par->footnotekind != LyXParagraph::WIDE_TAB
1434                                      &&
1435                                      par->footnotekind != LyXParagraph::ALGORITHM
1436                                             )
1437                                     )
1438                                 ){
1439                                 current_view->buffer()->text->SetCursorIntern(par, 0);
1440                                 current_view->buffer()->text->CloseFootnote();
1441                         }
1442                 }
1443                 par = par->next;
1444         }
1445
1446         current_view->buffer()->text->SetCursorIntern(cursor.par, cursor.pos);
1447         current_view->redraw();
1448         current_view->fitCursor();
1449         current_view->updateScrollbar();
1450 }
1451
1452
1453 void MenuLayoutCharacter()
1454 {
1455         static int ow = -1, oh;
1456
1457         if (fd_form_character->form_character->visible) {
1458                 fl_raise_form(fd_form_character->form_character);
1459         } else {
1460                 fl_show_form(fd_form_character->form_character,
1461                              FL_PLACE_MOUSE | FL_FREE_SIZE, FL_FULLBORDER,
1462                              _("Character Style"));
1463                 if (ow < 0) {
1464                         ow = fd_form_character->form_character->w;
1465                         oh = fd_form_character->form_character->h;
1466                 }
1467                 fl_set_form_minsize(fd_form_character->form_character, ow, oh);
1468         }
1469 }
1470
1471
1472 inline void DeactivateParagraphButtons ()
1473 {
1474         fl_deactivate_object (fd_form_paragraph->button_ok);
1475         fl_deactivate_object (fd_form_paragraph->button_apply);
1476         fl_set_object_lcol (fd_form_paragraph->button_ok, FL_INACTIVE);
1477         fl_set_object_lcol (fd_form_paragraph->button_apply, FL_INACTIVE);
1478 }
1479
1480
1481 inline void ActivateParagraphButtons ()
1482 {
1483         fl_activate_object (fd_form_paragraph->button_ok);
1484         fl_activate_object (fd_form_paragraph->button_apply);
1485         fl_set_object_lcol (fd_form_paragraph->button_ok, FL_BLACK);
1486         fl_set_object_lcol (fd_form_paragraph->button_apply, FL_BLACK);
1487 }
1488
1489
1490 inline void DisableParagraphLayout ()
1491 {
1492         DeactivateParagraphButtons();
1493         fl_deactivate_object (fd_form_paragraph->input_labelwidth);
1494         fl_deactivate_object (fd_form_paragraph->check_lines_top);
1495         fl_deactivate_object (fd_form_paragraph->check_lines_bottom);
1496         fl_deactivate_object (fd_form_paragraph->check_pagebreaks_top);
1497         fl_deactivate_object (fd_form_paragraph->check_pagebreaks_bottom);
1498         fl_deactivate_object (fd_form_paragraph->check_noindent);
1499         fl_deactivate_object (fd_form_paragraph->group_radio_alignment);
1500         fl_deactivate_object (fd_form_paragraph->radio_align_right);
1501         fl_deactivate_object (fd_form_paragraph->radio_align_left);
1502         fl_deactivate_object (fd_form_paragraph->radio_align_block);
1503         fl_deactivate_object (fd_form_paragraph->radio_align_center);
1504         fl_deactivate_object (fd_form_paragraph->input_space_above);
1505         fl_deactivate_object (fd_form_paragraph->input_space_below);
1506         fl_deactivate_object (fd_form_paragraph->choice_space_above);
1507         fl_deactivate_object (fd_form_paragraph->choice_space_below);
1508         fl_deactivate_object (fd_form_paragraph->check_space_above);
1509         fl_deactivate_object (fd_form_paragraph->check_space_below);
1510 }
1511
1512
1513 inline void EnableParagraphLayout ()
1514 {
1515         ActivateParagraphButtons();
1516         fl_activate_object (fd_form_paragraph->input_labelwidth);
1517         fl_activate_object (fd_form_paragraph->check_lines_top);
1518         fl_activate_object (fd_form_paragraph->check_lines_bottom);
1519         fl_activate_object (fd_form_paragraph->check_pagebreaks_top);
1520         fl_activate_object (fd_form_paragraph->check_pagebreaks_bottom);
1521         fl_activate_object (fd_form_paragraph->check_noindent);
1522         fl_activate_object (fd_form_paragraph->group_radio_alignment);
1523         fl_activate_object (fd_form_paragraph->radio_align_right);
1524         fl_activate_object (fd_form_paragraph->radio_align_left);
1525         fl_activate_object (fd_form_paragraph->radio_align_block);
1526         fl_activate_object (fd_form_paragraph->radio_align_center);
1527         fl_activate_object (fd_form_paragraph->input_space_above);
1528         fl_activate_object (fd_form_paragraph->input_space_below);
1529         fl_activate_object (fd_form_paragraph->choice_space_above);
1530         fl_activate_object (fd_form_paragraph->choice_space_below);
1531         fl_activate_object (fd_form_paragraph->check_space_above);
1532         fl_activate_object (fd_form_paragraph->check_space_below);
1533 }
1534
1535
1536 bool UpdateLayoutParagraph()
1537 {
1538         if (!current_view->getScreen() || !current_view->available()) {
1539                 if (fd_form_paragraph->form_paragraph->visible) 
1540                         fl_hide_form(fd_form_paragraph->form_paragraph);
1541                 return false;
1542         }
1543
1544         Buffer * buf = current_view->buffer();
1545
1546         fl_set_input(fd_form_paragraph->input_labelwidth,
1547                      buf->text->cursor.par->GetLabelWidthString().c_str());
1548         fl_set_button(fd_form_paragraph->radio_align_right, 0);
1549         fl_set_button(fd_form_paragraph->radio_align_left, 0);
1550         fl_set_button(fd_form_paragraph->radio_align_center, 0);
1551         fl_set_button(fd_form_paragraph->radio_align_block, 0);
1552
1553         int align = buf->text->cursor.par->GetAlign();
1554         if (align == LYX_ALIGN_LAYOUT)
1555                 align = textclasslist.Style(buf->params.textclass,
1556                                   buf->text->cursor.par->GetLayout()).align;
1557          
1558         switch (align) {
1559         case LYX_ALIGN_RIGHT:
1560                 fl_set_button(fd_form_paragraph->radio_align_right, 1);
1561                 break;
1562         case LYX_ALIGN_LEFT:
1563                 fl_set_button(fd_form_paragraph->radio_align_left, 1);
1564                 break;
1565         case LYX_ALIGN_CENTER:
1566                 fl_set_button(fd_form_paragraph->radio_align_center, 1);
1567                 break;
1568         default:
1569                 fl_set_button(fd_form_paragraph->radio_align_block, 1);
1570                 break;
1571         }
1572          
1573         fl_set_button(fd_form_paragraph->check_lines_top,
1574                       buf->text->cursor.par->FirstPhysicalPar()->line_top);
1575         fl_set_button(fd_form_paragraph->check_lines_bottom,
1576                       buf->text->cursor.par->FirstPhysicalPar()->line_bottom);
1577         fl_set_button(fd_form_paragraph->check_pagebreaks_top,
1578                       buf->text->cursor.par->FirstPhysicalPar()->pagebreak_top);
1579         fl_set_button(fd_form_paragraph->check_pagebreaks_bottom,
1580                       buf->text->cursor.par->FirstPhysicalPar()->pagebreak_bottom);
1581         fl_set_button(fd_form_paragraph->check_noindent,
1582                       buf->text->cursor.par->FirstPhysicalPar()->noindent);
1583         fl_set_input (fd_form_paragraph->input_space_above, "");
1584         
1585         switch (buf->text->cursor.par->FirstPhysicalPar()->added_space_top.kind()) {
1586         case VSpace::NONE:
1587                 fl_set_choice (fd_form_paragraph->choice_space_above, 1);
1588                 break;
1589         case VSpace::DEFSKIP:
1590                 fl_set_choice (fd_form_paragraph->choice_space_above, 2);
1591                 break;
1592         case VSpace::SMALLSKIP:
1593                 fl_set_choice (fd_form_paragraph->choice_space_above, 3);
1594                 break;
1595         case VSpace::MEDSKIP:
1596                 fl_set_choice (fd_form_paragraph->choice_space_above, 4);
1597                 break;
1598         case VSpace::BIGSKIP:
1599                 fl_set_choice (fd_form_paragraph->choice_space_above, 5);
1600                 break;
1601         case VSpace::VFILL:
1602                 fl_set_choice (fd_form_paragraph->choice_space_above, 6);
1603                 break;
1604         case VSpace::LENGTH:
1605                 fl_set_choice (fd_form_paragraph->choice_space_above, 7); 
1606                 fl_set_input  (fd_form_paragraph->input_space_above, 
1607                                buf->text->cursor.par->FirstPhysicalPar()->added_space_top.length().asString().c_str());
1608                 break;
1609         }
1610         fl_set_button (fd_form_paragraph->check_space_above,
1611                        buf->text->cursor.par->FirstPhysicalPar()->added_space_top.keep());
1612         fl_set_input (fd_form_paragraph->input_space_below, "");
1613         switch (buf->text->cursor.par->FirstPhysicalPar()->added_space_bottom.kind()) {
1614         case VSpace::NONE:
1615                 fl_set_choice (fd_form_paragraph->choice_space_below,
1616                                1);
1617                 break;
1618         case VSpace::DEFSKIP:
1619                 fl_set_choice (fd_form_paragraph->choice_space_below,
1620                                2);
1621                 break;
1622         case VSpace::SMALLSKIP:
1623                 fl_set_choice (fd_form_paragraph->choice_space_below,
1624                                3);
1625                 break;
1626         case VSpace::MEDSKIP:
1627                 fl_set_choice (fd_form_paragraph->choice_space_below,
1628                                4);
1629                 break;
1630         case VSpace::BIGSKIP:
1631                 fl_set_choice (fd_form_paragraph->choice_space_below,
1632                                5);
1633                 break;
1634         case VSpace::VFILL:
1635                 fl_set_choice (fd_form_paragraph->choice_space_below,
1636                                6);
1637                 break;
1638         case VSpace::LENGTH:
1639                 fl_set_choice (fd_form_paragraph->choice_space_below,
1640                                7); 
1641                 fl_set_input  (fd_form_paragraph->input_space_below, 
1642                                buf->text->cursor.par->FirstPhysicalPar()->added_space_bottom.length().asString().c_str());
1643                 break;
1644         }
1645         fl_set_button (fd_form_paragraph->check_space_below,
1646                        buf->text->cursor.par->FirstPhysicalPar()->added_space_bottom.keep());
1647
1648         fl_set_button(fd_form_paragraph->check_noindent,
1649                       buf->text->cursor.par->FirstPhysicalPar()->noindent);
1650
1651         if (current_view->buffer()->isReadonly()) {
1652                 DisableParagraphLayout();
1653         } else {
1654                 EnableParagraphLayout();
1655         }
1656         return true;
1657 }
1658
1659
1660 void MenuLayoutParagraph()
1661 {
1662         if (UpdateLayoutParagraph()) {
1663                 if (fd_form_paragraph->form_paragraph->visible) {
1664                         fl_raise_form(fd_form_paragraph->form_paragraph);
1665                 } else {
1666                         fl_show_form(fd_form_paragraph->form_paragraph,
1667                                      FL_PLACE_MOUSE, FL_FULLBORDER,
1668                                      _("Paragraph Environment"));
1669                 }
1670         }
1671 }
1672
1673
1674 inline
1675 void DeactivateDocumentButtons ()
1676 {
1677         fl_deactivate_object (fd_form_document->button_ok);
1678         fl_deactivate_object (fd_form_document->button_apply);
1679         fl_set_object_lcol (fd_form_document->button_ok, FL_INACTIVE);
1680         fl_set_object_lcol (fd_form_document->button_apply, FL_INACTIVE);
1681 }
1682
1683
1684 inline
1685 void ActivateDocumentButtons ()
1686 {
1687         fl_activate_object (fd_form_document->button_ok);
1688         fl_activate_object (fd_form_document->button_apply);
1689         fl_set_object_lcol (fd_form_document->button_ok, FL_BLACK);
1690         fl_set_object_lcol (fd_form_document->button_apply, FL_BLACK);
1691 }
1692
1693
1694 inline
1695 void DisableDocumentLayout ()
1696 {
1697         DeactivateDocumentButtons ();
1698         fl_deactivate_object (fd_form_document->group_radio_separation);
1699         fl_deactivate_object (fd_form_document->radio_indent);
1700         fl_deactivate_object (fd_form_document->radio_skip);
1701         fl_deactivate_object (fd_form_document->choice_class);
1702         fl_deactivate_object (fd_form_document->choice_pagestyle);
1703         fl_deactivate_object (fd_form_document->choice_fonts);
1704         fl_deactivate_object (fd_form_document->choice_fontsize);
1705         fl_deactivate_object (fd_form_document->input_float_placement);
1706         fl_deactivate_object (fd_form_document->choice_postscript_driver);
1707         fl_deactivate_object (fd_form_document->choice_inputenc);
1708         fl_deactivate_object (fd_form_document->group_radio_sides);
1709         fl_deactivate_object (fd_form_document->radio_sides_one);
1710         fl_deactivate_object (fd_form_document->radio_sides_two);
1711         fl_deactivate_object (fd_form_document->group_radio_columns);
1712         fl_deactivate_object (fd_form_document->radio_columns_one);
1713         fl_deactivate_object (fd_form_document->radio_columns_two);
1714         fl_deactivate_object (fd_form_document->input_extra);
1715         fl_deactivate_object (fd_form_document->choice_language);
1716         combo_language->deactivate();
1717         fl_deactivate_object (fd_form_document->input_default_skip);
1718         fl_deactivate_object (fd_form_document->choice_default_skip);
1719         fl_deactivate_object (fd_form_document->slider_secnumdepth);
1720         fl_deactivate_object (fd_form_document->slider_tocdepth);
1721         fl_deactivate_object (fd_form_document->choice_spacing);
1722         fl_deactivate_object (fd_form_document->input_spacing);
1723         fl_deactivate_object (fd_form_document->check_use_amsmath);
1724 }
1725
1726
1727 inline
1728 void EnableDocumentLayout ()
1729 {
1730         ActivateDocumentButtons ();
1731         fl_activate_object (fd_form_document->group_radio_separation);
1732         fl_activate_object (fd_form_document->radio_indent);
1733         fl_activate_object (fd_form_document->radio_skip);
1734         fl_activate_object (fd_form_document->choice_class);
1735         fl_activate_object (fd_form_document->choice_pagestyle);
1736         fl_activate_object (fd_form_document->choice_fonts);
1737         fl_activate_object (fd_form_document->choice_fontsize);
1738         fl_activate_object (fd_form_document->input_float_placement);
1739         fl_activate_object (fd_form_document->choice_postscript_driver);
1740         fl_activate_object (fd_form_document->choice_inputenc);
1741         fl_activate_object (fd_form_document->group_radio_sides);
1742         fl_activate_object (fd_form_document->radio_sides_one);
1743         fl_activate_object (fd_form_document->radio_sides_two);
1744         fl_activate_object (fd_form_document->group_radio_columns);
1745         fl_activate_object (fd_form_document->radio_columns_one);
1746         fl_activate_object (fd_form_document->radio_columns_two);
1747         fl_activate_object (fd_form_document->input_extra);
1748         fl_activate_object (fd_form_document->choice_language);
1749         combo_language->activate();
1750         fl_activate_object (fd_form_document->input_default_skip);
1751         fl_activate_object (fd_form_document->choice_default_skip);
1752         fl_activate_object (fd_form_document->slider_secnumdepth);
1753         fl_activate_object (fd_form_document->slider_tocdepth);
1754         fl_activate_object (fd_form_document->choice_spacing);
1755         fl_activate_object (fd_form_document->input_spacing);
1756         fl_activate_object (fd_form_document->check_use_amsmath);
1757 }
1758
1759
1760 bool UpdateLayoutDocument(BufferParams * params)
1761 {
1762         if (!current_view->getScreen() || !current_view->available()) {
1763                 if (fd_form_document->form_document->visible) 
1764                         fl_hide_form(fd_form_document->form_document);
1765                 return false;
1766         }               
1767
1768         if (params == 0)
1769                 params = &current_view->buffer()->params;
1770         LyXTextClass const & tclass = textclasslist.TextClass(params->textclass);
1771         
1772         fl_set_choice_text(fd_form_document->choice_class, 
1773                            textclasslist.DescOfClass(params->textclass).c_str());
1774         combo_language->select_text(params->language.c_str());
1775         
1776         fl_set_choice_text(fd_form_document->choice_fonts, 
1777                            params->fonts.c_str());
1778         fl_set_choice_text(fd_form_document->choice_inputenc, 
1779                            params->inputenc.c_str());
1780         fl_set_choice_text(fd_form_document->choice_postscript_driver, 
1781                            params->graphicsDriver.c_str());
1782
1783         // ale970405+lasgoutt970513
1784         fl_clear_choice(fd_form_document->choice_fontsize);
1785         fl_addto_choice(fd_form_document->choice_fontsize, "default");
1786         fl_addto_choice(fd_form_document->choice_fontsize, 
1787                         tclass.opt_fontsize().c_str());
1788         fl_set_choice(fd_form_document->choice_fontsize, 
1789                       tokenPos(tclass.opt_fontsize(), '|', params->fontsize) + 2);
1790
1791         // ale970405+lasgoutt970513
1792         fl_clear_choice(fd_form_document->choice_pagestyle);
1793         fl_addto_choice(fd_form_document->choice_pagestyle, "default");
1794         fl_addto_choice(fd_form_document->choice_pagestyle, 
1795                         tclass.opt_pagestyle().c_str());
1796     
1797         fl_set_choice(fd_form_document->choice_pagestyle,
1798                       tokenPos(tclass.opt_pagestyle(), '|', params->pagestyle) + 2);
1799
1800         fl_set_button(fd_form_document->radio_indent, 0);
1801         fl_set_button(fd_form_document->radio_skip, 0);
1802     
1803         
1804         fl_set_button(fd_form_document->check_use_amsmath, params->use_amsmath);
1805
1806         if (params->paragraph_separation == BufferParams::PARSEP_INDENT)
1807                 fl_set_button(fd_form_document->radio_indent, 1);
1808         else
1809                 fl_set_button(fd_form_document->radio_skip, 1);
1810
1811         switch (params->getDefSkip().kind()) {
1812         case VSpace::SMALLSKIP: 
1813                 fl_set_choice (fd_form_document->choice_default_skip, 1);
1814                 break;
1815         case VSpace::MEDSKIP: 
1816                 fl_set_choice (fd_form_document->choice_default_skip, 2);
1817                 break;
1818         case VSpace::BIGSKIP: 
1819                 fl_set_choice (fd_form_document->choice_default_skip, 3);
1820                 break;
1821         case VSpace::LENGTH: 
1822                 fl_set_choice (fd_form_document->choice_default_skip, 4);
1823                 fl_set_input (fd_form_document->input_default_skip,
1824                               params->getDefSkip().asLyXCommand().c_str());
1825                 break;
1826         default:
1827                 fl_set_choice (fd_form_document->choice_default_skip, 2);
1828                 break;
1829         }
1830    
1831         fl_set_button(fd_form_document->radio_sides_one, 0);
1832         fl_set_button(fd_form_document->radio_sides_two, 0);
1833    
1834         if (params->sides == 2)
1835                 fl_set_button(fd_form_document->radio_sides_two, 1);
1836         else
1837                 fl_set_button(fd_form_document->radio_sides_one, 1);
1838    
1839         fl_set_button(fd_form_document->radio_columns_one, 0);
1840         fl_set_button(fd_form_document->radio_columns_two, 0);
1841    
1842         if (params->columns == 2)
1843                 fl_set_button(fd_form_document->radio_columns_two, 1);
1844         else
1845                 fl_set_button(fd_form_document->radio_columns_one, 1);
1846    
1847         fl_set_input(fd_form_document->input_spacing, "");
1848         switch (params->spacing.getSpace()) {
1849         case Spacing::Single:
1850         {
1851                 // \singlespacing
1852                 fl_set_choice(fd_form_document->choice_spacing, 1);
1853                 break;
1854         }
1855         case Spacing::Onehalf:
1856         {
1857                 // \onehalfspacing
1858                 fl_set_choice(fd_form_document->choice_spacing, 2);
1859                 break;
1860         }
1861         case Spacing::Double:
1862         {
1863                 // \ doublespacing
1864                 fl_set_choice(fd_form_document->choice_spacing, 3);
1865                 break;
1866         }
1867         case Spacing::Other:
1868         {
1869                 fl_set_choice(fd_form_document->choice_spacing, 4);
1870                 char sval[20];
1871                 sprintf(sval, "%g", params->spacing.getValue()); 
1872                 fl_set_input(fd_form_document->input_spacing, sval);
1873                 break;
1874         }
1875         }
1876
1877
1878         fl_set_counter_value(fd_form_document->slider_secnumdepth, 
1879                              params->secnumdepth);
1880         fl_set_counter_value(fd_form_document->slider_tocdepth, 
1881                              params->tocdepth);
1882         if (!params->float_placement.empty()) { // buffer local (Lgb)
1883                 fl_set_input(fd_form_document->input_float_placement,
1884                              params->float_placement.c_str());
1885         } else {
1886                 fl_set_input(fd_form_document->input_float_placement, "");
1887         }
1888         if (!params->options.empty())
1889                 fl_set_input(fd_form_document->input_extra,
1890                              params->options.c_str());
1891         else
1892                 fl_set_input(fd_form_document->input_extra, "");
1893
1894         if (current_view->buffer()->isSGML()) {
1895                 // bullets not used in SGML derived documents
1896                 fl_deactivate_object(fd_form_document->button_bullets);
1897                 fl_set_object_lcol(fd_form_document->button_bullets,
1898                                    FL_INACTIVE);
1899         } else {
1900                 fl_activate_object(fd_form_document->button_bullets);
1901                 fl_set_object_lcol(fd_form_document->button_bullets,
1902                                    FL_BLACK);
1903         }
1904
1905         if (current_view->buffer()->isReadonly()) {
1906                 DisableDocumentLayout();
1907         } else {
1908                 EnableDocumentLayout();
1909         }
1910
1911         return true;
1912 }
1913
1914
1915 void MenuLayoutDocument()
1916 {
1917         if (UpdateLayoutDocument()) {
1918                 if (fd_form_document->form_document->visible) {
1919                         fl_raise_form(fd_form_document->form_document);
1920                 } else {
1921                         fl_show_form(fd_form_document->form_document,
1922                                      FL_PLACE_MOUSE, FL_FULLBORDER,
1923                                      _("Document Layout"));
1924                 }
1925         }
1926 }
1927
1928
1929 bool UpdateLayoutQuotes()
1930 {
1931         bool update = true;
1932         if (!current_view->getScreen()
1933             || !current_view->available()
1934             || current_view->buffer()->isReadonly())
1935                 update = false;
1936         
1937         if (update) {
1938                 fl_set_choice(fd_form_quotes->choice_quotes_language,
1939                       current_view->buffer()->params.quotes_language + 1);
1940                 fl_set_button(fd_form_quotes->radio_single, 0);
1941                 fl_set_button(fd_form_quotes->radio_double, 0);
1942         
1943                 if (current_view->buffer()->params.quotes_times == InsetQuotes::SingleQ)
1944                         fl_set_button(fd_form_quotes->radio_single, 1);
1945                 else
1946                         fl_set_button(fd_form_quotes->radio_double, 1);
1947         } else if (fd_form_quotes->form_quotes->visible) {
1948                 fl_hide_form(fd_form_quotes->form_quotes);
1949         }
1950         return update;
1951 }
1952
1953
1954 void MenuLayoutQuotes()
1955 {
1956         if (UpdateLayoutQuotes()) {
1957                 if (fd_form_quotes->form_quotes->visible) {
1958                         fl_raise_form(fd_form_quotes->form_quotes);
1959                 } else {
1960                         fl_show_form(fd_form_quotes->form_quotes,
1961                                      FL_PLACE_MOUSE, FL_FULLBORDER,
1962                                      _("Quotes"));
1963                 }
1964         }
1965 }
1966
1967
1968 bool UpdateLayoutPreamble()
1969 {
1970         bool update = true;
1971         if (!current_view->getScreen() || ! current_view->available())
1972             update = false;
1973
1974         if (update) {
1975                 fl_set_input(fd_form_preamble->input_preamble,
1976                      current_view->buffer()->params.preamble.c_str());
1977
1978                 if (current_view->buffer()->isReadonly()) {
1979                   fl_deactivate_object(fd_form_preamble->input_preamble);
1980                   fl_deactivate_object(fd_form_preamble->button_ok);
1981                   fl_deactivate_object(fd_form_preamble->button_apply);
1982                   fl_set_object_lcol(fd_form_preamble->button_ok, FL_INACTIVE);
1983                   fl_set_object_lcol(fd_form_preamble->button_apply, FL_INACTIVE);
1984                 }
1985                 else {
1986                   fl_activate_object(fd_form_preamble->input_preamble);
1987                   fl_activate_object(fd_form_preamble->button_ok);
1988                   fl_activate_object(fd_form_preamble->button_apply);
1989                   fl_set_object_lcol(fd_form_preamble->button_ok, FL_BLACK);
1990                   fl_set_object_lcol(fd_form_preamble->button_apply, FL_BLACK);
1991                 }
1992         } else if (fd_form_preamble->form_preamble->visible) {
1993                 fl_hide_form(fd_form_preamble->form_preamble);
1994         }
1995         return update;
1996 }
1997
1998 void MenuLayoutPreamble()
1999 {
2000         static int ow = -1, oh;
2001
2002         if (UpdateLayoutPreamble()) {
2003                 if (fd_form_preamble->form_preamble->visible) {
2004                         fl_raise_form(fd_form_preamble->form_preamble);
2005                 } else {
2006                         fl_show_form(fd_form_preamble->form_preamble,
2007                                      FL_PLACE_MOUSE | FL_FREE_SIZE,
2008                                      FL_FULLBORDER,
2009                                      _("LaTeX Preamble"));
2010                         if (ow < 0) {
2011                                 ow = fd_form_preamble->form_preamble->w;
2012                                 oh = fd_form_preamble->form_preamble->h;
2013                         }
2014                         fl_set_form_minsize(fd_form_preamble->form_preamble,
2015                                             ow, oh);
2016                 }
2017         }
2018 }
2019
2020
2021 void MenuLayoutSave()
2022 {
2023         if (!current_view->getScreen() || ! current_view->available())
2024             return;
2025
2026         if (AskQuestion(_("Do you want to save the current settings"),
2027                         _("for Character, Document, Paper and Quotes"),
2028                         _("as default for new documents?")))
2029                 current_view->buffer()->saveParamsAsDefaults();
2030 }
2031
2032
2033 void NoteCB()
2034 {
2035         InsetInfo * new_inset = new InsetInfo();
2036         current_view->buffer()->insertInset(new_inset);
2037         new_inset->Edit(0, 0);
2038 }
2039
2040
2041 void OpenStuff()
2042 {
2043         if (current_view->available()) {
2044                 minibuffer->Set(_("Open/Close..."));
2045                 current_view->getScreen()->HideCursor();
2046                 BeforeChange();
2047                 current_view->buffer()->update(-2);
2048                 current_view->buffer()->text->OpenStuff();
2049                 current_view->buffer()->update(0);
2050         }
2051 }
2052
2053
2054 void ToggleFloat()
2055 {
2056         if (current_view->available()) {
2057                 minibuffer->Set(_("Open/Close..."));
2058                 current_view->getScreen()->HideCursor();
2059                 BeforeChange();
2060                 current_view->buffer()->update(-2);
2061                 current_view->buffer()->text->ToggleFootnote();
2062                 current_view->buffer()->update(0);
2063         }
2064 }
2065
2066
2067 void MenuUndo()
2068 {
2069 /*      if (current_view->buffer()->the_locking_inset) {
2070                 minibuffer->Set(_("Undo not yet supported in math mode"));
2071                 return;
2072         }*/
2073    
2074         if (current_view->available()) {
2075                 minibuffer->Set(_("Undo"));
2076                 current_view->getScreen()->HideCursor();
2077                 BeforeChange();
2078                 current_view->buffer()->update(-2);
2079                 if (!current_view->buffer()->text->TextUndo())
2080                         minibuffer->Set(_("No further undo information"));
2081                 else
2082                         current_view->buffer()->update(-1);
2083         }
2084 }
2085
2086
2087 void MenuRedo()
2088 {
2089         if (current_view->buffer()->the_locking_inset) {
2090                 minibuffer->Set(_("Redo not yet supported in math mode"));
2091                 return;
2092         }    
2093    
2094         if (current_view->available()) {
2095                 minibuffer->Set(_("Redo"));
2096                 current_view->getScreen()->HideCursor();
2097                 BeforeChange();
2098                 current_view->buffer()->update(-2);
2099                 if (!current_view->buffer()->text->TextRedo())
2100                         minibuffer->Set(_("No further redo information"));
2101                 else
2102                         current_view->buffer()->update(-1);
2103         }
2104 }
2105
2106
2107 void HyphenationPoint()
2108 {
2109         if (current_view->available())  {
2110                 current_view->getScreen()->HideCursor();
2111                 current_view->buffer()->update(-2);
2112                 InsetSpecialChar * new_inset = 
2113                         new InsetSpecialChar(InsetSpecialChar::HYPHENATION);
2114                 current_view->buffer()->insertInset(new_inset);
2115         }
2116 }
2117
2118
2119 void Ldots()
2120 {
2121         if (current_view->available())  {
2122                 current_view->getScreen()->HideCursor();
2123                 current_view->buffer()->update(-2);
2124                 InsetSpecialChar * new_inset = 
2125                         new InsetSpecialChar(InsetSpecialChar::LDOTS);
2126                 current_view->buffer()->insertInset(new_inset);
2127         }
2128 }
2129
2130
2131 void EndOfSentenceDot()
2132 {
2133         if (current_view->available())  {
2134                 current_view->getScreen()->HideCursor();
2135                 current_view->buffer()->update(-2);
2136                 InsetSpecialChar * new_inset = 
2137                         new InsetSpecialChar(InsetSpecialChar::END_OF_SENTENCE);
2138                 current_view->buffer()->insertInset(new_inset);
2139         }
2140 }
2141
2142
2143 void MenuSeparator()
2144 {
2145         if (current_view->available())  {
2146                 current_view->getScreen()->HideCursor();
2147                 current_view->buffer()->update(-2);
2148                 InsetSpecialChar * new_inset = 
2149                         new InsetSpecialChar(InsetSpecialChar::MENU_SEPARATOR);
2150                 current_view->buffer()->insertInset(new_inset);
2151         }
2152 }
2153
2154
2155 void Newline()
2156 {
2157         if (current_view->available())  {
2158                 current_view->getScreen()->HideCursor();
2159                 current_view->buffer()->update(-2);
2160                 current_view->buffer()->text->InsertChar(LyXParagraph::META_NEWLINE);
2161                 current_view->buffer()->update(-1);
2162         }
2163 }
2164
2165
2166 void ProtectedBlank()
2167 {
2168         if (current_view->available())  {
2169                 current_view->getScreen()->HideCursor();
2170                 current_view->buffer()->update(-2);
2171                 current_view->buffer()->text->InsertChar(LyXParagraph::META_PROTECTED_SEPARATOR);
2172                 current_view->buffer()->update(-1);
2173         }
2174 }
2175
2176
2177 void HFill()
2178 {
2179         if (current_view->available())  {
2180                 current_view->getScreen()->HideCursor();
2181                 current_view->buffer()->update(-2);
2182                 current_view->buffer()->text->InsertChar(LyXParagraph::META_HFILL);
2183                 current_view->buffer()->update(-1);
2184         }
2185 }
2186
2187
2188 /* -------> These CB's use ToggleFree() as the (one and only?) font-changer. 
2189                         They also show the current font state. */
2190
2191 static
2192 void ToggleAndShow(LyXFont const &);
2193
2194
2195 void FontSizeCB(string const & size)
2196 {
2197         LyXFont font(LyXFont::ALL_IGNORE);
2198         font.setGUISize(size);
2199         ToggleAndShow(font);
2200 }
2201
2202
2203 void EmphCB()
2204 {
2205         LyXFont font(LyXFont::ALL_IGNORE);
2206         font.setEmph(LyXFont::TOGGLE);
2207         ToggleAndShow(font);
2208 }
2209
2210
2211 void NounCB()
2212 {
2213         LyXFont font(LyXFont::ALL_IGNORE);
2214         font.setNoun(LyXFont::TOGGLE);
2215         ToggleAndShow(font);
2216 }
2217
2218
2219 void BoldCB()
2220 {
2221         LyXFont font(LyXFont::ALL_IGNORE);
2222         font.setSeries(LyXFont::BOLD_SERIES);
2223         ToggleAndShow(font);
2224 }
2225
2226
2227 void UnderlineCB()
2228 {
2229         LyXFont font(LyXFont::ALL_IGNORE);
2230         font.setUnderbar(LyXFont::TOGGLE);
2231         ToggleAndShow(font);
2232 }
2233
2234
2235 void CodeCB()
2236 {
2237         LyXFont font(LyXFont::ALL_IGNORE);
2238         font.setFamily(LyXFont::TYPEWRITER_FAMILY); // no good
2239         ToggleAndShow(font);
2240 }
2241
2242
2243 void SansCB()
2244 {
2245         LyXFont font(LyXFont::ALL_IGNORE);
2246         font.setFamily(LyXFont::SANS_FAMILY);
2247         ToggleAndShow(font);
2248 }
2249
2250
2251 void RomanCB()
2252 {
2253         LyXFont font(LyXFont::ALL_IGNORE);
2254         font.setFamily(LyXFont::ROMAN_FAMILY);
2255         ToggleAndShow(font);
2256 }
2257
2258
2259 void TexCB()
2260 {
2261         LyXFont font(LyXFont::ALL_IGNORE);
2262         font.setLatex (LyXFont::TOGGLE);
2263         ToggleAndShow(font);
2264 }
2265
2266
2267 void StyleResetCB()
2268 {
2269         LyXFont font(LyXFont::ALL_INHERIT);
2270         ToggleAndShow(font);
2271 }
2272
2273
2274 /* -------> Returns the current font and depth by printing a message. In the
2275  * future perhaps we could try to implement a callback to the button-bar.
2276  * That is, `light' the bold button when the font is currently bold, etc.
2277  */
2278 string CurrentState()
2279 {
2280         string state;
2281         if (current_view->available()) { 
2282                 // I think we should only show changes from the default
2283                 // font. (Asger)
2284                 Buffer * buffer = current_view->buffer();
2285                 LyXFont font = buffer->text->real_current_font;
2286                 LyXFont defaultfont = textclasslist.TextClass(buffer->
2287                                                          params.textclass).defaultfont();
2288                 font.reduce(defaultfont);
2289                 state = _("Font: ") + font.stateText();
2290
2291                 int depth = buffer->text->GetDepth();
2292                 if (depth>0) 
2293                         state += string(_(", Depth: ")) + tostr(depth);
2294         }
2295         return state;
2296 }
2297
2298
2299 /* -------> Does the actual toggle job of the XxxCB() calls above.
2300  * Also shows the current font state.
2301  */
2302 static
2303 void ToggleAndShow(LyXFont const & font)
2304 {
2305         if (current_view->available()) { 
2306                 current_view->getScreen()->HideCursor();
2307                 current_view->buffer()->update(-2);
2308                 current_view->buffer()->text->ToggleFree(font, toggleall);
2309                 current_view->buffer()->update(1);
2310         }
2311         // removed since it overrides the ToggleFree Message about the style
2312         // Since Styles are more "High Level" than raw fonts I think the user
2313         // prefers it like this               Matthias
2314         // FontStateShowCB( 0, 0 );
2315 }
2316
2317
2318 extern "C" void MarginCB(FL_OBJECT *, long)
2319 {
2320         if (current_view->available()) {
2321                 minibuffer->Set(_("Inserting margin note..."));
2322                 current_view->getScreen()->HideCursor();
2323                 current_view->buffer()->update(-2);
2324                 current_view->buffer()->text->InsertFootnoteEnvironment(LyXParagraph::MARGIN);
2325                 current_view->buffer()->update(1);
2326         }
2327 }
2328
2329
2330 extern "C" void FigureCB(FL_OBJECT *, long)
2331 {
2332         if (fd_form_figure->form_figure->visible) {
2333                 fl_raise_form(fd_form_figure->form_figure);
2334         } else {
2335                 fl_show_form(fd_form_figure->form_figure,
2336                              FL_PLACE_MOUSE, FL_FULLBORDER,
2337                              _("Insert Figure"));
2338         }
2339 }
2340
2341
2342 extern "C" void TableCB(FL_OBJECT *, long)
2343 {
2344         if (fd_form_table->form_table->visible) {
2345                 fl_raise_form(fd_form_table->form_table);
2346         } else {
2347                 fl_show_form(fd_form_table->form_table,
2348                              FL_PLACE_MOUSE, FL_FULLBORDER,
2349                              _("Insert Table"));
2350         }
2351 }
2352
2353
2354 void CopyEnvironmentCB()
2355 {
2356         if (current_view->available()) {
2357                 current_view->buffer()->text->copyEnvironmentType();
2358                 /* clear the selection, even if mark_set */ 
2359                 current_view->getScreen()->ToggleSelection();
2360                 current_view->buffer()->text->ClearSelection();
2361                 current_view->buffer()->update(-2);
2362                 minibuffer->Set(_("Paragraph environment type copied"));
2363         }
2364 }
2365
2366
2367 void PasteEnvironmentCB()
2368 {
2369         if (current_view->available()) {
2370                 current_view->buffer()->text->pasteEnvironmentType();
2371                 minibuffer->Set(_("Paragraph environment type set"));
2372                 current_view->buffer()->update(1);
2373         }
2374 }
2375
2376
2377 void CopyCB()
2378 {
2379         if (current_view->available()) {
2380                 current_view->buffer()->text->CopySelection();
2381                 /* clear the selection, even if mark_set */ 
2382                 current_view->getScreen()->ToggleSelection();
2383                 current_view->buffer()->text->ClearSelection();
2384                 current_view->buffer()->update(-2);
2385                 minibuffer->Set(_("Copy"));
2386         }
2387 }
2388
2389
2390 void CutCB()
2391 {
2392         if (current_view->available()) {
2393                 current_view->getScreen()->HideCursor();
2394                 current_view->buffer()->update(-2);
2395                 current_view->buffer()->text->CutSelection();
2396                 current_view->buffer()->update(1);
2397                 minibuffer->Set(_("Cut"));
2398         }
2399 }
2400
2401
2402 void PasteCB()
2403 {
2404         if (!current_view->available()) return;
2405         
2406         minibuffer->Set(_("Paste"));
2407         current_view->getScreen()->HideCursor();
2408         /* clear the selection */ 
2409         current_view->getScreen()->ToggleSelection();
2410         current_view->buffer()->text->ClearSelection();
2411         current_view->buffer()->update(-2);
2412         
2413         /* paste */ 
2414         current_view->buffer()->text->PasteSelection();
2415         current_view->buffer()->update(1);
2416         
2417         /* clear the selection */ 
2418         current_view->getScreen()->ToggleSelection();
2419         current_view->buffer()->text->ClearSelection();
2420         current_view->buffer()->update(-2);
2421 }
2422
2423
2424 extern "C" void MeltCB(FL_OBJECT *, long)
2425 {
2426         if (!current_view->available()) return;
2427         
2428         minibuffer->Set(_("Melt"));
2429         current_view->getScreen()->HideCursor();
2430         BeforeChange();
2431         current_view->buffer()->update(-2);
2432         current_view->buffer()->text->MeltFootnoteEnvironment();
2433         current_view->buffer()->update(1);
2434 }
2435
2436
2437 // Change environment depth.
2438 // if decInc == 0, depth change taking mouse button number into account
2439 // if decInc == 1, increment depth
2440 // if decInc == -1, decrement depth
2441 extern "C" void DepthCB(FL_OBJECT * ob, long decInc)
2442 {
2443         int button = 1;
2444
2445         /* When decInc != 0, fake a mouse button. This allows us to
2446            implement depth-plus and depth-min commands. RVDK_PATCH_5. */
2447         /* check out wether ob is defined, too (Matthias) */ 
2448         if ( decInc < 0 )
2449                 button = 0;
2450         else if (!decInc && ob) {
2451                 button = fl_get_button_numb(ob);
2452         }
2453   
2454         if (current_view->available()) {
2455                 current_view->getScreen()->HideCursor();
2456                 current_view->buffer()->update(-2);
2457                 if (button == 1)
2458                         current_view->buffer()->text->IncDepth();
2459                 else
2460                         current_view->buffer()->text->DecDepth();
2461                 current_view->buffer()->update(1);
2462                 minibuffer->Set(_("Changed environment depth"
2463                                   " (in possible range, maybe not)"));
2464         }
2465 }
2466
2467
2468 // This is both GUI and LyXFont dependent. Don't know where to put it. (Asger)
2469 // Well, it's mostly GUI dependent, so I guess it will stay here. (Asger)
2470 LyXFont UserFreeFont()
2471 {
2472         LyXFont font(LyXFont::ALL_IGNORE);
2473
2474         int pos = fl_get_choice(fd_form_character->choice_family);
2475         switch(pos) {
2476         case 1: font.setFamily(LyXFont::IGNORE_FAMILY); break;
2477         case 2: font.setFamily(LyXFont::ROMAN_FAMILY); break;
2478         case 3: font.setFamily(LyXFont::SANS_FAMILY); break;
2479         case 4: font.setFamily(LyXFont::TYPEWRITER_FAMILY); break;
2480         case 5: font.setFamily(LyXFont::INHERIT_FAMILY); break;
2481         }
2482
2483         pos = fl_get_choice(fd_form_character->choice_series);
2484         switch(pos) {
2485         case 1: font.setSeries(LyXFont::IGNORE_SERIES); break;
2486         case 2: font.setSeries(LyXFont::MEDIUM_SERIES); break;
2487         case 3: font.setSeries(LyXFont::BOLD_SERIES); break;
2488         case 4: font.setSeries(LyXFont::INHERIT_SERIES); break;
2489         }
2490
2491         pos = fl_get_choice(fd_form_character->choice_shape);
2492         switch(pos) {
2493         case 1: font.setShape(LyXFont::IGNORE_SHAPE); break;
2494         case 2: font.setShape(LyXFont::UP_SHAPE); break;
2495         case 3: font.setShape(LyXFont::ITALIC_SHAPE); break;
2496         case 4: font.setShape(LyXFont::SLANTED_SHAPE); break;
2497         case 5: font.setShape(LyXFont::SMALLCAPS_SHAPE); break;
2498         case 6: font.setShape(LyXFont::INHERIT_SHAPE); break;
2499         }
2500
2501         pos = fl_get_choice(fd_form_character->choice_size);
2502         switch(pos) {
2503         case 1: font.setSize(LyXFont::IGNORE_SIZE); break;
2504         case 2: font.setSize(LyXFont::SIZE_TINY); break;
2505         case 3: font.setSize(LyXFont::SIZE_SCRIPT); break;
2506         case 4: font.setSize(LyXFont::SIZE_FOOTNOTE); break;
2507         case 5: font.setSize(LyXFont::SIZE_SMALL); break;
2508         case 6: font.setSize(LyXFont::SIZE_NORMAL); break;
2509         case 7: font.setSize(LyXFont::SIZE_LARGE); break;
2510         case 8: font.setSize(LyXFont::SIZE_LARGER); break;
2511         case 9: font.setSize(LyXFont::SIZE_LARGEST); break;
2512         case 10: font.setSize(LyXFont::SIZE_HUGE); break;
2513         case 11: font.setSize(LyXFont::SIZE_HUGER); break;
2514         case 12: font.setSize(LyXFont::INCREASE_SIZE); break;
2515         case 13: font.setSize(LyXFont::DECREASE_SIZE); break;
2516         case 14: font.setSize(LyXFont::INHERIT_SIZE); break;
2517         }
2518
2519         pos = fl_get_choice(fd_form_character->choice_bar);
2520         switch(pos) {
2521         case 1: font.setEmph(LyXFont::IGNORE);
2522                 font.setUnderbar(LyXFont::IGNORE);
2523                 font.setNoun(LyXFont::IGNORE);
2524                 font.setLatex(LyXFont::IGNORE);
2525                 break;
2526         case 2: font.setEmph(LyXFont::TOGGLE); break;
2527         case 3: font.setUnderbar(LyXFont::TOGGLE); break;
2528         case 4: font.setNoun(LyXFont::TOGGLE); break;
2529         case 5: font.setLatex(LyXFont::TOGGLE); break;
2530         case 6: font.setEmph(LyXFont::INHERIT);
2531                 font.setUnderbar(LyXFont::INHERIT);
2532                 font.setNoun(LyXFont::INHERIT);
2533                 font.setLatex(LyXFont::INHERIT);
2534                 break;
2535         }
2536
2537         pos = fl_get_choice(fd_form_character->choice_color);
2538         switch(pos) {
2539         case 1: font.setColor(LyXFont::IGNORE_COLOR); break;
2540         case 2: font.setColor(LyXFont::NONE); break;
2541         case 3: font.setColor(LyXFont::BLACK); break;
2542         case 4: font.setColor(LyXFont::WHITE); break;
2543         case 5: font.setColor(LyXFont::RED); break;
2544         case 6: font.setColor(LyXFont::GREEN); break;
2545         case 7: font.setColor(LyXFont::BLUE); break;
2546         case 8: font.setColor(LyXFont::CYAN); break;
2547         case 9: font.setColor(LyXFont::MAGENTA); break;
2548         case 10: font.setColor(LyXFont::YELLOW); break;
2549         case 11: font.setColor(LyXFont::INHERIT_COLOR); break;
2550         }
2551
2552         return font; 
2553 }
2554
2555
2556 void FreeCB()
2557 {
2558         ToggleAndShow(UserFreeFont());
2559 }
2560
2561
2562 /* callbacks for form form_title */
2563 extern "C" void TimerCB(FL_OBJECT *, long)
2564 {
2565         // only if the form still exists
2566         if (fd_form_title->form_title != 0) {
2567                 if (fd_form_title->form_title->visible) {
2568                         fl_hide_form(fd_form_title->form_title);
2569                 }
2570                 fl_free_form(fd_form_title->form_title);
2571                 fd_form_title->form_title = 0;
2572         }
2573 }
2574
2575
2576 /* callbacks for form form_paragraph */
2577
2578 extern "C" void ParagraphVSpaceCB(FL_OBJECT * obj, long )
2579 {
2580         // "Synchronize" the choices and input fields, making it
2581         // impossible to commit senseless data.
2582
2583         FD_form_paragraph const * fp = fd_form_paragraph;
2584
2585         if (obj == fp->choice_space_above) {
2586                 if (fl_get_choice (fp->choice_space_above) != 7) {
2587                         fl_set_input (fp->input_space_above, "");
2588                         ActivateParagraphButtons();
2589                 }
2590         } else if (obj == fp->choice_space_below) {
2591                 if (fl_get_choice (fp->choice_space_below) != 7) {
2592                         fl_set_input (fp->input_space_below, "");
2593                         ActivateParagraphButtons();
2594                 }
2595         } else if (obj == fp->input_space_above) {
2596                 string input = fl_get_input (fp->input_space_above);
2597
2598                 if (input.empty()) {
2599                         fl_set_choice (fp->choice_space_above, 1);
2600                         ActivateParagraphButtons();
2601                 }
2602                 else if (isValidGlueLength (input)) {
2603                         fl_set_choice (fp->choice_space_above, 7);
2604                         ActivateParagraphButtons();
2605                 }
2606                 else {
2607                         fl_set_choice (fp->choice_space_above, 7);
2608                         DeactivateParagraphButtons();
2609                 }
2610         } else if (obj == fp->input_space_below) {
2611                 string input = fl_get_input (fp->input_space_below);
2612
2613                 if (input.empty()) {
2614                         fl_set_choice (fp->choice_space_below, 1);
2615                         ActivateParagraphButtons();
2616                 }
2617                 else if (isValidGlueLength (input)) {
2618                         fl_set_choice (fp->choice_space_below, 7);
2619                         ActivateParagraphButtons();
2620                 }
2621                 else {
2622                         fl_set_choice (fp->choice_space_below, 7);
2623                         DeactivateParagraphButtons();
2624                 }
2625         }
2626 }
2627
2628
2629 extern "C" void ParagraphApplyCB(FL_OBJECT *, long)
2630 {
2631         if (!current_view->available())
2632                 return;
2633         
2634         VSpace space_top, space_bottom;
2635         LyXAlignment align;
2636         string labelwidthstring;
2637         bool noindent;
2638
2639         // If a vspace kind is "Length" but there's no text in
2640         // the input field, reset the kind to "None". 
2641         if (fl_get_choice (fd_form_paragraph->choice_space_above) == 7
2642             && !*(fl_get_input (fd_form_paragraph->input_space_above))) {
2643                 fl_set_choice (fd_form_paragraph->choice_space_above, 1);
2644         }
2645         if (fl_get_choice (fd_form_paragraph->choice_space_below) == 7
2646             && !*(fl_get_input (fd_form_paragraph->input_space_below))) {
2647                 fl_set_choice (fd_form_paragraph->choice_space_below, 1);
2648         }
2649    
2650         bool line_top = fl_get_button(fd_form_paragraph->check_lines_top);
2651         bool line_bottom = fl_get_button(fd_form_paragraph->check_lines_bottom);
2652         bool pagebreak_top = fl_get_button(fd_form_paragraph->check_pagebreaks_top);
2653         bool pagebreak_bottom = fl_get_button(fd_form_paragraph->check_pagebreaks_bottom);
2654         switch (fl_get_choice (fd_form_paragraph->choice_space_above)) {
2655         case 1: space_top = VSpace(VSpace::NONE); break;
2656         case 2: space_top = VSpace(VSpace::DEFSKIP); break;
2657         case 3: space_top = VSpace(VSpace::SMALLSKIP); break;
2658         case 4: space_top = VSpace(VSpace::MEDSKIP); break;
2659         case 5: space_top = VSpace(VSpace::BIGSKIP); break;
2660         case 6: space_top = VSpace(VSpace::VFILL); break;
2661         case 7: space_top = VSpace(LyXGlueLength (fl_get_input (fd_form_paragraph->input_space_above))); break;
2662         }
2663         if (fl_get_button (fd_form_paragraph->check_space_above))
2664           space_top.setKeep (true);
2665         switch (fl_get_choice (fd_form_paragraph->choice_space_below)) {
2666         case 1: space_bottom = VSpace(VSpace::NONE); break;
2667         case 2: space_bottom = VSpace(VSpace::DEFSKIP); break;
2668         case 3: space_bottom = VSpace(VSpace::SMALLSKIP); break;
2669         case 4: space_bottom = VSpace(VSpace::MEDSKIP); break;
2670         case 5: space_bottom = VSpace(VSpace::BIGSKIP); break;
2671         case 6: space_bottom = VSpace(VSpace::VFILL); break;
2672         case 7: space_bottom = VSpace(LyXGlueLength (fl_get_input (fd_form_paragraph->input_space_below))); break;
2673         }
2674         if (fl_get_button (fd_form_paragraph->check_space_below))
2675           space_bottom.setKeep (true);
2676
2677         if (fl_get_button(fd_form_paragraph->radio_align_left))
2678                 align = LYX_ALIGN_LEFT;
2679         else if (fl_get_button(fd_form_paragraph->radio_align_right))
2680                 align = LYX_ALIGN_RIGHT;
2681         else if (fl_get_button(fd_form_paragraph->radio_align_center))
2682                 align = LYX_ALIGN_CENTER;
2683         else 
2684                 align = LYX_ALIGN_BLOCK;
2685    
2686         labelwidthstring = fl_get_input(fd_form_paragraph->input_labelwidth);
2687         noindent = fl_get_button(fd_form_paragraph->check_noindent);
2688    
2689         current_view->buffer()->text->SetParagraph(line_top,
2690                                                           line_bottom,
2691                                                           pagebreak_top,
2692                                                           pagebreak_bottom,
2693                                                           space_top,
2694                                                           space_bottom,
2695                                                           align, 
2696                                                           labelwidthstring,
2697                                                           noindent);
2698         current_view->buffer()->update(1);
2699         minibuffer->Set(_("Paragraph layout set"));
2700 }
2701
2702
2703 extern "C" void ParagraphCancelCB(FL_OBJECT *, long)
2704 {
2705         fl_hide_form(fd_form_paragraph->form_paragraph);
2706 }
2707
2708
2709 extern "C" void ParagraphOKCB(FL_OBJECT *ob, long data)
2710 {
2711         ParagraphApplyCB(ob, data);
2712         ParagraphCancelCB(ob, data);
2713 }
2714
2715
2716 /* callbacks for form form_character */
2717
2718 extern "C" void CharacterApplyCB(FL_OBJECT *, long)
2719 {
2720         // we set toggleall locally here, since it should be true for
2721         // all other uses of ToggleAndShow() (JMarc)
2722         toggleall = fl_get_button(fd_form_character->check_toggle_all);
2723         ToggleAndShow( UserFreeFont());
2724         toggleall = true;
2725 }
2726
2727
2728 extern "C" void CharacterCloseCB(FL_OBJECT *, long)
2729 {
2730         fl_hide_form(fd_form_character->form_character);
2731 }
2732
2733
2734 extern "C" void CharacterOKCB(FL_OBJECT *ob, long data)
2735 {
2736         CharacterApplyCB(ob, data);
2737         CharacterCloseCB(ob, data);
2738 }
2739
2740
2741 /* callbacks for form form_document */
2742
2743 void UpdateDocumentButtons(BufferParams const & params) 
2744 {
2745         fl_set_choice(fd_form_document->choice_pagestyle, 1);
2746         
2747         if (params.sides == 2)
2748                 fl_set_button(fd_form_document->radio_sides_two, 1);
2749         else
2750                 fl_set_button(fd_form_document->radio_sides_one, 1);
2751         
2752         if (params.columns == 2)
2753                 fl_set_button(fd_form_document->radio_columns_two, 1);
2754         else
2755                 fl_set_button(fd_form_document->radio_columns_one, 1);
2756         
2757         fl_set_input(fd_form_document->input_extra, params.options.c_str());
2758         fl_set_counter_value(fd_form_document->slider_secnumdepth, 
2759                              params.secnumdepth);
2760         fl_set_counter_value(fd_form_document->slider_tocdepth, 
2761                              params.tocdepth);
2762         
2763 }
2764
2765 extern "C" void ChoiceClassCB(FL_OBJECT * ob, long)
2766 {
2767         ProhibitInput();
2768         if (textclasslist.Load(fl_get_choice(ob)-1)) {
2769                 if (AskQuestion(_("Should I set some parameters to"),
2770                                 fl_get_choice_text(ob),
2771                                 _("the defaults of this document class?"))) {
2772                         BufferParams params = BufferParams();
2773                         params.textclass = fl_get_choice(ob)-1;
2774                         params.useClassDefaults();
2775                         UpdateLayoutDocument(&params);
2776                         UpdateDocumentButtons(params);
2777                 }
2778         } else {
2779                 // unable to load new style
2780                 WriteAlert(_("Conversion Errors!"),
2781                            _("Unable to switch to new document class."),
2782                            _("Reverting to original document class."));
2783                 fl_set_choice(fd_form_document->choice_class, 
2784                               GetCurrentTextClass() + 1);
2785         }
2786         AllowInput();
2787 }
2788
2789
2790 extern "C" void DocumentDefskipCB(FL_OBJECT * obj, long)
2791 {
2792         // "Synchronize" the choice and the input field, so that it
2793         // is impossible to commit senseless data.
2794         FD_form_document const * fd = fd_form_document;
2795
2796         if (obj == fd->choice_default_skip) {
2797                 if (fl_get_choice (fd->choice_default_skip) != 4) {
2798                         fl_set_input (fd->input_default_skip, "");
2799                         ActivateDocumentButtons();
2800                 }
2801         } else if (obj == fd->input_default_skip) {
2802
2803                 char const * input = fl_get_input (fd->input_default_skip);
2804
2805                 if (!*input) {
2806                         fl_set_choice (fd->choice_default_skip, 2);
2807                         ActivateDocumentButtons();
2808                 } else if (isValidGlueLength (input)) {
2809                         fl_set_choice (fd->choice_default_skip, 4);
2810                         ActivateDocumentButtons();
2811                 } else {
2812                         fl_set_choice (fd->choice_default_skip, 4);
2813                         DeactivateDocumentButtons();
2814                 }
2815         }
2816 }
2817
2818
2819 extern "C" void DocumentSpacingCB(FL_OBJECT * obj, long)
2820 {
2821         // "Synchronize" the choice and the input field, so that it
2822         // is impossible to commit senseless data.
2823         FD_form_document const * fd = fd_form_document;
2824
2825         if (obj == fd->choice_spacing
2826             && fl_get_choice (fd->choice_spacing) != 4) {
2827                 fl_set_input(fd->input_spacing, "");
2828         } else if (obj == fd->input_spacing) {
2829
2830                 const char* input = fl_get_input (fd->input_spacing);
2831
2832                 if (!*input) {
2833                         fl_set_choice (fd->choice_spacing, 1);
2834                 } else {
2835                         fl_set_choice (fd->choice_spacing, 4);
2836                 }
2837         }
2838 }
2839
2840
2841 extern "C" void DocumentApplyCB(FL_OBJECT *, long)
2842 {
2843         bool redo = false;
2844         BufferParams *params = &(current_view->buffer()->params);
2845         current_view->buffer()->params.language = 
2846                 combo_language->getline();
2847
2848         // If default skip is a "Length" but there's no text in the
2849         // input field, reset the kind to "Medskip", which is the default.
2850         if (fl_get_choice (fd_form_document->choice_default_skip) == 4
2851             && !*(fl_get_input (fd_form_document->input_default_skip))) {
2852                 fl_set_choice (fd_form_document->choice_default_skip, 2);
2853         }
2854
2855         /* this shouldn't be done automatically IMO. For example I write german
2856          * documents with an american keyboard very often. Matthias */
2857    
2858         /* ChangeKeymap(buffer->parameters.language, TRUE, false,
2859            fl_get_choice(fd_form_document->choice_language)); */
2860         params->fonts = 
2861                 fl_get_choice_text(fd_form_document->choice_fonts);
2862         params->inputenc = 
2863                 fl_get_choice_text(fd_form_document->choice_inputenc);
2864         params->fontsize = 
2865                 fl_get_choice_text(fd_form_document->choice_fontsize);
2866         params->pagestyle = 
2867                 fl_get_choice_text(fd_form_document->choice_pagestyle);
2868         params->graphicsDriver = 
2869                 fl_get_choice_text(fd_form_document->choice_postscript_driver);
2870         params->use_amsmath = 
2871                 fl_get_button(fd_form_document->check_use_amsmath);
2872    
2873         if (!current_view->available())
2874                 return;
2875
2876         LyXTextClassList::ClassList::size_type new_class = fl_get_choice(fd_form_document->choice_class) - 1;
2877         if (params->textclass != new_class) {
2878                 // try to load new_class
2879                 if (textclasslist.Load(new_class)) {
2880                         // successfully loaded
2881                         redo = true;
2882                         minibuffer->Set(_("Converting document to new document class..."));
2883                         int ret = current_view->buffer()->
2884                                 text->
2885                                 SwitchLayoutsBetweenClasses(current_view->buffer()->
2886                                                             params.textclass,
2887                                                             new_class,
2888                                                             current_view->buffer()->
2889                                                             paragraph);
2890
2891                         if (ret){
2892                                 string s;
2893                                 if (ret == 1)
2894                                         s = _("One paragraph couldn't be converted");
2895                                 else {
2896                                         s += tostr(ret);
2897                                         s += _(" paragraphs couldn't be converted");
2898                                 }
2899                                 WriteAlert(_("Conversion Errors!"), s,
2900                                            _("into chosen document class"));
2901                         }
2902
2903                         params->textclass = new_class;
2904                 } else {
2905                         // problem changing class -- warn user and retain old style
2906                         WriteAlert(_("Conversion Errors!"),
2907                                    _("Unable to switch to new document class."),
2908                                    _("Reverting to original document class."));
2909                         fl_set_choice(fd_form_document->choice_class, params->textclass + 1);
2910                 }
2911         }
2912
2913         char tmpsep = params->paragraph_separation;
2914         if (fl_get_button(fd_form_document->radio_indent))
2915                 params->paragraph_separation = BufferParams::PARSEP_INDENT;
2916         else
2917                 params->paragraph_separation = BufferParams::PARSEP_SKIP;
2918         if (tmpsep != params->paragraph_separation)
2919                 redo = true;
2920    
2921         VSpace tmpdefskip = params->getDefSkip();
2922         switch (fl_get_choice (fd_form_document->choice_default_skip)) {
2923         case 1: params->setDefSkip(VSpace(VSpace::SMALLSKIP)); break;
2924         case 2: params->setDefSkip(VSpace(VSpace::MEDSKIP)); break;
2925         case 3: params->setDefSkip(VSpace(VSpace::BIGSKIP)); break;
2926         case 4: params->setDefSkip( 
2927                 VSpace (LyXGlueLength (fl_get_input 
2928                                        (fd_form_document->input_default_skip))));
2929         break;
2930         // DocumentDefskipCB assures that this never happens
2931         default: params->setDefSkip(VSpace(VSpace::MEDSKIP)); break;
2932         }
2933         if (!(tmpdefskip == params->getDefSkip()))
2934                 redo = true;
2935
2936         if (fl_get_button(fd_form_document->radio_columns_two))
2937                 params->columns = 2;
2938         else
2939                 params->columns = 1;
2940         if (fl_get_button(fd_form_document->radio_sides_two))
2941                 params->sides = LyXTextClass::TwoSides;
2942         else
2943                 params->sides = LyXTextClass::OneSide;
2944
2945         Spacing tmpSpacing = params->spacing;
2946         switch(fl_get_choice(fd_form_document->choice_spacing)) {
2947         case 1:
2948                 lyxerr.debug() << "Spacing: SINGLE" << endl;
2949                 params->spacing.set(Spacing::Single);
2950                 break;
2951         case 2:
2952                 lyxerr.debug() << "Spacing: ONEHALF" << endl;
2953                 params->spacing.set(Spacing::Onehalf);
2954                 break;
2955         case 3:
2956                 lyxerr.debug() << "Spacing: DOUBLE" << endl;
2957                 params->spacing.set(Spacing::Double);
2958                 break;
2959         case 4:
2960                 lyxerr.debug() << "Spacing: OTHER" << endl;
2961                 params->spacing.set(Spacing::Other, 
2962                                     fl_get_input(fd_form_document->input_spacing));
2963                 break;
2964         }
2965         if (tmpSpacing != params->spacing)
2966                 redo = true;
2967         
2968         signed char tmpchar =  
2969                 static_cast<signed char>(fl_get_counter_value(fd_form_document->slider_secnumdepth));
2970         if (params->secnumdepth != tmpchar)
2971                 redo = true;
2972         params->secnumdepth = tmpchar;
2973    
2974         params->tocdepth =  
2975                 static_cast<int>(fl_get_counter_value(fd_form_document->slider_tocdepth));
2976
2977         params->float_placement = 
2978                 fl_get_input(fd_form_document->input_float_placement);
2979
2980         // More checking should be done to ensure the string doesn't have
2981         // spaces or illegal placement characters in it. (thornley)
2982
2983         if (redo)
2984                 current_view->redoCurrentBuffer();
2985    
2986         minibuffer->Set(_("Document layout set"));
2987         current_view->buffer()->markDirty();
2988
2989         params->options = 
2990                 fl_get_input(fd_form_document->input_extra);
2991    
2992 }
2993
2994
2995 extern "C" void DocumentCancelCB(FL_OBJECT *, long)
2996 {
2997         fl_hide_form(fd_form_document->form_document);
2998 }
2999
3000
3001 extern "C" void DocumentOKCB(FL_OBJECT * ob, long data)
3002 {
3003         DocumentCancelCB(ob, data);
3004         DocumentApplyCB(ob, data);
3005 }
3006
3007
3008 extern "C" void DocumentBulletsCB(FL_OBJECT *, long)
3009 {
3010         bulletForm();
3011         // bullet callbacks etc. in bullet_panel.C -- ARRae
3012 }
3013
3014
3015 void GotoNote()
3016 {
3017         if (!current_view->getScreen())
3018                 return;
3019    
3020         current_view->getScreen()->HideCursor();
3021         BeforeChange();
3022         current_view->buffer()->update(-2);
3023         LyXCursor tmp;
3024    
3025         if (!current_view->buffer()->text->GotoNextNote()) {
3026                 if (current_view->buffer()->text->cursor.pos 
3027                     || current_view->buffer()->text->cursor.par != 
3028                     current_view->buffer()->text->FirstParagraph())
3029                         {
3030                                 tmp = current_view->buffer()->text->cursor;
3031                                 current_view->buffer()->text->cursor.par = 
3032                                         current_view->buffer()->text->FirstParagraph();
3033                                 current_view->buffer()->text->cursor.pos = 0;
3034                                 if (!current_view->buffer()->text->GotoNextNote()) {
3035                                         current_view->buffer()->text->cursor = tmp;
3036                                         minibuffer->Set(_("No more notes"));
3037                                         LyXBell();
3038                                 }
3039                         } else {
3040                                 minibuffer->Set(_("No more notes"));
3041                                 LyXBell();
3042                         }
3043         }
3044         current_view->buffer()->update(0);
3045         current_view->buffer()->text->sel_cursor = 
3046                 current_view->buffer()->text->cursor;
3047 }
3048
3049
3050 void InsertCorrectQuote()
3051 {
3052         Buffer * cbuffer = current_view->buffer();
3053         char c;
3054
3055         if  (cbuffer->text->cursor.pos )
3056                 c = cbuffer->text->cursor.par->GetChar(cbuffer->text->cursor.pos - 1);
3057         else 
3058                 c = ' ';
3059
3060         cbuffer->insertInset(new InsetQuotes(c, cbuffer->params));
3061 }
3062
3063
3064 /* callbacks for form form_quotes */
3065
3066 extern "C" void QuotesApplyCB(FL_OBJECT *, long)
3067 {
3068         if (!current_view->available())
3069                 return;
3070         
3071         minibuffer->Set(_("Quotes type set"));
3072         //current_view->buffer()->params.quotes_language = 
3073         //      fl_get_choice(fd_form_quotes->choice_quotes_language) - 1;
3074         InsetQuotes::quote_language lga = InsetQuotes::EnglishQ;
3075         switch(fl_get_choice(fd_form_quotes->choice_quotes_language) - 1) {
3076         case 0:
3077                 lga = InsetQuotes::EnglishQ;
3078                 break;
3079         case 1:
3080                 lga = InsetQuotes::SwedishQ;
3081                 break;
3082         case 2:
3083                 lga = InsetQuotes::GermanQ;
3084                 break;
3085         case 3:
3086                 lga = InsetQuotes::PolishQ;
3087                 break;
3088         case 4:
3089                 lga = InsetQuotes::FrenchQ;
3090                 break;
3091         case 5:
3092                 lga = InsetQuotes::DanishQ;
3093                 break;
3094         }
3095         current_view->buffer()->params.quotes_language = lga;
3096         if (fl_get_button(fd_form_quotes->radio_single))   
3097                 current_view->buffer()->
3098                         params.quotes_times = InsetQuotes::SingleQ;
3099         else
3100                 current_view->buffer()->
3101                         params.quotes_times = InsetQuotes::DoubleQ;
3102 }
3103
3104
3105 extern "C" void QuotesCancelCB(FL_OBJECT *, long)
3106 {
3107         fl_hide_form(fd_form_quotes->form_quotes);
3108 }
3109
3110
3111 extern "C" void QuotesOKCB(FL_OBJECT * ob, long data)
3112 {
3113         QuotesApplyCB(ob, data);
3114         QuotesCancelCB(ob, data);
3115 }
3116
3117
3118
3119 /* callbacks for form form_preamble */
3120
3121 extern "C" void PreambleCancelCB(FL_OBJECT *, long)
3122 {
3123         fl_hide_form(fd_form_preamble->form_preamble);
3124 }
3125
3126
3127 extern "C" void PreambleApplyCB(FL_OBJECT *, long)
3128 {
3129         if (!current_view->available())
3130                 return;
3131         
3132         current_view->buffer()->params.preamble = 
3133                 fl_get_input(fd_form_preamble->input_preamble);
3134         current_view->buffer()->markDirty();
3135         minibuffer->Set(_("LaTeX preamble set"));
3136 }
3137
3138    
3139 extern "C" void PreambleOKCB(FL_OBJECT * ob, long data)
3140 {
3141         PreambleApplyCB(ob, data);
3142         PreambleCancelCB(ob, data);
3143 }
3144
3145
3146 /* callbacks for form form_table */
3147
3148 extern "C" void TableApplyCB(FL_OBJECT *, long)
3149 {
3150         if (!current_view->getScreen())
3151                 return;
3152    
3153         // check for tables in tables
3154         if (current_view->buffer()->text->cursor.par->table){
3155                 WriteAlert(_("Impossible Operation!"),
3156                            _("Cannot insert table in table."),
3157                            _("Sorry."));
3158                 return;
3159         }
3160  
3161         minibuffer->Set(_("Inserting table..."));
3162
3163         int ysize = int(fl_get_slider_value(fd_form_table->slider_columns) + 0.5);
3164         int xsize = int(fl_get_slider_value(fd_form_table->slider_rows) + 0.5);
3165    
3166    
3167         current_view->getScreen()->HideCursor();
3168         BeforeChange();
3169         current_view->buffer()->update(-2);
3170    
3171         current_view->buffer()->text->SetCursorParUndo(); 
3172         current_view->buffer()->text->FreezeUndo();
3173
3174         current_view->buffer()->text->BreakParagraph();
3175         current_view->buffer()->update(-1);
3176    
3177         if (current_view->buffer()->text->cursor.par->Last()) {
3178                 current_view->buffer()->text->CursorLeft();
3179       
3180                 current_view->buffer()->text->BreakParagraph();
3181                 current_view->buffer()->update(-1);
3182         }
3183
3184         current_view->buffer()->text->current_font.setLatex(LyXFont::OFF);
3185         //if (!fl_get_button(fd_form_table->check_latex)){
3186         // insert the new wysiwy table
3187         current_view->buffer()->text->SetLayout(0); // standard layout
3188         if (current_view->buffer()->text->cursor.par->footnoteflag == 
3189             LyXParagraph::NO_FOOTNOTE) {
3190                 current_view->buffer()->
3191                         text->SetParagraph(0, 0,
3192                                            0, 0,
3193                                            VSpace (0.3 * current_view->buffer()->
3194                                                    params.spacing.getValue(),
3195                                                    LyXLength::CM),
3196                                            VSpace (0.3 * current_view->buffer()->
3197                                                    params.spacing.getValue(),
3198                                                    LyXLength::CM),
3199                                            LYX_ALIGN_CENTER,
3200                                            string(),
3201                                            0);
3202         }
3203         else
3204                 current_view->buffer()->
3205                         text->SetParagraph(0, 0,
3206                                            0, 0,
3207                                            VSpace(VSpace::NONE),
3208                                            VSpace(VSpace::NONE),
3209                                            LYX_ALIGN_CENTER, 
3210                                            string(),
3211                                            0);
3212
3213         current_view->buffer()->text->cursor.par->table =
3214                 new LyXTable(xsize, ysize);
3215
3216         for (int i = 0; i < xsize * ysize - 1; ++i)
3217                 current_view->buffer()->text->cursor.par->InsertChar(0, LyXParagraph::META_NEWLINE);
3218         current_view->buffer()->text->RedoParagraph();
3219    
3220         current_view->buffer()->text->UnFreezeUndo();
3221      
3222         current_view->buffer()->update(1);
3223         minibuffer->Set(_("Table inserted"));
3224 }
3225
3226
3227 extern "C" void TableCancelCB(FL_OBJECT *, long)
3228 {
3229         fl_hide_form(fd_form_table->form_table);
3230 }
3231
3232
3233 extern "C" void TableOKCB(FL_OBJECT * ob, long data)
3234 {
3235         TableApplyCB(ob, data);
3236         TableCancelCB(ob, data);
3237 }
3238
3239
3240 /* callbacks for form form_print */
3241
3242 extern "C" void PrintCancelCB(FL_OBJECT *, long)
3243 {
3244         fl_hide_form(fd_form_print->form_print);
3245 }
3246
3247 static bool stringOnlyContains (string const & LStr, char const * cset)
3248 {
3249         char const * cstr = LStr.c_str() ;
3250
3251         return strspn(cstr, cset) == strlen(cstr) ;
3252 }
3253
3254 extern "C" void PrintApplyCB(FL_OBJECT *, long)
3255 {
3256         if (!current_view->available())
3257                 return;
3258         Buffer * buffer = current_view->buffer();
3259         string path = OnlyPath(buffer->getFileName());
3260
3261         string pageflag;
3262         if (fl_get_button(fd_form_print->radio_even_pages))
3263                 pageflag = lyxrc->print_evenpage_flag + ' ';
3264         else if (fl_get_button(fd_form_print->radio_odd_pages))
3265                 pageflag = lyxrc->print_oddpage_flag + ' ';
3266
3267 // Changes by Stephan Witt (stephan.witt@beusen.de), 19-Jan-99
3268 // User may give a page (range) list
3269 // User may print multiple (unsorted) copies
3270         string pages = subst(fl_get_input(fd_form_print->input_pages), ';',',');
3271         pages = subst(pages, '+',',');
3272         pages = frontStrip(strip(pages)) ;
3273         while (!pages.empty()) { // a page range was given
3274                 string piece ;
3275                 pages = split (pages, piece, ',') ;
3276                 piece = strip(piece) ;
3277                 piece = frontStrip(piece) ;
3278                 if ( !stringOnlyContains (piece, "0123456789-") ) {
3279                         WriteAlert(_("ERROR!  Unable to print!"),
3280                                 _("Check 'range of pages'!"));
3281                         return;
3282                 }
3283                 if (piece.find('-') == string::npos) { // not found
3284                         pageflag += lyxrc->print_pagerange_flag + piece + '-' + piece + ' ' ;
3285                 } else if (suffixIs(piece, "-") ) { // missing last page
3286                         pageflag += lyxrc->print_pagerange_flag + piece + "1000 ";
3287                 } else if (prefixIs(piece, "-") ) { // missing first page
3288                         pageflag += lyxrc->print_pagerange_flag + '1' + piece + ' ' ;
3289                 } else {
3290                         pageflag += lyxrc->print_pagerange_flag + piece + ' ' ;
3291                 }
3292         }
3293    
3294         string copies = frontStrip(strip(fl_get_input(fd_form_print->input_copies)));
3295         if (!copies.empty()) { // a number of copies was given
3296                 if ( !stringOnlyContains (copies, "0123456789") ) {
3297                         WriteAlert(_("ERROR!  Unable to print!"),
3298                                 _("Check 'number of copies'!"));
3299                         return;
3300                 }
3301                 if (fl_get_button(fd_form_print->do_unsorted))
3302                         pageflag += lyxrc->print_copies_flag;
3303                 else
3304                         pageflag += lyxrc->print_collcopies_flag;
3305                 pageflag += " " + copies + ' ' ;
3306         }
3307
3308         string reverseflag;
3309         if (fl_get_button(fd_form_print->radio_order_reverse))
3310                 reverseflag = lyxrc->print_reverse_flag + ' ';
3311    
3312         string orientationflag;
3313         if (buffer->params.orientation == BufferParams::ORIENTATION_LANDSCAPE)
3314                 orientationflag = lyxrc->print_landscape_flag + ' ';
3315    
3316         string ps_file = fl_get_input(fd_form_print->input_file);
3317         string printer = strip(fl_get_input(fd_form_print->input_printer));
3318
3319         string printerflag;
3320         if (lyxrc->print_adapt_output // printer name should be passed to dvips
3321             && ! printer.empty()) // a printer name has been given
3322                 printerflag = lyxrc->print_to_printer + printer + ' ';
3323      
3324         string extraflags;
3325         if (!lyxrc->print_extra_options.empty())
3326                 extraflags = lyxrc->print_extra_options + ' ';
3327
3328         string command = lyxrc->print_command + ' ' 
3329                 + printerflag + pageflag + reverseflag 
3330                 + orientationflag + extraflags;
3331  
3332         char real_papersize = buffer->params.papersize;
3333         if (real_papersize == BufferParams::PAPER_DEFAULT)
3334                 real_papersize = lyxrc->default_papersize;
3335         
3336         string paper;
3337         switch (real_papersize) {
3338         case BufferParams::PAPER_USLETTER:
3339                 paper = "letter";
3340                 break;
3341         case BufferParams::PAPER_A3PAPER:
3342                 paper = "a3";
3343                 break;
3344         case BufferParams::PAPER_A4PAPER:
3345                 paper = "a4";
3346                 break;
3347         case BufferParams::PAPER_A5PAPER:
3348                 paper = "a5";
3349                 break;
3350         case BufferParams::PAPER_B5PAPER:
3351                 paper = "b5";
3352                 break;
3353         case BufferParams::PAPER_EXECUTIVEPAPER:
3354                 paper = "foolscap";
3355                 break;
3356         case BufferParams::PAPER_LEGALPAPER:
3357                 paper = "legal";
3358                 break;
3359         default: /* If nothing else fits, keep an empty value... */
3360                 break;
3361         }
3362
3363         if (buffer->params.use_geometry
3364             && buffer->params.papersize2 == BufferParams::VM_PAPER_CUSTOM
3365             && !lyxrc->print_paper_dimension_flag.empty()
3366             && !buffer->params.paperwidth.empty()
3367             && !buffer->params.paperheight.empty()) {
3368                 // using a custom papersize
3369                 command += ' ';
3370                 command += lyxrc->print_paper_dimension_flag + ' ';
3371                 command += buffer->params.paperwidth + ',';
3372                 command += buffer->params.paperheight + ' ';
3373         } else if (!lyxrc->print_paper_flag.empty()
3374                    && !paper.empty()
3375                    && (real_papersize != BufferParams::PAPER_USLETTER ||
3376                        buffer->params.orientation == BufferParams::ORIENTATION_PORTRAIT)) {
3377                 command += " " + lyxrc->print_paper_flag + " " + paper + " ";
3378         }
3379         if (fl_get_button(fd_form_print->radio_file))
3380                 command += lyxrc->print_to_file 
3381                            + QuoteName(MakeAbsPath(ps_file, path));
3382         else if (!lyxrc->print_spool_command.empty())
3383                 command += lyxrc->print_to_file 
3384                         + QuoteName(ps_file);
3385         
3386         // push directorypath, if necessary 
3387         if (lyxrc->use_tempdir || (IsDirWriteable(path) < 1)){
3388                 path = buffer->tmppath;
3389         }
3390         Path p(path);
3391
3392         bool result;
3393         if (!lyxrc->print_spool_command.empty() && 
3394             !fl_get_button(fd_form_print->radio_file)) {
3395                 string command2 = lyxrc->print_spool_command + ' ';
3396                 if (!printer.empty())
3397                         command2 += lyxrc->print_spool_printerprefix 
3398                                     + printer;
3399                 // First run dvips and, if succesful, then spool command
3400                 if ((result = RunScript(buffer, true, command))) {
3401                         result = RunScript(buffer, false, command2, ps_file);
3402                 }
3403         } else
3404                 result = RunScript(buffer, false, command);
3405
3406         if (!result)
3407                 WriteAlert(_("Error:"),
3408                            _("Unable to print"),
3409                            _("Check that your parameters are correct"));
3410 }
3411
3412
3413 extern "C" void PrintOKCB(FL_OBJECT * ob, long data)
3414 {
3415         PrintCancelCB(ob, data);  
3416         PrintApplyCB(ob, data);
3417 }
3418
3419
3420 /* callbacks for form form_figure */
3421
3422 extern "C" void FigureApplyCB(FL_OBJECT *, long)
3423 {
3424         if (!current_view->available())
3425                 return;
3426
3427         Buffer * buffer = current_view->buffer();
3428         if(buffer->isReadonly()) // paranoia
3429                 return;
3430         
3431         minibuffer->Set(_("Inserting figure..."));
3432         if (fl_get_button(fd_form_figure->radio_inline)
3433             || buffer->text->cursor.par->table) {
3434                 InsetFig * new_inset = new InsetFig(100, 20, buffer);
3435                 buffer->insertInset(new_inset);
3436                 minibuffer->Set(_("Figure inserted"));
3437                 new_inset->Edit(0, 0);
3438                 return;
3439         }
3440         
3441         current_view->getScreen()->HideCursor();
3442         buffer->update(-2);
3443         BeforeChange();
3444       
3445         buffer->text->SetCursorParUndo(); 
3446         buffer->text->FreezeUndo();
3447
3448         buffer->text->BreakParagraph();
3449         buffer->update(-1);
3450       
3451         if (buffer->text->cursor.par->Last()) {
3452                 buffer->text->CursorLeft();
3453          
3454                 buffer->text->BreakParagraph();
3455                 buffer->update(-1);
3456         }
3457
3458         // The standard layout should always be numer 0;
3459         buffer->text->SetLayout(0);
3460         
3461         if (buffer->text->cursor.par->footnoteflag == 
3462             LyXParagraph::NO_FOOTNOTE) {
3463                 buffer->text->
3464                         SetParagraph(0, 0,
3465                                      0, 0,
3466                                      VSpace (0.3 * buffer->params.spacing.getValue(),
3467                                              LyXLength::CM),
3468                                      VSpace (0.3 *
3469                                              buffer->params.spacing.getValue(),
3470                                              LyXLength::CM),
3471                                      LYX_ALIGN_CENTER, string(), 0);
3472         } else
3473                 buffer->text->SetParagraph(0, 0,
3474                                            0, 0,
3475                                            VSpace(VSpace::NONE),
3476                                            VSpace(VSpace::NONE),
3477                                            LYX_ALIGN_CENTER, 
3478                                            string(),
3479                                            0);
3480         
3481         buffer->update(-1);
3482       
3483         Inset * new_inset = new InsetFig(100, 100, buffer);
3484         buffer->insertInset(new_inset);
3485         new_inset->Edit(0, 0);
3486         buffer->update(0);
3487         minibuffer->Set(_("Figure inserted"));
3488         buffer->text->UnFreezeUndo();
3489 }
3490
3491    
3492 extern "C" void FigureCancelCB(FL_OBJECT *, long)
3493 {
3494         fl_hide_form(fd_form_figure->form_figure);
3495 }
3496
3497
3498 extern "C" void FigureOKCB(FL_OBJECT * ob, long data)
3499 {
3500         FigureApplyCB(ob, data);
3501         FigureCancelCB(ob, data);
3502 }
3503
3504
3505 extern "C" void ScreenApplyCB(FL_OBJECT *, long)
3506 {
3507         lyxrc->roman_font_name = fl_get_input(fd_form_screen->input_roman);
3508         lyxrc->sans_font_name = fl_get_input(fd_form_screen->input_sans);
3509         lyxrc->typewriter_font_name = fl_get_input(fd_form_screen->input_typewriter);
3510         lyxrc->font_norm = fl_get_input(fd_form_screen->input_font_norm);
3511         lyxrc->zoom = atoi(fl_get_input(fd_form_screen->intinput_size));
3512         fontloader.update();
3513    
3514         // All buffers will need resize
3515         bufferlist.resize();
3516
3517         minibuffer->Set(_("Screen options set"));
3518 }
3519
3520
3521 extern "C" void ScreenCancelCB(FL_OBJECT *, long)
3522 {
3523         fl_hide_form(fd_form_screen->form_screen);
3524 }
3525
3526
3527 extern "C" void ScreenOKCB(FL_OBJECT * ob, long data)
3528 {
3529         ScreenCancelCB(ob, data);
3530         ScreenApplyCB(ob, data);
3531 }
3532
3533
3534 void LaTeXOptions()
3535 {
3536         if (!current_view->available())
3537                 return;
3538
3539         fl_set_button(fd_latex_options->accents,
3540                       (int)current_view->buffer()->params.allowAccents);
3541         
3542         if (fd_latex_options->LaTeXOptions->visible) {
3543                 fl_raise_form(fd_latex_options->LaTeXOptions);
3544         } else {
3545                 fl_show_form(fd_latex_options->LaTeXOptions,
3546                              FL_PLACE_MOUSE, FL_FULLBORDER,
3547                              _("LaTeX Options"));
3548         }
3549 }
3550
3551
3552 // This function runs "configure" and then rereads lyx.defaults to
3553 // reconfigure the automatic settings.
3554 void Reconfigure()
3555 {
3556         minibuffer->Set(_("Running configure..."));
3557
3558         // Run configure in user lyx directory
3559         Path p(user_lyxdir);
3560         Systemcalls one(Systemcalls::System, 
3561                           AddName(system_lyxdir, "configure"));
3562         p.pop();
3563         minibuffer->Set(_("Reloading configuration..."));
3564         lyxrc->read(LibFileSearch(string(), "lyxrc.defaults"));
3565         WriteAlert(_("The system has been reconfigured."), 
3566                    _("You need to restart LyX to make use of any"),
3567                    _("updated document class specifications."));
3568 }
3569
3570
3571 /* these functions are for the spellchecker */ 
3572 char * NextWord(float & value)
3573 {
3574         if (!current_view->available()){
3575                 value = 1;
3576                 return 0;
3577         }
3578    
3579         char * string =  current_view->buffer()->text->SelectNextWord(value);
3580
3581         return string;
3582 }
3583
3584   
3585 void SelectLastWord()
3586 {
3587         if (!current_view->available())
3588                 return;
3589    
3590         current_view->getScreen()->HideCursor();
3591         BeforeChange(); 
3592         current_view->buffer()->text->SelectSelectedWord();
3593         current_view->getScreen()->ToggleSelection(false);
3594         current_view->buffer()->update(0);
3595 }
3596
3597
3598 void EndOfSpellCheck()
3599 {
3600         if (!current_view->available())
3601                 return;
3602    
3603         current_view->getScreen()->HideCursor();
3604         BeforeChange(); 
3605         current_view->buffer()->text->SelectSelectedWord();
3606         current_view->buffer()->text->ClearSelection();
3607         current_view->buffer()->update(0);
3608 }
3609
3610
3611 void ReplaceWord(string const & replacestring)
3612 {
3613         if (!current_view->getScreen())
3614                 return;
3615
3616         current_view->getScreen()->HideCursor();
3617         current_view->buffer()->update(-2);
3618    
3619         /* clear the selection (if there is any) */ 
3620         current_view->getScreen()->ToggleSelection(false);
3621         current_view->buffer()->text->
3622                 ReplaceSelectionWithString(replacestring.c_str());
3623    
3624         current_view->buffer()->text->SetSelectionOverString(replacestring.c_str());
3625
3626         // Go back so that replacement string is also spellchecked
3627         for (string::size_type i = 0; i < replacestring.length() + 1; ++i) {
3628                 current_view->buffer()->text->CursorLeftIntern();
3629         }
3630         current_view->buffer()->update(1);
3631 }
3632 // End of spellchecker stuff
3633
3634
3635
3636 //
3637 // Table of Contents
3638 //
3639
3640 struct TocList {
3641         int counter[6];
3642         bool appendix;
3643         TocList * next;
3644 };
3645
3646
3647 static TocList * toclist = 0;
3648
3649
3650 extern "C" void TocSelectCB(FL_OBJECT * ob, long)
3651 {
3652         if (!current_view->available())
3653                 return;
3654    
3655         TocList * tmptoclist = toclist;
3656         int i = fl_get_browser(ob);
3657         for (int a = 1; a < i && tmptoclist->next; ++a) {
3658                 tmptoclist = tmptoclist->next;
3659         }
3660
3661         if (!tmptoclist)
3662                 return;
3663      
3664
3665         LyXParagraph * par = current_view->buffer()->paragraph;
3666         while (par && (par->GetFirstCounter(0) != tmptoclist->counter[0] ||
3667                        par->GetFirstCounter(1) != tmptoclist->counter[1] ||
3668                        par->GetFirstCounter(2) != tmptoclist->counter[2] ||
3669                        par->GetFirstCounter(3) != tmptoclist->counter[3] ||
3670                        par->GetFirstCounter(4) != tmptoclist->counter[4] ||
3671                        par->GetFirstCounter(5) != tmptoclist->counter[5] ||
3672                        par->appendix != tmptoclist->appendix)) {
3673                 par = par->LastPhysicalPar()->Next();
3674         }
3675    
3676         if (par) {
3677                 BeforeChange();
3678                 current_view->buffer()->text->SetCursor(par, 0);
3679                 current_view->buffer()->text->sel_cursor = 
3680                         current_view->buffer()->text->cursor;
3681                 current_view->buffer()->update(0);
3682         }
3683         else {
3684                 WriteAlert(_("Error"), 
3685                            _("Couldn't find this label"), 
3686                            _("in current document."));
3687         }
3688           
3689 }
3690
3691
3692 extern "C" void TocCancelCB(FL_OBJECT *, long)
3693 {
3694         fl_hide_form(fd_form_toc->form_toc);
3695 }
3696
3697
3698 extern "C" void TocUpdateCB(FL_OBJECT *, long)
3699 {
3700         static LyXParagraph * stapar = 0;
3701         TocList * tmptoclist = 0;
3702    
3703         /* deleted the toclist */ 
3704         if (toclist){
3705                 while (toclist){
3706                         tmptoclist = toclist->next;
3707                         delete toclist;
3708                         toclist = tmptoclist;
3709                 }
3710         }
3711         toclist = 0;
3712         tmptoclist = toclist;
3713
3714
3715         fl_clear_browser(fd_form_toc->browser_toc);
3716         if (!current_view->available()) {
3717                 fl_add_browser_line(fd_form_toc->browser_toc,
3718                                     _("*** No Document ***"));
3719                 return;
3720         }
3721         fl_hide_object(fd_form_toc->browser_toc);
3722         /* get the table of contents */ 
3723         LyXParagraph * par = current_view->buffer()->paragraph;
3724         char labeltype;
3725         char * line = new char[200];
3726         int pos = 0;
3727         unsigned char c;
3728         int topline = 0;
3729    
3730         if (stapar == par)
3731                 topline = fl_get_browser_topline(fd_form_toc->browser_toc);
3732         stapar = par;
3733    
3734         while (par) {
3735                 labeltype = textclasslist.Style(current_view->buffer()->params.textclass, 
3736                                            par->GetLayout()).labeltype;
3737       
3738                 if (labeltype >= LABEL_COUNTER_CHAPTER
3739                     && labeltype <= LABEL_COUNTER_CHAPTER +
3740                     current_view->buffer()->params.tocdepth) {
3741                         /* insert this into the table of contents */ 
3742                         /* first indent a little bit */ 
3743                         
3744                         for (pos = 0; 
3745                              pos < (labeltype - 
3746                                     textclasslist.TextClass(current_view->buffer()->
3747                                                        params.textclass).maxcounter()) * 4 + 2;
3748                              pos++)
3749                                 line[pos] = ' ';
3750                         
3751                         // Then the labestring
3752                         if (!par->labelstring.empty()) {
3753                                 string::size_type i = 0;
3754                                 while (pos < 199 && i < par->labelstring.length()) {
3755                                         line[pos] = par->labelstring[i];
3756                                         i++;
3757                                         pos++;
3758                                 }
3759                         }
3760          
3761                         line[pos] = ' ';
3762                         pos++;
3763                         
3764                         /* now the contents */
3765                         LyXParagraph::size_type i = 0;
3766                         while (pos < 199 && i < par->size()) {
3767                                 c = par->GetChar(i);
3768                                 if (isprint(c) || c >= 128) {
3769                                         line[pos] = c;
3770                                         pos++;
3771                                 }
3772                                 i++;
3773                         }
3774                         line[pos] = '\0';
3775                         fl_add_browser_line(fd_form_toc->browser_toc, line);
3776                         
3777                         /* make a toclist entry */
3778                         if (!tmptoclist){
3779                                 tmptoclist = new TocList;
3780                                 toclist = tmptoclist;
3781                         } else {
3782                                 tmptoclist->next = new TocList;
3783                                 tmptoclist = tmptoclist->next;
3784                         }
3785                         
3786                         tmptoclist->next = 0;
3787                         int a = 0;
3788                         for (a = 0; a<6; a++){
3789                                 tmptoclist->counter[a] = par->GetFirstCounter(a);
3790                         }
3791                         tmptoclist->appendix = par->appendix;
3792                 }
3793                 par = par->LastPhysicalPar()->Next();
3794                 
3795         }
3796         delete[] line;
3797         fl_set_browser_topline(fd_form_toc->browser_toc, topline);
3798         fl_show_object(fd_form_toc->browser_toc);
3799 }
3800
3801
3802 /* callbacks for form form_ref */
3803 extern "C" void RefSelectCB(FL_OBJECT *, long data)
3804 {
3805         if (!current_view->available())
3806                 return;
3807
3808         string s = 
3809                 fl_get_browser_line(fd_form_ref->browser_ref,
3810                                     fl_get_browser(fd_form_ref->browser_ref));
3811         string u = frontStrip(strip(fl_get_input(fd_form_ref->ref_name)));
3812
3813         if (s.empty())
3814                 return;
3815
3816         if (data == 2) {
3817                 current_view->owner()->getLyXFunc()->Dispatch(LFUN_REFGOTO, s.c_str());
3818                 return;
3819         }
3820             
3821         string t;
3822         if (data == 0)
3823                 t += "\\ref";
3824         else
3825                 t += "\\pageref";
3826
3827         if(current_view->buffer()->isSGML())
3828                 t += "[" + u + "]" + "{" + s + "}";
3829         else
3830                 t += "{" + s + "}";
3831
3832         Inset * new_inset = 
3833                 new InsetRef(t, current_view->buffer());
3834         current_view->buffer()->insertInset(new_inset);
3835 }
3836
3837
3838 extern "C" void RefUpdateCB(FL_OBJECT *, long)
3839 {
3840         if (!current_view->available()) {
3841                 fl_clear_browser(fd_form_ref->browser_ref);
3842                 return;
3843         }
3844
3845         FL_OBJECT * brow = fd_form_ref->browser_ref;
3846
3847         // Get the current line, in order to restore it later
3848         char const * const btmp = fl_get_browser_line(brow,
3849                                                      fl_get_browser(brow));
3850         string currentstr = btmp ? btmp : "";
3851         //string currentstr = fl_get_browser_line(brow,
3852         //                                      fl_get_browser(brow));
3853
3854         fl_clear_browser(brow);
3855
3856         string refs = current_view->buffer()->getReferenceList('\n');
3857         int topline = 1;
3858
3859 #if FL_REVISION > 85
3860         fl_addto_browser_chars(brow, refs.c_str());
3861         int total_lines = fl_get_browser_maxline(brow);
3862         for (int i = 1; i <= total_lines ; i++) {
3863                 if (fl_get_browser_line(brow, i) == currentstr) {
3864                         topline = i;
3865                         break;
3866                 }
3867         }
3868         fl_set_browser_topline(brow, topline);
3869 #else
3870         // Keep the old ugly code for xforms 0.81 compatibility
3871         string curr_ref;
3872         int ref_num = 0;
3873                                        
3874         while(true) {
3875                 curr_ref = refs.token('\n', ref_num);
3876                 if (curr_ref.empty())
3877                         break;
3878                 fl_add_browser_line(brow, curr_ref.c_str());
3879                 ref_num++;
3880         }
3881 #endif
3882
3883         if (!fl_get_browser_maxline(brow)) {
3884                 fl_add_browser_line(brow, 
3885                                     _("*** No labels found in document ***"));
3886                 fl_deactivate_object(brow);
3887         } else {
3888                 fl_select_browser_line(brow, topline);
3889                 fl_activate_object(brow);
3890         }
3891         if (current_view->buffer()->isReadonly()) {
3892                 // would be better to de/activate insert buttons
3893                 // but that's more work... besides this works. ARRae
3894                 fl_hide_form(fd_form_ref->form_ref);
3895         }
3896         if (!current_view->buffer()->isSGML()) {
3897                 fl_deactivate_object(fd_form_ref->ref_name);
3898                 fl_set_object_lcol(fd_form_ref->ref_name, FL_INACTIVE);
3899         }
3900         else {
3901                 fl_activate_object(fd_form_ref->ref_name);
3902                 fl_set_object_lcol(fd_form_ref->ref_name, FL_BLACK);
3903         }
3904 }
3905
3906
3907 extern "C" void RefHideCB(FL_OBJECT *, long)
3908 {
3909         fl_hide_form(fd_form_ref->form_ref);
3910 }
3911
3912
3913 void UpdateInset(Inset * inset, bool mark_dirty)
3914 {
3915         if (!inset)
3916                 return;
3917
3918         /* very first check for locking insets*/
3919         if (current_view->buffer()->the_locking_inset == inset){
3920                 if (current_view->buffer()->text->UpdateInset(inset)){
3921                         current_view->update();
3922                         if (mark_dirty){
3923                                 if (current_view->buffer()->isLyxClean())
3924                                         minibuffer->setTimer(4);
3925                                 current_view->buffer()->markDirty();
3926                         }
3927                         current_view->updateScrollbar();
3928                         return;
3929                 }
3930         }
3931   
3932         /* first check the current buffer */
3933         if (current_view->available()){
3934                 current_view->getScreen()->HideCursor();
3935                 current_view->buffer()->update(-3);
3936                 if (current_view->buffer()->text->UpdateInset(inset)){
3937                         if (mark_dirty)
3938                                 current_view->buffer()->update(1);
3939                         else 
3940                                 current_view->buffer()->update(3);
3941                         return;
3942                 }
3943         }
3944   
3945         // check all buffers
3946         bufferlist.updateInset(inset, mark_dirty);
3947
3948 }
3949
3950
3951 /* these functions return 1 if an error occured, 
3952    otherwise 0 */
3953 int LockInset(UpdatableInset * inset)
3954 {
3955         if (!current_view->buffer()->the_locking_inset && inset){
3956                 current_view->buffer()->the_locking_inset = inset;
3957                 return 0;
3958         }
3959         return 1;
3960 }
3961
3962
3963 void ShowLockedInsetCursor(long x, long y, int asc, int desc)
3964 {
3965         if (current_view->buffer()->the_locking_inset &&
3966             current_view->getScreen()){
3967                 y += current_view->buffer()->text->cursor.y;
3968                 current_view->getScreen()->ShowManualCursor(x, y,
3969                                                             asc, desc);
3970         }
3971 }
3972
3973
3974 void HideLockedInsetCursor(long x, long y, int asc, int desc)
3975 {
3976         if (current_view->buffer()->the_locking_inset &&
3977             current_view->getScreen()){
3978                 y += current_view->buffer()->text->cursor.y;
3979                 current_view->getScreen()->HideManualCursor(x, y,
3980                                                             asc, desc);
3981         }
3982 }
3983
3984
3985 void FitLockedInsetCursor(long x, long y, int asc, int desc)
3986 {
3987         if (current_view->buffer()->the_locking_inset &&
3988             current_view->getScreen()){
3989                 y += current_view->buffer()->text->cursor.y;
3990                 if (current_view->getScreen()->FitManualCursor(x, y, asc, desc))
3991                         current_view->updateScrollbar();
3992         }
3993 }
3994
3995
3996 int UnlockInset(UpdatableInset * inset)
3997 {
3998         if (inset &&
3999             current_view->buffer()->the_locking_inset == inset){
4000                 inset->InsetUnlock();
4001                 current_view->buffer()->the_locking_inset = 0;
4002                 current_view->buffer()->text->FinishUndo();
4003                 return 0;
4004         }
4005         return bufferlist.unlockInset(inset);
4006 }
4007
4008
4009 void LockedInsetStoreUndo(Undo::undo_kind kind)
4010 {
4011         if (!current_view->buffer()->the_locking_inset)
4012                 return; // shouldn't happen
4013         if (kind == Undo::EDIT) // in this case insets would not be stored!
4014                 kind = Undo::FINISH;
4015         current_view->buffer()->text->SetUndo(kind,
4016                               current_view->buffer()->text->cursor.par->
4017                               ParFromPos(current_view->buffer()->text->cursor.pos)->previous, 
4018                               current_view->buffer()->text->cursor.par->
4019                               ParFromPos(current_view->buffer()->text->cursor.pos)->next); 
4020 }
4021
4022
4023 void PutInsetIntoInsetUpdateList(Inset * inset)
4024 {
4025         if (inset) {
4026                 InsetUpdateStruct * tmp = new InsetUpdateStruct();
4027                 tmp->inset = inset;
4028                 tmp->next = InsetUpdateList;
4029                 InsetUpdateList = tmp;
4030         }
4031 }
4032
4033
4034 void UpdateInsetUpdateList()
4035 {
4036         InsetUpdateStruct * tmp = InsetUpdateList;
4037         while (tmp) {
4038                 UpdateInset(tmp->inset, false); // "false" because no document change
4039                 tmp = tmp->next;
4040         }
4041   
4042         // delete the update list
4043         while (InsetUpdateList) {
4044                 tmp = InsetUpdateList;
4045                 InsetUpdateList = InsetUpdateList->next;
4046                 delete tmp;
4047         }
4048         InsetUpdateList = 0;
4049 }
4050
4051
4052 #ifdef WITH_WARNINGS
4053 #warning UGLY!!
4054 #endif
4055 // I know we shouldn't put anything in here but this seems the fastest
4056 // way to do this (and the cleanest for now). This function just inserts
4057 // a newline in the string and the inserts 'depth'-spaces so that the
4058 // code is indented in the right way!!!
4059 void addNewlineAndDepth(string & file, int const depth)
4060 {
4061        file += '\n';
4062        file.append(depth, ' ');
4063 }