]> git.lyx.org Git - lyx.git/blob - src/lyxlayout.C
fix bug 2089: Touching Navigate menu crashes Lyx when a TOC inset is in a section...
[lyx.git] / src / lyxlayout.C
1 /**
2  * \file lyxlayout.C
3  * This file is part of LyX, the document processor.
4  * Licence details can be found in the file COPYING.
5  *
6  * \author Lars Gullik Bjønnes
7  * \author Jean-Marc Lasgouttes
8  * \author André Pönitz
9  *
10  * Full author contact details are available in file CREDITS.
11  */
12
13 #include <config.h>
14
15 #include "lyxlayout.h"
16 #include "lyxtextclass.h"
17 #include "lyxlex.h"
18 #include "debug.h"
19
20 #include "support/lstrings.h"
21
22 using lyx::support::subst;
23 using lyx::support::trim;
24
25 using std::endl;
26 using std::string;
27
28 /// Special value of toclevel for layouts that to not belong in a TOC
29 const int LyXLayout::NOT_IN_TOC = -1000;
30
31 //  The order of the LayoutTags enum is no more important. [asierra300396]
32 // Tags indexes.
33 enum LayoutTags {
34         LT_ALIGN = 1,
35         LT_ALIGNPOSSIBLE,
36         LT_MARGIN,
37         LT_BOTTOMSEP,
38         LT_COMMANDDEPTH,
39         LT_COPYSTYLE,
40         LT_DEPENDSON,
41         LT_OBSOLETEDBY,
42         //LT_EMPTY,
43         LT_END,
44         //LT_ENVIRONMENT_DEFAULT,
45         //LT_FANCYHDR,
46         LT_FILL_BOTTOM,
47         LT_FILL_TOP,
48         //LT_FIRST_COUNTER,
49         LT_FONT,
50         LT_FREE_SPACING,
51         LT_PASS_THRU,
52         //LT_HEADINGS,
53         LT_ITEMSEP,
54         LT_KEEPEMPTY,
55         LT_LABEL_BOTTOMSEP,
56         LT_LABELFONT,
57         LT_TEXTFONT,
58         LT_LABELINDENT,
59         LT_LABELSEP,
60         LT_LABELSTRING,
61         LT_LABELSTRING_APPENDIX,
62         LT_LABELCOUNTER,
63         LT_LABELTYPE,
64         LT_ENDLABELSTRING,
65         LT_ENDLABELTYPE,
66         LT_LATEXNAME,
67         LT_LATEXPARAM,
68         LT_OPTARGS,
69         LT_LATEXTYPE,
70         LT_LATEXHEADER,
71         LT_LATEXFOOTER,
72         LT_LATEXPARAGRAPH,
73         LT_LEFTMARGIN,
74         LT_NEED_PROTECT,
75         LT_NEWLINE,
76         LT_NEXTNOINDENT,
77         LT_PARINDENT,
78         LT_PARSEP,
79         LT_PARSKIP,
80         //LT_PLAIN,
81         LT_PREAMBLE,
82         LT_RIGHTMARGIN,
83         LT_SPACING,
84         LT_TOPSEP,
85         LT_TOCLEVEL,
86         LT_INNERTAG,
87         LT_LABELTAG,
88         LT_ITEMTAG,
89         LT_INTITLE // keep this last!
90 };
91
92 /////////////////////
93
94 // Constructor for layout
95 LyXLayout::LyXLayout ()
96 {
97         margintype = MARGIN_STATIC;
98         latextype = LATEX_PARAGRAPH;
99         intitle = false;
100         optionalargs = 0;
101         needprotect = false;
102         keepempty = false;
103         font = LyXFont(LyXFont::ALL_INHERIT);
104         labelfont = LyXFont(LyXFont::ALL_INHERIT);
105         resfont = LyXFont(LyXFont::ALL_SANE);
106         reslabelfont = LyXFont(LyXFont::ALL_SANE);
107         nextnoindent = false;
108         parskip = 0.0;
109         itemsep = 0;
110         topsep = 0.0;
111         bottomsep = 0.0;
112         labelbottomsep = 0.0;
113         parsep = 0;
114         align = LYX_ALIGN_BLOCK;
115         alignpossible = LYX_ALIGN_BLOCK;
116         labeltype = LABEL_NO_LABEL;
117         endlabeltype = END_LABEL_NO_LABEL;
118         // Should or should not. That is the question.
119         // spacing.set(Spacing::OneHalf);
120         fill_top = false;
121         fill_bottom = false;
122         newline_allowed = true;
123         free_spacing = false;
124         pass_thru = false;
125         is_environment = false;
126         toclevel = NOT_IN_TOC;
127         commanddepth = 0;
128 }
129
130
131 // Reads a layout definition from file
132 bool LyXLayout::Read(LyXLex & lexrc, LyXTextClass const & tclass)
133 {
134         // This table is sorted alphabetically [asierra 30March96]
135         keyword_item layoutTags[] = {
136                 { "align",          LT_ALIGN },
137                 { "alignpossible",  LT_ALIGNPOSSIBLE },
138                 { "bottomsep",      LT_BOTTOMSEP },
139                 { "commanddepth",   LT_COMMANDDEPTH },
140                 { "copystyle",      LT_COPYSTYLE },
141                 { "dependson",      LT_DEPENDSON },
142                 { "end",            LT_END },
143                 { "endlabelstring", LT_ENDLABELSTRING },
144                 { "endlabeltype",   LT_ENDLABELTYPE },
145                 { "fill_bottom",    LT_FILL_BOTTOM },
146                 { "fill_top",       LT_FILL_TOP },
147                 { "font",           LT_FONT },
148                 { "freespacing",    LT_FREE_SPACING },
149                 { "innertag",       LT_INNERTAG },
150                 { "intitle",        LT_INTITLE },
151                 { "itemsep",        LT_ITEMSEP },
152                 { "itemtag",        LT_ITEMTAG },
153                 { "keepempty",      LT_KEEPEMPTY },
154                 { "labelbottomsep", LT_LABEL_BOTTOMSEP },
155                 { "labelcounter",   LT_LABELCOUNTER },
156                 { "labelfont",      LT_LABELFONT },
157                 { "labelindent",    LT_LABELINDENT },
158                 { "labelsep",       LT_LABELSEP },
159                 { "labelstring",    LT_LABELSTRING },
160                 { "labelstringappendix", LT_LABELSTRING_APPENDIX },
161                 { "labeltag",       LT_LABELTAG },
162                 { "labeltype",      LT_LABELTYPE },
163                 { "latexfooter",    LT_LATEXFOOTER },
164                 { "latexheader",    LT_LATEXHEADER },
165                 { "latexname",      LT_LATEXNAME },
166                 { "latexparagraph", LT_LATEXPARAGRAPH },
167                 { "latexparam",     LT_LATEXPARAM },
168                 { "latextype",      LT_LATEXTYPE },
169                 { "leftmargin",     LT_LEFTMARGIN },
170                 { "margin",         LT_MARGIN },
171                 { "needprotect",    LT_NEED_PROTECT },
172                 { "newline",        LT_NEWLINE },
173                 { "nextnoindent",   LT_NEXTNOINDENT },
174                 { "obsoletedby",    LT_OBSOLETEDBY },
175                 { "optionalargs",   LT_OPTARGS },
176                 { "parindent",      LT_PARINDENT },
177                 { "parsep",         LT_PARSEP },
178                 { "parskip",        LT_PARSKIP },
179                 { "passthru",       LT_PASS_THRU },
180                 { "preamble",       LT_PREAMBLE },
181                 { "rightmargin",    LT_RIGHTMARGIN },
182                 { "spacing",        LT_SPACING },
183                 { "textfont",       LT_TEXTFONT },
184                 { "toclevel",       LT_TOCLEVEL },
185                 { "topsep",         LT_TOPSEP }
186         };
187
188         bool error = false;
189         bool finished = false;
190         lexrc.pushTable(layoutTags, LT_INTITLE);
191         // parse style section
192         while (!finished && lexrc.isOK() && !error) {
193                 int le = lexrc.lex();
194                 // See comment in lyxrc.C.
195                 switch (le) {
196                 case LyXLex::LEX_FEOF:
197                         continue;
198
199                 case LyXLex::LEX_UNDEF:         // parse error
200                         lexrc.printError("Unknown layout tag `$$Token'");
201                         error = true;
202                         continue;
203                 default: break;
204                 }
205                 switch (static_cast<LayoutTags>(le)) {
206                 case LT_END:            // end of structure
207                         finished = true;
208                         break;
209
210                 case LT_COPYSTYLE:     // initialize with a known style
211                         if (lexrc.next()) {
212                                 string const style = subst(lexrc.getString(),
213                                                                 '_', ' ');
214
215                                 if (tclass.hasLayout(style)) {
216                                         string const tmpname = name_;
217                                         this->operator=(*tclass[style]);
218                                         name_ = tmpname;
219                                 } else {
220                                         lyxerr << "Cannot copy unknown style `"
221                                                << style << "'\n"
222                                                << "All layouts so far:"
223                                                << endl;
224                                         LyXTextClass::const_iterator it =
225                                                 tclass.begin();
226                                         LyXTextClass::const_iterator end =
227                                                 tclass.end();
228                                         for (; it != end; ++it) {
229                                                 lyxerr << (*it)->name()
230                                                        << endl;
231                                         }
232
233                                         //lexrc.printError("Cannot copy known "
234                                         //               "style `$$Token'");
235                                 }
236                         }
237                         break;
238
239                 case LT_OBSOLETEDBY:     // replace with a known style
240                         if (lexrc.next()) {
241                                 string const style = lexrc.getString();
242
243                                 if (tclass.hasLayout(style)) {
244                                         string const tmpname = name_;
245                                         this->operator=(*tclass[style]);
246                                         name_ = tmpname;
247                                         if (obsoleted_by().empty())
248                                                 obsoleted_by_ = style;
249                                 } else {
250                                         lyxerr << "Cannot replace with unknown style `" << style << '\'' << endl;
251
252                                         //lexrc.printError("Cannot replace with"
253                                         //               " unknown style "
254                                         //               "`$$Token'");
255                                 }
256                         }
257                         break;
258
259                 case LT_DEPENDSON:
260                         if (lexrc.next())
261                                 depends_on_ = lexrc.getString();
262                         break;
263
264                 case LT_MARGIN:         // margin style definition.
265                         readMargin(lexrc);
266                         break;
267
268                 case LT_LATEXTYPE:      // LaTeX style definition.
269                         readLatexType(lexrc);
270                         break;
271
272                 case LT_LATEXHEADER:    // header for environments
273                         lexrc.next();
274                         latexheader = lexrc.getString();
275                         break;
276
277                 case LT_LATEXFOOTER:    // footer for environments
278                         lexrc.next();
279                         latexfooter = lexrc.getString();
280                         break;
281
282                 case LT_LATEXPARAGRAPH:
283                         lexrc.next();
284                         latexparagraph = lexrc.getString();
285                         break;
286
287                 case LT_INTITLE:
288                         intitle = lexrc.next() && lexrc.getInteger();
289                         break;
290
291                 case LT_TOCLEVEL:
292                         lexrc.next();
293                         toclevel = lexrc.getInteger();
294                         break;
295
296                 case LT_OPTARGS:
297                         if (lexrc.next())
298                                 optionalargs = lexrc.getInteger();
299                         break;
300
301                 case LT_NEED_PROTECT:
302                         needprotect = lexrc.next() && lexrc.getInteger();
303                         break;
304
305                 case LT_KEEPEMPTY:
306                         keepempty = lexrc.next() && lexrc.getInteger();
307                         break;
308
309                 case LT_FONT:
310                         font.lyxRead(lexrc);
311                         labelfont= font;
312                         break;
313
314                 case LT_TEXTFONT:
315                         font.lyxRead(lexrc);
316                         break;
317
318                 case LT_LABELFONT:
319                         labelfont.lyxRead(lexrc);
320                         break;
321
322                 case LT_NEXTNOINDENT:   // Indent next paragraph?
323                         if (lexrc.next() && lexrc.getInteger())
324                                 nextnoindent = true;
325                         else
326                                 nextnoindent = false;
327                         break;
328
329                 case LT_COMMANDDEPTH:
330                         lexrc.next();
331                         commanddepth = lexrc.getInteger();
332                         break;
333
334                 case LT_LATEXNAME:
335                         if (lexrc.next())
336                                 latexname_ = lexrc.getString();
337                         break;
338
339                 case LT_LATEXPARAM:
340                         if (lexrc.next())
341                                 latexparam_ = subst(lexrc.getString(), "&quot;", "\"");
342                         break;
343
344                 case LT_INNERTAG:
345                         if (lexrc.next())
346                                 innertag_ = lexrc.getString();
347                         break;
348
349                 case LT_LABELTAG:
350                         if (lexrc.next())
351                                 labeltag_ = lexrc.getString();
352                         break;
353
354                 case LT_ITEMTAG:
355                         if (lexrc.next())
356                                 itemtag_ = lexrc.getString();
357                         break;
358
359                 case LT_PREAMBLE:
360                         preamble_ = lexrc.getLongString("EndPreamble");
361                         break;
362
363                 case LT_LABELTYPE:
364                         readLabelType(lexrc);
365                         break;
366
367                 case LT_ENDLABELTYPE:
368                         readEndLabelType(lexrc);
369                         break;
370
371                 case LT_LEFTMARGIN:     // left margin type
372                         if (lexrc.next())
373                                 leftmargin = lexrc.getString();
374                         break;
375
376                 case LT_RIGHTMARGIN:    // right margin type
377                         if (lexrc.next())
378                                 rightmargin = lexrc.getString();
379                         break;
380
381                 case LT_LABELINDENT:    // label indenting flag
382                         if (lexrc.next())
383                                 labelindent = lexrc.getString();
384                         break;
385
386                 case LT_PARINDENT:      // paragraph indent. flag
387                         if (lexrc.next())
388                                 parindent = lexrc.getString();
389                         break;
390
391                 case LT_PARSKIP:        // paragraph skip size
392                         if (lexrc.next())
393                                 parskip = lexrc.getFloat();
394                         break;
395
396                 case LT_ITEMSEP:        // item separation size
397                         if (lexrc.next())
398                                 itemsep = lexrc.getFloat();
399                         break;
400
401                 case LT_TOPSEP:         // top separation size
402                         if (lexrc.next())
403                                 topsep = lexrc.getFloat();
404                         break;
405
406                 case LT_BOTTOMSEP:      // bottom separation size
407                         if (lexrc.next())
408                                 bottomsep = lexrc.getFloat();
409                         break;
410
411                 case LT_LABEL_BOTTOMSEP: // label bottom separation size
412                         if (lexrc.next())
413                                 labelbottomsep = lexrc.getFloat();
414                         break;
415
416                 case LT_LABELSEP:       // label separator
417                         if (lexrc.next()) {
418                                 labelsep = subst(lexrc.getString(), 'x', ' ');
419                         }
420                         break;
421
422                 case LT_PARSEP:         // par. separation size
423                         if (lexrc.next())
424                                 parsep = lexrc.getFloat();
425                         break;
426
427                 case LT_FILL_TOP:       // fill top flag
428                         if (lexrc.next())
429                                 fill_top = lexrc.getInteger();
430                         break;
431
432                 case LT_FILL_BOTTOM:    // fill bottom flag
433                         if (lexrc.next())
434                                 fill_bottom = lexrc.getInteger();
435                         break;
436
437                 case LT_NEWLINE:        // newlines allowed?
438                         if (lexrc.next())
439                                 newline_allowed = lexrc.getInteger();
440                         break;
441
442                 case LT_ALIGN:          // paragraph align
443                         readAlign(lexrc);
444                         break;
445                 case LT_ALIGNPOSSIBLE:  // paragraph allowed align
446                         readAlignPossible(lexrc);
447                         break;
448
449                 case LT_LABELSTRING:    // label string definition
450                         if (lexrc.next())
451                                 labelstring_ = trim(lexrc.getString());
452                         break;
453
454                 case LT_ENDLABELSTRING: // endlabel string definition
455                         if (lexrc.next())
456                                 endlabelstring_ = trim(lexrc.getString());
457                         break;
458
459                 case LT_LABELSTRING_APPENDIX: // label string appendix definition
460                         if (lexrc.next())
461                                 labelstring_appendix_ = trim(lexrc.getString());
462                         break;
463
464                 case LT_LABELCOUNTER: // name of counter to use
465                         if (lexrc.next())
466                                 counter = trim(lexrc.getString());
467                         break;
468
469                 case LT_FREE_SPACING:   // Allow for free spacing.
470                         if (lexrc.next())
471                                 free_spacing = lexrc.getInteger();
472                         break;
473
474                 case LT_PASS_THRU:      // Allow for pass thru.
475                         if (lexrc.next())
476                                 pass_thru = lexrc.getInteger();
477                         break;
478
479                 case LT_SPACING: // setspace.sty
480                         readSpacing(lexrc);
481                         break;
482                 }
483         }
484         lexrc.popTable();
485
486         if (labelstring_appendix_.empty())
487                 labelstring_appendix_ = labelstring_;
488         return error;
489 }
490
491
492 enum AlignTags {
493         AT_BLOCK = 1,
494         AT_LEFT,
495         AT_RIGHT,
496         AT_CENTER,
497         AT_LAYOUT
498 };
499
500
501 void LyXLayout::readAlign(LyXLex & lexrc)
502 {
503         keyword_item alignTags[] = {
504                 { "block",  AT_BLOCK },
505                 { "center", AT_CENTER },
506                 { "layout", AT_LAYOUT },
507                 { "left",   AT_LEFT },
508                 { "right",  AT_RIGHT }
509         };
510
511         pushpophelper pph(lexrc, alignTags, AT_LAYOUT);
512         int le = lexrc.lex();
513         switch (le) {
514         case LyXLex::LEX_UNDEF:
515                 lexrc.printError("Unknown alignment `$$Token'");
516                 return;
517         default: break;
518         };
519         switch (static_cast<AlignTags>(le)) {
520         case AT_BLOCK:
521                 align = LYX_ALIGN_BLOCK;
522                 break;
523         case AT_LEFT:
524                 align = LYX_ALIGN_LEFT;
525                 break;
526         case AT_RIGHT:
527                 align = LYX_ALIGN_RIGHT;
528                 break;
529         case AT_CENTER:
530                 align = LYX_ALIGN_CENTER;
531                 break;
532         case AT_LAYOUT:
533                 align = LYX_ALIGN_LAYOUT;
534                 break;
535         }
536 }
537
538
539 void LyXLayout::readAlignPossible(LyXLex & lexrc)
540 {
541         keyword_item alignTags[] = {
542                 { "block",  AT_BLOCK },
543                 { "center", AT_CENTER },
544                 { "layout", AT_LAYOUT },
545                 { "left",   AT_LEFT },
546                 { "right",  AT_RIGHT }
547         };
548
549         lexrc.pushTable(alignTags, AT_LAYOUT);
550         alignpossible = LYX_ALIGN_NONE;
551         int lineno = lexrc.getLineNo();
552         do {
553                 int le = lexrc.lex();
554                 switch (le) {
555                 case LyXLex::LEX_UNDEF:
556                         lexrc.printError("Unknown alignment `$$Token'");
557                         continue;
558                 default: break;
559                 };
560                 switch (static_cast<AlignTags>(le)) {
561                 case AT_BLOCK:
562                         alignpossible |= LYX_ALIGN_BLOCK;
563                         break;
564                 case AT_LEFT:
565                         alignpossible |= LYX_ALIGN_LEFT;
566                         break;
567                 case AT_RIGHT:
568                         alignpossible |= LYX_ALIGN_RIGHT;
569                         break;
570                 case AT_CENTER:
571                         alignpossible |= LYX_ALIGN_CENTER;
572                         break;
573                 case AT_LAYOUT:
574                         alignpossible |= LYX_ALIGN_LAYOUT;
575                         break;
576                 }
577         } while (lineno == lexrc.getLineNo());
578         lexrc.popTable();
579 }
580
581
582 enum LabelTypeTags {
583         LA_NO_LABEL = 1,
584         LA_MANUAL,
585         LA_TOP_ENVIRONMENT,
586         LA_CENTERED_TOP_ENVIRONMENT,
587         LA_STATIC,
588         LA_SENSITIVE,
589         LA_COUNTER,
590         LA_ENUMERATE,
591         LA_ITEMIZE,
592         LA_BIBLIO
593 };
594
595
596 void LyXLayout::readLabelType(LyXLex & lexrc)
597 {
598         keyword_item labelTypeTags[] = {
599         { "bibliography",             LA_BIBLIO },
600         { "centered_top_environment", LA_CENTERED_TOP_ENVIRONMENT },
601         { "counter",                  LA_COUNTER },
602         { "enumerate",                LA_ENUMERATE },
603         { "itemize",                  LA_ITEMIZE },
604         { "manual",                   LA_MANUAL },
605         { "no_label",                 LA_NO_LABEL },
606         { "sensitive",                LA_SENSITIVE },
607         { "static",                   LA_STATIC },
608         { "top_environment",          LA_TOP_ENVIRONMENT }
609         };
610
611         pushpophelper pph(lexrc, labelTypeTags, LA_BIBLIO);
612         int le = lexrc.lex();
613         switch (le) {
614         case LyXLex::LEX_UNDEF:
615                 lexrc.printError("Unknown labeltype tag `$$Token'");
616                 return;
617         default: break;
618         }
619         switch (static_cast<LabelTypeTags>(le)) {
620         case LA_NO_LABEL:
621                 labeltype = LABEL_NO_LABEL;
622                 break;
623         case LA_MANUAL:
624                 labeltype = LABEL_MANUAL;
625                 break;
626         case LA_TOP_ENVIRONMENT:
627                 labeltype = LABEL_TOP_ENVIRONMENT;
628                 break;
629         case LA_CENTERED_TOP_ENVIRONMENT:
630                 labeltype = LABEL_CENTERED_TOP_ENVIRONMENT;
631                 break;
632         case LA_STATIC:
633                 labeltype = LABEL_STATIC;
634                 break;
635         case LA_SENSITIVE:
636                 labeltype = LABEL_SENSITIVE;
637                 break;
638         case LA_COUNTER:
639                 labeltype = LABEL_COUNTER;
640                 break;
641         case LA_ENUMERATE:
642                 labeltype = LABEL_ENUMERATE;
643                 break;
644         case LA_ITEMIZE:
645                 labeltype = LABEL_ITEMIZE;
646                 break;
647         case LA_BIBLIO:
648                 labeltype = LABEL_BIBLIO;
649                 break;
650         }
651 }
652
653
654 namespace {
655
656 keyword_item endlabelTypeTags[] = {
657         { "box",        END_LABEL_BOX },
658         { "filled_box", END_LABEL_FILLED_BOX },
659         { "no_label",   END_LABEL_NO_LABEL },
660         { "static",     END_LABEL_STATIC }
661 };
662
663 } // namespace anon
664
665
666 void LyXLayout::readEndLabelType(LyXLex & lexrc)
667 {
668         pushpophelper pph(lexrc, endlabelTypeTags,
669                           END_LABEL_ENUM_LAST-END_LABEL_ENUM_FIRST+1);
670         int le = lexrc.lex();
671         switch (le) {
672         case LyXLex::LEX_UNDEF:
673                 lexrc.printError("Unknown labeltype tag `$$Token'");
674                 break;
675         case END_LABEL_STATIC:
676         case END_LABEL_BOX:
677         case END_LABEL_FILLED_BOX:
678         case END_LABEL_NO_LABEL:
679                 endlabeltype = static_cast<LYX_END_LABEL_TYPES>(le);
680                 break;
681         default:
682                 lyxerr << "Unhandled value " << le
683                        << " in LyXLayout::readEndLabelType." << endl;
684                 break;
685         }
686 }
687
688
689 void LyXLayout::readMargin(LyXLex & lexrc)
690 {
691         keyword_item marginTags[] = {
692                 { "dynamic",           MARGIN_DYNAMIC },
693                 { "first_dynamic",     MARGIN_FIRST_DYNAMIC },
694                 { "manual",            MARGIN_MANUAL },
695                 { "right_address_box", MARGIN_RIGHT_ADDRESS_BOX },
696                 { "static",            MARGIN_STATIC }
697         };
698
699         pushpophelper pph(lexrc, marginTags, MARGIN_RIGHT_ADDRESS_BOX);
700
701         int le = lexrc.lex();
702         switch (le) {
703         case LyXLex::LEX_UNDEF:
704                 lexrc.printError("Unknown margin type tag `$$Token'");
705                 return;
706         case MARGIN_STATIC:
707         case MARGIN_MANUAL:
708         case MARGIN_DYNAMIC:
709         case MARGIN_FIRST_DYNAMIC:
710         case MARGIN_RIGHT_ADDRESS_BOX:
711                 margintype = static_cast<LYX_MARGIN_TYPE>(le);
712                 break;
713         default:
714                 lyxerr << "Unhandled value " << le
715                        << " in LyXLayout::readMargin." << endl;
716                 break;
717         }
718 }
719
720
721 void LyXLayout::readLatexType(LyXLex & lexrc)
722 {
723         keyword_item latexTypeTags[] = {
724                 { "bib_environment",  LATEX_BIB_ENVIRONMENT },
725                 { "command",          LATEX_COMMAND },
726                 { "environment",      LATEX_ENVIRONMENT },
727                 { "item_environment", LATEX_ITEM_ENVIRONMENT },
728                 { "list_environment", LATEX_LIST_ENVIRONMENT },
729                 { "paragraph",        LATEX_PARAGRAPH }
730         };
731
732         pushpophelper pph(lexrc, latexTypeTags, LATEX_LIST_ENVIRONMENT);
733         int le = lexrc.lex();
734         switch (le) {
735         case LyXLex::LEX_UNDEF:
736                 lexrc.printError("Unknown latextype tag `$$Token'");
737                 return;
738         case LATEX_PARAGRAPH:
739         case LATEX_COMMAND:
740         case LATEX_ENVIRONMENT:
741         case LATEX_ITEM_ENVIRONMENT:
742         case LATEX_BIB_ENVIRONMENT:
743         case LATEX_LIST_ENVIRONMENT:
744                 latextype = static_cast<LYX_LATEX_TYPES>(le);
745                 break;
746         default:
747                 lyxerr << "Unhandled value " << le
748                        << " in LyXLayout::readLatexType." << endl;
749                 break;
750         }
751 }
752
753
754 enum SpacingTags {
755         ST_SPACING_SINGLE = 1,
756         ST_SPACING_ONEHALF,
757         ST_SPACING_DOUBLE,
758         ST_OTHER
759 };
760
761
762 void LyXLayout::readSpacing(LyXLex & lexrc)
763 {
764         keyword_item spacingTags[] = {
765                 {"double",  ST_SPACING_DOUBLE },
766                 {"onehalf", ST_SPACING_ONEHALF },
767                 {"other",   ST_OTHER },
768                 {"single",  ST_SPACING_SINGLE }
769         };
770
771         pushpophelper pph(lexrc, spacingTags, ST_OTHER);
772         int le = lexrc.lex();
773         switch (le) {
774         case LyXLex::LEX_UNDEF:
775                 lexrc.printError("Unknown spacing token `$$Token'");
776                 return;
777         default: break;
778         }
779         switch (static_cast<SpacingTags>(le)) {
780         case ST_SPACING_SINGLE:
781                 spacing.set(Spacing::Single);
782                 break;
783         case ST_SPACING_ONEHALF:
784                 spacing.set(Spacing::Onehalf);
785                 break;
786         case ST_SPACING_DOUBLE:
787                 spacing.set(Spacing::Double);
788                 break;
789         case ST_OTHER:
790                 lexrc.next();
791                 spacing.set(Spacing::Other, lexrc.getString());
792                 break;
793         }
794 }
795
796
797 string const & LyXLayout::name() const
798 {
799         return name_;
800 }
801
802
803 void LyXLayout::setName(string const & n)
804 {
805         name_ = n;
806 }
807
808
809 string const & LyXLayout::obsoleted_by() const
810 {
811         return obsoleted_by_;
812 }
813
814
815 string const & LyXLayout::depends_on() const
816 {
817         return depends_on_;
818 }