2 * \file GuiDocument.cpp
3 * This file is part of LyX, the document processor.
4 * Licence details can be found in the file COPYING.
7 * \author Richard Heck (modules)
9 * Full author contact details are available in file CREDITS.
14 #include "GuiDocument.h"
16 #include "GuiApplication.h"
17 #include "GuiBranches.h"
18 #include "GuiSelectionManager.h"
19 #include "LaTeXHighlighter.h"
20 #include "LengthCombo.h"
21 #include "PanelStack.h"
22 #include "Validator.h"
24 #include "LayoutFile.h"
25 #include "BranchList.h"
26 #include "buffer_funcs.h"
28 #include "BufferParams.h"
29 #include "BufferView.h"
32 #include "FloatPlacement.h"
33 #include "FuncRequest.h"
35 #include "LaTeXFeatures.h"
37 #include "LyXRC.h" // defaultUnit
38 #include "ModuleList.h"
39 #include "OutputParams.h"
40 #include "PDFOptions.h"
41 #include "qt_helpers.h"
44 #include "insets/InsetListingsParams.h"
46 #include "support/debug.h"
47 #include "support/FileName.h"
48 #include "support/filetools.h"
49 #include "support/gettext.h"
50 #include "support/lstrings.h"
52 #include "frontends/alert.h"
54 #include <QAbstractItemModel>
55 #include <QCloseEvent>
57 #include <QTextCursor>
68 using namespace lyx::support;
73 char const * const tex_graphics[] =
75 "default", "dvialw", "dvilaser", "dvipdf", "dvipdfm", "dvipdfmx",
76 "dvips", "dvipsone", "dvitops", "dviwin", "dviwindo", "dvi2ps", "emtex",
77 "ln", "oztex", "pctexhp", "pctexps", "pctexwin", "pctex32", "pdftex",
78 "psprint", "pubps", "tcidvi", "textures", "truetex", "vtex", "xdvi",
83 char const * const tex_graphics_gui[] =
85 N_("Default"), "dvialw", "DviLaser", "dvipdf", "DVIPDFM", "DVIPDFMx",
86 "Dvips", "DVIPSONE", "DVItoPS", "DVIWIN", "DVIWindo", "dvi2ps", "EmTeX",
87 "LN", "OzTeX", "pctexhp", "pctexps", "pctexwin", "PCTeX32", "pdfTeX",
88 "psprint", "pubps", "tcidvi", "Textures", "TrueTeX", "VTeX", "xdvi",
89 "XeTeX", N_("None"), ""
93 char const * const tex_fonts_roman[] =
95 "default", "cmr", "lmodern", "ae", "times", "palatino",
96 "charter", "newcent", "bookman", "utopia", "beraserif",
97 "ccfonts", "chancery", ""
101 char const * tex_fonts_roman_gui[] =
103 N_("Default"), N_("Computer Modern Roman"), N_("Latin Modern Roman"),
104 N_("AE (Almost European)"), N_("Times Roman"), N_("Palatino"),
105 N_("Bitstream Charter"), N_("New Century Schoolbook"), N_("Bookman"),
106 N_("Utopia"), N_("Bera Serif"), N_("Concrete Roman"), N_("Zapf Chancery"),
111 char const * const tex_fonts_sans[] =
113 "default", "cmss", "lmss", "helvet", "avant", "berasans", "cmbr", ""
117 char const * tex_fonts_sans_gui[] =
119 N_("Default"), N_("Computer Modern Sans"), N_("Latin Modern Sans"),
120 N_("Helvetica"), N_("Avant Garde"), N_("Bera Sans"), N_("CM Bright"), ""
124 char const * const tex_fonts_monospaced[] =
126 "default", "cmtt", "lmtt", "courier", "beramono", "luximono", "cmtl", ""
130 char const * tex_fonts_monospaced_gui[] =
132 N_("Default"), N_("Computer Modern Typewriter"),
133 N_("Latin Modern Typewriter"), N_("Courier"), N_("Bera Mono"),
134 N_("LuxiMono"), N_("CM Typewriter Light"), ""
138 char const * backref_opts[] =
140 "false", "section", "slide", "page", ""
144 char const * backref_opts_gui[] =
146 N_("Off"), N_("Section"), N_("Slide"), N_("Page"), ""
150 vector<pair<string, QString> > pagestyles;
153 } // anonymous namespace
158 // used when sorting the textclass list.
159 class less_textclass_avail_desc
160 : public binary_function<string, string, int>
163 bool operator()(string const & lhs, string const & rhs) const
165 // Ordering criteria:
166 // 1. Availability of text class
167 // 2. Description (lexicographic)
168 LayoutFile const & tc1 = LayoutFileList::get()[lhs];
169 LayoutFile const & tc2 = LayoutFileList::get()[rhs];
170 return (tc1.isTeXClassAvailable() && !tc2.isTeXClassAvailable()) ||
171 (tc1.isTeXClassAvailable() == tc2.isTeXClassAvailable() &&
172 _(tc1.description()) < _(tc2.description()));
181 vector<string> getRequiredList(string const & modName)
183 LyXModule const * const mod = moduleList[modName];
185 return vector<string>(); //empty such thing
186 return mod->getRequiredModules();
190 vector<string> getExcludedList(string const & modName)
192 LyXModule const * const mod = moduleList[modName];
194 return vector<string>(); //empty such thing
195 return mod->getExcludedModules();
199 docstring getModuleDescription(string const & modName)
201 LyXModule const * const mod = moduleList[modName];
203 return _("Module not found!");
204 return _(mod->getDescription());
208 vector<string> getPackageList(string const & modName)
210 LyXModule const * const mod = moduleList[modName];
212 return vector<string>(); //empty such thing
213 return mod->getPackageList();
217 bool isModuleAvailable(string const & modName)
219 LyXModule * mod = moduleList[modName];
222 return mod->isAvailable();
225 } // anonymous namespace
228 /////////////////////////////////////////////////////////////////////
230 // ModuleSelectionManager
232 /////////////////////////////////////////////////////////////////////
234 /// SelectionManager for use with modules
235 class ModuleSelectionManager : public GuiSelectionManager
239 ModuleSelectionManager(
240 QListView * availableLV,
241 QListView * selectedLV,
245 QPushButton * downPB,
246 GuiIdListModel * availableModel,
247 GuiIdListModel * selectedModel,
248 GuiDocument const * container)
249 : GuiSelectionManager(availableLV, selectedLV, addPB, delPB,
250 upPB, downPB, availableModel, selectedModel), container_(container)
254 virtual void updateAddPB();
256 virtual void updateUpPB();
258 virtual void updateDownPB();
260 virtual void updateDelPB();
261 /// returns availableModel as a GuiIdListModel
262 GuiIdListModel * getAvailableModel()
264 return dynamic_cast<GuiIdListModel *>(availableModel);
266 /// returns selectedModel as a GuiIdListModel
267 GuiIdListModel * getSelectedModel()
269 return dynamic_cast<GuiIdListModel *>(selectedModel);
272 GuiDocument const * container_;
275 void ModuleSelectionManager::updateAddPB()
277 int const arows = availableModel->rowCount();
278 QModelIndexList const availSels =
279 availableLV->selectionModel()->selectedIndexes();
281 // disable if there aren't any modules (?), if none of them is chosen
282 // in the dialog, or if the chosen one is already selected for use.
283 if (arows == 0 || availSels.isEmpty() || isSelected(availSels.first())) {
284 addPB->setEnabled(false);
288 QModelIndex const & idx = availableLV->selectionModel()->currentIndex();
289 string const modName = getAvailableModel()->getIDString(idx.row());
292 container_->params().moduleCanBeAdded(modName);
293 addPB->setEnabled(enable);
297 void ModuleSelectionManager::updateDownPB()
299 int const srows = selectedModel->rowCount();
301 downPB->setEnabled(false);
304 QModelIndex const & curIdx = selectedLV->selectionModel()->currentIndex();
305 int const curRow = curIdx.row();
306 if (curRow < 0 || curRow >= srows - 1) { // invalid or last item
307 downPB->setEnabled(false);
311 // determine whether immediately succeding element requires this one
312 string const curModName = getSelectedModel()->getIDString(curRow);
313 string const nextModName = getSelectedModel()->getIDString(curRow + 1);
315 vector<string> reqs = getRequiredList(nextModName);
317 // if it doesn't require anything....
319 downPB->setEnabled(true);
323 // Enable it if this module isn't required.
324 // FIXME This should perhaps be more flexible and check whether, even
325 // if the next one is required, there is also an earlier one that will do.
327 find(reqs.begin(), reqs.end(), curModName) == reqs.end());
330 void ModuleSelectionManager::updateUpPB()
332 int const srows = selectedModel->rowCount();
334 upPB->setEnabled(false);
338 QModelIndex const & curIdx = selectedLV->selectionModel()->currentIndex();
339 int curRow = curIdx.row();
340 if (curRow <= 0 || curRow > srows - 1) { // first item or invalid
341 upPB->setEnabled(false);
344 string const curModName = getSelectedModel()->getIDString(curRow);
346 // determine whether immediately preceding element is required by this one
347 vector<string> reqs = getRequiredList(curModName);
349 // if this one doesn't require anything....
351 upPB->setEnabled(true);
356 // Enable it if the preceding module isn't required.
357 // NOTE This is less flexible than it might be. We could check whether, even
358 // if the previous one is required, there is an earlier one that would do.
359 string const preModName = getSelectedModel()->getIDString(curRow - 1);
360 upPB->setEnabled(find(reqs.begin(), reqs.end(), preModName) == reqs.end());
363 void ModuleSelectionManager::updateDelPB()
365 int const srows = selectedModel->rowCount();
367 deletePB->setEnabled(false);
371 QModelIndex const & curIdx =
372 selectedLV->selectionModel()->currentIndex();
373 int const curRow = curIdx.row();
374 if (curRow < 0 || curRow >= srows) { // invalid index?
375 deletePB->setEnabled(false);
379 string const curModName = getSelectedModel()->getIDString(curRow);
381 // We're looking here for a reason NOT to enable the button. If we
382 // find one, we disable it and return. If we don't, we'll end up at
383 // the end of the function, and then we enable it.
384 for (int i = curRow + 1; i < srows; ++i) {
385 string const thisMod = getSelectedModel()->getIDString(i);
386 vector<string> reqs = getRequiredList(thisMod);
387 //does this one require us?
388 if (find(reqs.begin(), reqs.end(), curModName) == reqs.end())
392 // OK, so this module requires us
393 // is there an EARLIER module that also satisfies the require?
394 // NOTE We demand that it be earlier to keep the list of modules
395 // consistent with the rule that a module must be proceeded by a
396 // required module. There would be more flexible ways to proceed,
397 // but that would be a lot more complicated, and the logic here is
398 // already complicated. (That's why I've left the debugging code.)
399 // lyxerr << "Testing " << thisMod << std::endl;
400 bool foundOne = false;
401 for (int j = 0; j < curRow; ++j) {
402 string const mod = getSelectedModel()->getIDString(j);
403 // lyxerr << "In loop: Testing " << mod << std::endl;
404 // do we satisfy the require?
405 if (find(reqs.begin(), reqs.end(), mod) != reqs.end()) {
406 // lyxerr << mod << " does the trick." << std::endl;
411 // did we find a module to satisfy the require?
413 // lyxerr << "No matching module found." << std::endl;
414 deletePB->setEnabled(false);
418 // lyxerr << "All's well that ends well." << std::endl;
419 deletePB->setEnabled(true);
423 /////////////////////////////////////////////////////////////////////
427 /////////////////////////////////////////////////////////////////////
429 PreambleModule::PreambleModule() : current_id_(0)
431 // This is not a memory leak. The object will be destroyed
433 (void) new LaTeXHighlighter(preambleTE->document());
434 setFocusProxy(preambleTE);
435 connect(preambleTE, SIGNAL(textChanged()), this, SIGNAL(changed()));
439 void PreambleModule::update(BufferParams const & params, BufferId id)
441 QString preamble = toqstr(params.preamble);
442 // Nothing to do if the params and preamble are unchanged.
443 if (id == current_id_
444 && preamble == preambleTE->document()->toPlainText())
447 QTextCursor cur = preambleTE->textCursor();
448 // Save the coords before switching to the new one.
449 preamble_coords_[current_id_] =
450 make_pair(cur.position(), preambleTE->verticalScrollBar()->value());
452 // Save the params address for further use.
454 preambleTE->document()->setPlainText(preamble);
455 Coords::const_iterator it = preamble_coords_.find(current_id_);
456 if (it == preamble_coords_.end())
457 // First time we open this one.
458 preamble_coords_[current_id_] = make_pair(0, 0);
460 // Restore saved coords.
461 QTextCursor cur = preambleTE->textCursor();
462 cur.setPosition(it->second.first);
463 preambleTE->setTextCursor(cur);
464 preambleTE->verticalScrollBar()->setValue(it->second.second);
469 void PreambleModule::apply(BufferParams & params)
471 params.preamble = fromqstr(preambleTE->document()->toPlainText());
475 void PreambleModule::closeEvent(QCloseEvent * e)
477 // Save the coords before closing.
478 QTextCursor cur = preambleTE->textCursor();
479 preamble_coords_[current_id_] =
480 make_pair(cur.position(), preambleTE->verticalScrollBar()->value());
485 /////////////////////////////////////////////////////////////////////
489 /////////////////////////////////////////////////////////////////////
492 GuiDocument::GuiDocument(GuiView & lv)
493 : GuiDialog(lv, "document", qt_("Document Settings"))
497 connect(okPB, SIGNAL(clicked()), this, SLOT(slotOK()));
498 connect(applyPB, SIGNAL(clicked()), this, SLOT(slotApply()));
499 connect(closePB, SIGNAL(clicked()), this, SLOT(slotClose()));
500 connect(restorePB, SIGNAL(clicked()), this, SLOT(slotRestore()));
502 connect(savePB, SIGNAL(clicked()), this, SLOT(saveDefaultClicked()));
503 connect(defaultPB, SIGNAL(clicked()), this, SLOT(useDefaultsClicked()));
505 // Manage the restore, ok, apply, restore and cancel/close buttons
506 bc().setPolicy(ButtonPolicy::NoRepeatedApplyReadOnlyPolicy);
508 bc().setApply(applyPB);
509 bc().setCancel(closePB);
510 bc().setRestore(restorePB);
512 textLayoutModule = new UiWidget<Ui::TextLayoutUi>;
514 connect(textLayoutModule->lspacingCO, SIGNAL(activated(int)),
515 this, SLOT(change_adaptor()));
516 connect(textLayoutModule->lspacingCO, SIGNAL(activated(int)),
517 this, SLOT(setLSpacing(int)));
518 connect(textLayoutModule->lspacingLE, SIGNAL(textChanged(const QString &)),
519 this, SLOT(change_adaptor()));
520 connect(textLayoutModule->skipRB, SIGNAL(clicked()),
521 this, SLOT(change_adaptor()));
522 connect(textLayoutModule->indentRB, SIGNAL(clicked()),
523 this, SLOT(change_adaptor()));
524 connect(textLayoutModule->skipCO, SIGNAL(activated(int)),
525 this, SLOT(change_adaptor()));
526 connect(textLayoutModule->skipLE, SIGNAL(textChanged(const QString &)),
527 this, SLOT(change_adaptor()));
528 connect(textLayoutModule->skipLengthCO, SIGNAL(activated(int)),
529 this, SLOT(change_adaptor()));
530 connect(textLayoutModule->skipCO, SIGNAL(activated(int)),
531 this, SLOT(setSkip(int)));
532 connect(textLayoutModule->skipRB, SIGNAL(toggled(bool)),
533 this, SLOT(enableSkip(bool)));
534 connect(textLayoutModule->twoColumnCB, SIGNAL(clicked()),
535 this, SLOT(change_adaptor()));
536 connect(textLayoutModule->twoColumnCB, SIGNAL(clicked()),
537 this, SLOT(setColSep()));
538 connect(textLayoutModule->listingsED, SIGNAL(textChanged()),
539 this, SLOT(change_adaptor()));
540 connect(textLayoutModule->bypassCB, SIGNAL(clicked()),
541 this, SLOT(change_adaptor()));
542 connect(textLayoutModule->bypassCB, SIGNAL(clicked()),
543 this, SLOT(setListingsMessage()));
544 connect(textLayoutModule->listingsED, SIGNAL(textChanged()),
545 this, SLOT(setListingsMessage()));
546 textLayoutModule->listingsTB->setPlainText(
547 qt_("Input listings parameters on the right. Enter ? for a list of parameters."));
548 textLayoutModule->lspacingLE->setValidator(new QDoubleValidator(
549 textLayoutModule->lspacingLE));
550 textLayoutModule->skipLE->setValidator(unsignedLengthValidator(
551 textLayoutModule->skipLE));
553 textLayoutModule->skipCO->addItem(qt_("SmallSkip"));
554 textLayoutModule->skipCO->addItem(qt_("MedSkip"));
555 textLayoutModule->skipCO->addItem(qt_("BigSkip"));
556 textLayoutModule->skipCO->addItem(qt_("Length"));
557 // remove the %-items from the unit choice
558 textLayoutModule->skipLengthCO->noPercents();
559 textLayoutModule->lspacingCO->insertItem(
560 Spacing::Single, qt_("Single"));
561 textLayoutModule->lspacingCO->insertItem(
562 Spacing::Onehalf, qt_("OneHalf"));
563 textLayoutModule->lspacingCO->insertItem(
564 Spacing::Double, qt_("Double"));
565 textLayoutModule->lspacingCO->insertItem(
566 Spacing::Other, qt_("Custom"));
568 // initialize the length validator
569 bc().addCheckedLineEdit(textLayoutModule->skipLE);
571 fontModule = new UiWidget<Ui::FontUi>;
573 connect(fontModule->fontsRomanCO, SIGNAL(activated(int)),
574 this, SLOT(change_adaptor()));
575 connect(fontModule->fontsRomanCO, SIGNAL(activated(int)),
576 this, SLOT(romanChanged(int)));
577 connect(fontModule->fontsSansCO, SIGNAL(activated(int)),
578 this, SLOT(change_adaptor()));
579 connect(fontModule->fontsSansCO, SIGNAL(activated(int)),
580 this, SLOT(sansChanged(int)));
581 connect(fontModule->fontsTypewriterCO, SIGNAL(activated(int)),
582 this, SLOT(change_adaptor()));
583 connect(fontModule->fontsTypewriterCO, SIGNAL(activated(int)),
584 this, SLOT(ttChanged(int)));
585 connect(fontModule->fontsDefaultCO, SIGNAL(activated(int)),
586 this, SLOT(change_adaptor()));
587 connect(fontModule->fontsizeCO, SIGNAL(activated(int)),
588 this, SLOT(change_adaptor()));
589 connect(fontModule->cjkFontLE, SIGNAL(textChanged(const QString &)),
590 this, SLOT(change_adaptor()));
591 connect(fontModule->scaleSansSB, SIGNAL(valueChanged(int)),
592 this, SLOT(change_adaptor()));
593 connect(fontModule->scaleTypewriterSB, SIGNAL(valueChanged(int)),
594 this, SLOT(change_adaptor()));
595 connect(fontModule->fontScCB, SIGNAL(clicked()),
596 this, SLOT(change_adaptor()));
597 connect(fontModule->fontOsfCB, SIGNAL(clicked()),
598 this, SLOT(change_adaptor()));
600 for (int n = 0; tex_fonts_roman[n][0]; ++n) {
601 QString font = qt_(tex_fonts_roman_gui[n]);
602 if (!isFontAvailable(tex_fonts_roman[n]))
603 font += qt_(" (not installed)");
604 fontModule->fontsRomanCO->addItem(font);
606 for (int n = 0; tex_fonts_sans[n][0]; ++n) {
607 QString font = qt_(tex_fonts_sans_gui[n]);
608 if (!isFontAvailable(tex_fonts_sans[n]))
609 font += qt_(" (not installed)");
610 fontModule->fontsSansCO->addItem(font);
612 for (int n = 0; tex_fonts_monospaced[n][0]; ++n) {
613 QString font = qt_(tex_fonts_monospaced_gui[n]);
614 if (!isFontAvailable(tex_fonts_monospaced[n]))
615 font += qt_(" (not installed)");
616 fontModule->fontsTypewriterCO->addItem(font);
619 fontModule->fontsizeCO->addItem(qt_("Default"));
620 fontModule->fontsizeCO->addItem(qt_("10"));
621 fontModule->fontsizeCO->addItem(qt_("11"));
622 fontModule->fontsizeCO->addItem(qt_("12"));
624 for (int n = 0; GuiDocument::fontfamilies_gui[n][0]; ++n)
625 fontModule->fontsDefaultCO->addItem(
626 qt_(GuiDocument::fontfamilies_gui[n]));
629 pageLayoutModule = new UiWidget<Ui::PageLayoutUi>;
631 connect(pageLayoutModule->papersizeCO, SIGNAL(activated(int)),
632 this, SLOT(setCustomPapersize(int)));
633 connect(pageLayoutModule->papersizeCO, SIGNAL(activated(int)),
634 this, SLOT(setCustomPapersize(int)));
635 connect(pageLayoutModule->portraitRB, SIGNAL(clicked()),
636 this, SLOT(portraitChanged()));
637 connect(pageLayoutModule->papersizeCO, SIGNAL(activated(int)),
638 this, SLOT(change_adaptor()));
639 connect(pageLayoutModule->paperheightLE, SIGNAL(textChanged(const QString &)),
640 this, SLOT(change_adaptor()));
641 connect(pageLayoutModule->paperwidthLE, SIGNAL(textChanged(const QString &)),
642 this, SLOT(change_adaptor()));
643 connect(pageLayoutModule->paperwidthUnitCO, SIGNAL(activated(int)),
644 this, SLOT(change_adaptor()));
645 connect(pageLayoutModule->paperheightUnitCO, SIGNAL(activated(int)),
646 this, SLOT(change_adaptor()));
647 connect(pageLayoutModule->portraitRB, SIGNAL(clicked()),
648 this, SLOT(change_adaptor()));
649 connect(pageLayoutModule->landscapeRB, SIGNAL(clicked()),
650 this, SLOT(change_adaptor()));
651 connect(pageLayoutModule->facingPagesCB, SIGNAL(clicked()),
652 this, SLOT(change_adaptor()));
653 connect(pageLayoutModule->pagestyleCO, SIGNAL(activated(int)),
654 this, SLOT(change_adaptor()));
656 pageLayoutModule->pagestyleCO->addItem(qt_("Default"));
657 pageLayoutModule->pagestyleCO->addItem(qt_("empty"));
658 pageLayoutModule->pagestyleCO->addItem(qt_("plain"));
659 pageLayoutModule->pagestyleCO->addItem(qt_("headings"));
660 pageLayoutModule->pagestyleCO->addItem(qt_("fancy"));
661 bc().addCheckedLineEdit(pageLayoutModule->paperheightLE,
662 pageLayoutModule->paperheightL);
663 bc().addCheckedLineEdit(pageLayoutModule->paperwidthLE,
664 pageLayoutModule->paperwidthL);
667 QComboBox * cb = pageLayoutModule->papersizeCO;
668 cb->addItem(qt_("Default"));
669 cb->addItem(qt_("Custom"));
670 cb->addItem(qt_("US letter"));
671 cb->addItem(qt_("US legal"));
672 cb->addItem(qt_("US executive"));
673 cb->addItem(qt_("A3"));
674 cb->addItem(qt_("A4"));
675 cb->addItem(qt_("A5"));
676 cb->addItem(qt_("B3"));
677 cb->addItem(qt_("B4"));
678 cb->addItem(qt_("B5"));
679 // remove the %-items from the unit choice
680 pageLayoutModule->paperwidthUnitCO->noPercents();
681 pageLayoutModule->paperheightUnitCO->noPercents();
682 pageLayoutModule->paperheightLE->setValidator(unsignedLengthValidator(
683 pageLayoutModule->paperheightLE));
684 pageLayoutModule->paperwidthLE->setValidator(unsignedLengthValidator(
685 pageLayoutModule->paperwidthLE));
688 marginsModule = new UiWidget<Ui::MarginsUi>;
690 connect(marginsModule->marginCB, SIGNAL(toggled(bool)),
691 this, SLOT(setCustomMargins(bool)));
692 connect(marginsModule->marginCB, SIGNAL(clicked()),
693 this, SLOT(change_adaptor()));
694 connect(marginsModule->topLE, SIGNAL(textChanged(QString)),
695 this, SLOT(change_adaptor()));
696 connect(marginsModule->topUnit, SIGNAL(activated(int)),
697 this, SLOT(change_adaptor()));
698 connect(marginsModule->bottomLE, SIGNAL(textChanged(QString)),
699 this, SLOT(change_adaptor()));
700 connect(marginsModule->bottomUnit, SIGNAL(activated(int)),
701 this, SLOT(change_adaptor()));
702 connect(marginsModule->innerLE, SIGNAL(textChanged(QString)),
703 this, SLOT(change_adaptor()));
704 connect(marginsModule->innerUnit, SIGNAL(activated(int)),
705 this, SLOT(change_adaptor()));
706 connect(marginsModule->outerLE, SIGNAL(textChanged(QString)),
707 this, SLOT(change_adaptor()));
708 connect(marginsModule->outerUnit, SIGNAL(activated(int)),
709 this, SLOT(change_adaptor()));
710 connect(marginsModule->headheightLE, SIGNAL(textChanged(QString)),
711 this, SLOT(change_adaptor()));
712 connect(marginsModule->headheightUnit, SIGNAL(activated(int)),
713 this, SLOT(change_adaptor()));
714 connect(marginsModule->headsepLE, SIGNAL(textChanged(QString)),
715 this, SLOT(change_adaptor()));
716 connect(marginsModule->headsepUnit, SIGNAL(activated(int)),
717 this, SLOT(change_adaptor()));
718 connect(marginsModule->footskipLE, SIGNAL(textChanged(QString)),
719 this, SLOT(change_adaptor()));
720 connect(marginsModule->footskipUnit, SIGNAL(activated(int)),
721 this, SLOT(change_adaptor()));
722 connect(marginsModule->columnsepLE, SIGNAL(textChanged(QString)),
723 this, SLOT(change_adaptor()));
724 connect(marginsModule->columnsepUnit, SIGNAL(activated(int)),
725 this, SLOT(change_adaptor()));
726 marginsModule->topLE->setValidator(unsignedLengthValidator(
727 marginsModule->topLE));
728 marginsModule->bottomLE->setValidator(unsignedLengthValidator(
729 marginsModule->bottomLE));
730 marginsModule->innerLE->setValidator(unsignedLengthValidator(
731 marginsModule->innerLE));
732 marginsModule->outerLE->setValidator(unsignedLengthValidator(
733 marginsModule->outerLE));
734 marginsModule->headsepLE->setValidator(unsignedLengthValidator(
735 marginsModule->headsepLE));
736 marginsModule->headheightLE->setValidator(unsignedLengthValidator(
737 marginsModule->headheightLE));
738 marginsModule->footskipLE->setValidator(unsignedLengthValidator(
739 marginsModule->footskipLE));
740 marginsModule->columnsepLE->setValidator(unsignedLengthValidator(
741 marginsModule->columnsepLE));
743 bc().addCheckedLineEdit(marginsModule->topLE,
744 marginsModule->topL);
745 bc().addCheckedLineEdit(marginsModule->bottomLE,
746 marginsModule->bottomL);
747 bc().addCheckedLineEdit(marginsModule->innerLE,
748 marginsModule->innerL);
749 bc().addCheckedLineEdit(marginsModule->outerLE,
750 marginsModule->outerL);
751 bc().addCheckedLineEdit(marginsModule->headsepLE,
752 marginsModule->headsepL);
753 bc().addCheckedLineEdit(marginsModule->headheightLE,
754 marginsModule->headheightL);
755 bc().addCheckedLineEdit(marginsModule->footskipLE,
756 marginsModule->footskipL);
757 bc().addCheckedLineEdit(marginsModule->columnsepLE,
758 marginsModule->columnsepL);
761 langModule = new UiWidget<Ui::LanguageUi>;
763 connect(langModule->languageCO, SIGNAL(activated(int)),
764 this, SLOT(change_adaptor()));
765 connect(langModule->defaultencodingRB, SIGNAL(clicked()),
766 this, SLOT(change_adaptor()));
767 connect(langModule->otherencodingRB, SIGNAL(clicked()),
768 this, SLOT(change_adaptor()));
769 connect(langModule->encodingCO, SIGNAL(activated(int)),
770 this, SLOT(change_adaptor()));
771 connect(langModule->quoteStyleCO, SIGNAL(activated(int)),
772 this, SLOT(change_adaptor()));
774 QAbstractItemModel * language_model = guiApp->languageModel();
775 // FIXME: it would be nice if sorting was enabled/disabled via a checkbox.
776 language_model->sort(0);
777 langModule->languageCO->setModel(language_model);
779 // Always put the default encoding in the first position.
780 langModule->encodingCO->addItem(qt_("Language Default (no inputenc)"));
781 QStringList encodinglist;
782 Encodings::const_iterator it = encodings.begin();
783 Encodings::const_iterator const end = encodings.end();
784 for (; it != end; ++it)
785 encodinglist.append(qt_(it->guiName()));
787 langModule->encodingCO->addItems(encodinglist);
789 langModule->quoteStyleCO->addItem(qt_("``text''"));
790 langModule->quoteStyleCO->addItem(qt_("''text''"));
791 langModule->quoteStyleCO->addItem(qt_(",,text``"));
792 langModule->quoteStyleCO->addItem(qt_(",,text''"));
793 langModule->quoteStyleCO->addItem(qt_("<<text>>"));
794 langModule->quoteStyleCO->addItem(qt_(">>text<<"));
797 numberingModule = new UiWidget<Ui::NumberingUi>;
799 connect(numberingModule->depthSL, SIGNAL(valueChanged(int)),
800 this, SLOT(change_adaptor()));
801 connect(numberingModule->tocSL, SIGNAL(valueChanged(int)),
802 this, SLOT(change_adaptor()));
803 connect(numberingModule->depthSL, SIGNAL(valueChanged(int)),
804 this, SLOT(updateNumbering()));
805 connect(numberingModule->tocSL, SIGNAL(valueChanged(int)),
806 this, SLOT(updateNumbering()));
807 numberingModule->tocTW->setColumnCount(3);
808 numberingModule->tocTW->headerItem()->setText(0, qt_("Example"));
809 numberingModule->tocTW->headerItem()->setText(1, qt_("Numbered"));
810 numberingModule->tocTW->headerItem()->setText(2, qt_("Appears in TOC"));
813 biblioModule = new UiWidget<Ui::BiblioUi>;
814 connect(biblioModule->citeNatbibRB, SIGNAL(toggled(bool)),
815 biblioModule->citationStyleL, SLOT(setEnabled(bool)));
816 connect(biblioModule->citeNatbibRB, SIGNAL(toggled(bool)),
817 biblioModule->citeStyleCO, SLOT(setEnabled(bool)));
819 connect(biblioModule->citeDefaultRB, SIGNAL(clicked()),
820 this, SLOT(change_adaptor()));
821 connect(biblioModule->citeNatbibRB, SIGNAL(clicked()),
822 this, SLOT(change_adaptor()));
823 connect(biblioModule->citeStyleCO, SIGNAL(activated(int)),
824 this, SLOT(change_adaptor()));
825 connect(biblioModule->citeJurabibRB, SIGNAL(clicked()),
826 this, SLOT(change_adaptor()));
827 connect(biblioModule->bibtopicCB, SIGNAL(clicked()),
828 this, SLOT(change_adaptor()));
830 biblioModule->citeStyleCO->addItem(qt_("Author-year"));
831 biblioModule->citeStyleCO->addItem(qt_("Numerical"));
832 biblioModule->citeStyleCO->setCurrentIndex(0);
835 mathsModule = new UiWidget<Ui::MathsUi>;
836 connect(mathsModule->amsautoCB, SIGNAL(toggled(bool)),
837 mathsModule->amsCB, SLOT(setDisabled(bool)));
838 connect(mathsModule->esintautoCB, SIGNAL(toggled(bool)),
839 mathsModule->esintCB, SLOT(setDisabled(bool)));
841 connect(mathsModule->amsCB, SIGNAL(clicked()),
842 this, SLOT(change_adaptor()));
843 connect(mathsModule->amsautoCB, SIGNAL(clicked()),
844 this, SLOT(change_adaptor()));
845 connect(mathsModule->esintCB, SIGNAL(clicked()),
846 this, SLOT(change_adaptor()));
847 connect(mathsModule->esintautoCB, SIGNAL(clicked()),
848 this, SLOT(change_adaptor()));
850 latexModule = new UiWidget<Ui::LaTeXUi>;
852 connect(latexModule->optionsLE, SIGNAL(textChanged(QString)),
853 this, SLOT(change_adaptor()));
854 connect(latexModule->defaultOptionsCB, SIGNAL(clicked()),
855 this, SLOT(change_adaptor()));
856 connect(latexModule->psdriverCO, SIGNAL(activated(int)),
857 this, SLOT(change_adaptor()));
858 connect(latexModule->classCO, SIGNAL(activated(int)),
859 this, SLOT(classChanged()));
860 connect(latexModule->classCO, SIGNAL(activated(int)),
861 this, SLOT(change_adaptor()));
862 connect(latexModule->layoutPB, SIGNAL(clicked()),
863 this, SLOT(browseLayout()));
864 connect(latexModule->layoutPB, SIGNAL(clicked()),
865 this, SLOT(change_adaptor()));
866 connect(latexModule->childDocGB, SIGNAL(clicked()),
867 this, SLOT(change_adaptor()));
868 connect(latexModule->childDocLE, SIGNAL(textChanged(QString)),
869 this, SLOT(change_adaptor()));
870 connect(latexModule->childDocPB, SIGNAL(clicked()),
871 this, SLOT(browseMaster()));
873 // postscript drivers
874 for (int n = 0; tex_graphics[n][0]; ++n) {
875 QString enc = qt_(tex_graphics_gui[n]);
876 latexModule->psdriverCO->addItem(enc);
879 latexModule->classCO->setModel(&classes_model_);
880 LayoutFileList const & bcl = LayoutFileList::get();
881 vector<LayoutFileIndex> classList = bcl.classList();
882 sort(classList.begin(), classList.end(), less_textclass_avail_desc());
884 vector<LayoutFileIndex>::const_iterator cit = classList.begin();
885 vector<LayoutFileIndex>::const_iterator cen = classList.end();
886 for (int i = 0; cit != cen; ++cit, ++i) {
887 LayoutFile const & tc = bcl[*cit];
888 docstring item = (tc.isTeXClassAvailable()) ?
889 from_utf8(tc.description()) :
890 bformat(_("Unavailable: %1$s"), from_utf8(tc.description()));
891 classes_model_.insertRow(i, toqstr(item), *cit);
895 branchesModule = new GuiBranches;
896 connect(branchesModule, SIGNAL(changed()),
897 this, SLOT(change_adaptor()));
900 preambleModule = new PreambleModule;
901 connect(preambleModule, SIGNAL(changed()),
902 this, SLOT(change_adaptor()));
905 bulletsModule = new BulletsModule;
906 connect(bulletsModule, SIGNAL(changed()),
907 this, SLOT(change_adaptor()));
910 modulesModule = new UiWidget<Ui::ModulesUi>;
913 new ModuleSelectionManager(modulesModule->availableLV,
914 modulesModule->selectedLV,
915 modulesModule->addPB, modulesModule->deletePB,
916 modulesModule->upPB, modulesModule->downPB,
917 availableModel(), selectedModel(), this);
918 connect(selectionManager, SIGNAL(updateHook()),
919 this, SLOT(updateModuleInfo()));
920 connect(selectionManager, SIGNAL(updateHook()),
921 this, SLOT(change_adaptor()));
922 connect(selectionManager, SIGNAL(selectionChanged()),
923 this, SLOT(modulesChanged()));
926 pdfSupportModule = new UiWidget<Ui::PDFSupportUi>;
928 connect(pdfSupportModule->use_hyperrefGB, SIGNAL(toggled(bool)),
929 this, SLOT(change_adaptor()));
930 connect(pdfSupportModule->titleLE, SIGNAL(textChanged(QString)),
931 this, SLOT(change_adaptor()));
932 connect(pdfSupportModule->authorLE, SIGNAL(textChanged(QString)),
933 this, SLOT(change_adaptor()));
934 connect(pdfSupportModule->subjectLE, SIGNAL(textChanged(QString)),
935 this, SLOT(change_adaptor()));
936 connect(pdfSupportModule->keywordsLE, SIGNAL(textChanged(QString)),
937 this, SLOT(change_adaptor()));
938 connect(pdfSupportModule->bookmarksGB, SIGNAL(toggled(bool)),
939 this, SLOT(change_adaptor()));
940 connect(pdfSupportModule->bookmarksnumberedCB, SIGNAL(toggled(bool)),
941 this, SLOT(change_adaptor()));
942 connect(pdfSupportModule->bookmarksopenGB, SIGNAL(toggled(bool)),
943 this, SLOT(change_adaptor()));
944 connect(pdfSupportModule->bookmarksopenlevelSB, SIGNAL(valueChanged(int)),
945 this, SLOT(change_adaptor()));
946 connect(pdfSupportModule->breaklinksCB, SIGNAL(toggled(bool)),
947 this, SLOT(change_adaptor()));
948 connect(pdfSupportModule->pdfborderCB, SIGNAL(toggled(bool)),
949 this, SLOT(change_adaptor()));
950 connect(pdfSupportModule->colorlinksCB, SIGNAL(toggled(bool)),
951 this, SLOT(change_adaptor()));
952 connect(pdfSupportModule->backrefCO, SIGNAL(activated(int)),
953 this, SLOT(change_adaptor()));
954 connect(pdfSupportModule->pdfusetitleCB, SIGNAL(toggled(bool)),
955 this, SLOT(change_adaptor()));
956 connect(pdfSupportModule->fullscreenCB, SIGNAL(toggled(bool)),
957 this, SLOT(change_adaptor()));
958 connect(pdfSupportModule->optionsLE, SIGNAL(textChanged(QString)),
959 this, SLOT(change_adaptor()));
961 for (int i = 0; backref_opts[i][0]; ++i)
962 pdfSupportModule->backrefCO->addItem(qt_(backref_opts_gui[i]));
965 floatModule = new FloatPlacement;
966 connect(floatModule, SIGNAL(changed()),
967 this, SLOT(change_adaptor()));
969 docPS->addPanel(latexModule, qt_("Document Class"));
970 docPS->addPanel(modulesModule, qt_("Modules"));
971 docPS->addPanel(fontModule, qt_("Fonts"));
972 docPS->addPanel(textLayoutModule, qt_("Text Layout"));
973 docPS->addPanel(pageLayoutModule, qt_("Page Layout"));
974 docPS->addPanel(marginsModule, qt_("Page Margins"));
975 docPS->addPanel(langModule, qt_("Language"));
976 docPS->addPanel(numberingModule, qt_("Numbering & TOC"));
977 docPS->addPanel(biblioModule, qt_("Bibliography"));
978 docPS->addPanel(pdfSupportModule, qt_("PDF Properties"));
979 docPS->addPanel(mathsModule, qt_("Math Options"));
980 docPS->addPanel(floatModule, qt_("Float Placement"));
981 docPS->addPanel(bulletsModule, qt_("Bullets"));
982 docPS->addPanel(branchesModule, qt_("Branches"));
983 docPS->addPanel(preambleModule, qt_("LaTeX Preamble"));
984 docPS->setCurrentPanel(qt_("Document Class"));
985 // FIXME: hack to work around resizing bug in Qt >= 4.2
986 // bug verified with Qt 4.2.{0-3} (JSpitzm)
987 #if QT_VERSION >= 0x040200
988 docPS->updateGeometry();
993 void GuiDocument::showPreamble()
995 docPS->setCurrentPanel(qt_("LaTeX Preamble"));
999 void GuiDocument::saveDefaultClicked()
1005 void GuiDocument::useDefaultsClicked()
1011 void GuiDocument::change_adaptor()
1017 QString GuiDocument::validateListingsParameters()
1019 // use a cache here to avoid repeated validation
1020 // of the same parameters
1021 static string param_cache;
1022 static QString msg_cache;
1024 if (textLayoutModule->bypassCB->isChecked())
1027 string params = fromqstr(textLayoutModule->listingsED->toPlainText());
1028 if (params != param_cache) {
1029 param_cache = params;
1030 msg_cache = toqstr(InsetListingsParams(params).validate());
1036 void GuiDocument::setListingsMessage()
1038 static bool isOK = true;
1039 QString msg = validateListingsParameters();
1040 if (msg.isEmpty()) {
1044 // listingsTB->setTextColor("black");
1045 textLayoutModule->listingsTB->setPlainText(
1046 qt_("Input listings parameters on the right. "
1047 "Enter ? for a list of parameters."));
1050 // listingsTB->setTextColor("red");
1051 textLayoutModule->listingsTB->setPlainText(msg);
1056 void GuiDocument::setLSpacing(int item)
1058 textLayoutModule->lspacingLE->setEnabled(item == 3);
1062 void GuiDocument::setSkip(int item)
1064 bool const enable = (item == 3);
1065 textLayoutModule->skipLE->setEnabled(enable);
1066 textLayoutModule->skipLengthCO->setEnabled(enable);
1070 void GuiDocument::enableSkip(bool skip)
1072 textLayoutModule->skipCO->setEnabled(skip);
1073 textLayoutModule->skipLE->setEnabled(skip);
1074 textLayoutModule->skipLengthCO->setEnabled(skip);
1076 setSkip(textLayoutModule->skipCO->currentIndex());
1079 void GuiDocument::portraitChanged()
1081 setMargins(pageLayoutModule->papersizeCO->currentIndex());
1084 void GuiDocument::setMargins(bool custom)
1086 marginsModule->marginCB->setChecked(custom);
1087 setCustomMargins(custom);
1091 void GuiDocument::setCustomPapersize(int papersize)
1093 bool const custom = (papersize == 1);
1095 pageLayoutModule->paperwidthL->setEnabled(custom);
1096 pageLayoutModule->paperwidthLE->setEnabled(custom);
1097 pageLayoutModule->paperwidthUnitCO->setEnabled(custom);
1098 pageLayoutModule->paperheightL->setEnabled(custom);
1099 pageLayoutModule->paperheightLE->setEnabled(custom);
1100 pageLayoutModule->paperheightLE->setFocus();
1101 pageLayoutModule->paperheightUnitCO->setEnabled(custom);
1105 void GuiDocument::setColSep()
1107 setCustomMargins(marginsModule->marginCB->checkState() == Qt::Checked);
1111 void GuiDocument::setCustomMargins(bool custom)
1113 marginsModule->topL->setEnabled(!custom);
1114 marginsModule->topLE->setEnabled(!custom);
1115 marginsModule->topUnit->setEnabled(!custom);
1117 marginsModule->bottomL->setEnabled(!custom);
1118 marginsModule->bottomLE->setEnabled(!custom);
1119 marginsModule->bottomUnit->setEnabled(!custom);
1121 marginsModule->innerL->setEnabled(!custom);
1122 marginsModule->innerLE->setEnabled(!custom);
1123 marginsModule->innerUnit->setEnabled(!custom);
1125 marginsModule->outerL->setEnabled(!custom);
1126 marginsModule->outerLE->setEnabled(!custom);
1127 marginsModule->outerUnit->setEnabled(!custom);
1129 marginsModule->headheightL->setEnabled(!custom);
1130 marginsModule->headheightLE->setEnabled(!custom);
1131 marginsModule->headheightUnit->setEnabled(!custom);
1133 marginsModule->headsepL->setEnabled(!custom);
1134 marginsModule->headsepLE->setEnabled(!custom);
1135 marginsModule->headsepUnit->setEnabled(!custom);
1137 marginsModule->footskipL->setEnabled(!custom);
1138 marginsModule->footskipLE->setEnabled(!custom);
1139 marginsModule->footskipUnit->setEnabled(!custom);
1141 bool const enableColSep = !custom &&
1142 textLayoutModule->twoColumnCB->checkState() == Qt::Checked;
1143 marginsModule->columnsepL->setEnabled(enableColSep);
1144 marginsModule->columnsepLE->setEnabled(enableColSep);
1145 marginsModule->columnsepUnit->setEnabled(enableColSep);
1149 void GuiDocument::updateFontsize(string const & items, string const & sel)
1151 fontModule->fontsizeCO->clear();
1152 fontModule->fontsizeCO->addItem(qt_("Default"));
1154 for (int n = 0; !token(items,'|',n).empty(); ++n)
1155 fontModule->fontsizeCO->
1156 addItem(toqstr(token(items,'|',n)));
1158 for (int n = 0; n < fontModule->fontsizeCO->count(); ++n) {
1159 if (fromqstr(fontModule->fontsizeCO->itemText(n)) == sel) {
1160 fontModule->fontsizeCO->setCurrentIndex(n);
1167 void GuiDocument::romanChanged(int item)
1169 string const font = tex_fonts_roman[item];
1170 fontModule->fontScCB->setEnabled(providesSC(font));
1171 fontModule->fontOsfCB->setEnabled(providesOSF(font));
1175 void GuiDocument::sansChanged(int item)
1177 string const font = tex_fonts_sans[item];
1178 bool scaleable = providesScale(font);
1179 fontModule->scaleSansSB->setEnabled(scaleable);
1180 fontModule->scaleSansLA->setEnabled(scaleable);
1184 void GuiDocument::ttChanged(int item)
1186 string const font = tex_fonts_monospaced[item];
1187 bool scaleable = providesScale(font);
1188 fontModule->scaleTypewriterSB->setEnabled(scaleable);
1189 fontModule->scaleTypewriterLA->setEnabled(scaleable);
1193 void GuiDocument::updatePagestyle(string const & items, string const & sel)
1196 pageLayoutModule->pagestyleCO->clear();
1197 pageLayoutModule->pagestyleCO->addItem(qt_("Default"));
1199 for (int n = 0; !token(items, '|', n).empty(); ++n) {
1200 string style = token(items, '|', n);
1201 QString style_gui = qt_(style);
1202 pagestyles.push_back(pair<string, QString>(style, style_gui));
1203 pageLayoutModule->pagestyleCO->addItem(style_gui);
1206 if (sel == "default") {
1207 pageLayoutModule->pagestyleCO->setCurrentIndex(0);
1213 for (size_t i = 0; i < pagestyles.size(); ++i)
1214 if (pagestyles[i].first == sel)
1215 nn = pageLayoutModule->pagestyleCO->findText(pagestyles[i].second);
1218 pageLayoutModule->pagestyleCO->setCurrentIndex(nn);
1222 void GuiDocument::browseLayout()
1224 QString const label1 = qt_("Layouts|#o#O");
1225 QString const dir1 = toqstr(lyxrc.document_path);
1226 QStringList const filter(qt_("LyX Layout (*.layout)"));
1227 QString file = browseRelFile(QString(), bufferFilepath(),
1228 qt_("Local layout file"), filter, false,
1231 if (!file.endsWith(".layout"))
1234 FileName layoutFile = support::makeAbsPath(fromqstr(file),
1235 fromqstr(bufferFilepath()));
1237 int const ret = Alert::prompt(_("Local layout file"),
1238 _("The layout file you have selected is a local layout\n"
1239 "file, not one in the system or user directory. Your\n"
1240 "document may not work with this layout if you do not\n"
1241 "keep the layout file in the document directory."),
1242 1, 1, _("&Set Layout"), _("&Cancel"));
1246 // load the layout file
1247 LayoutFileList & bcl = LayoutFileList::get();
1248 string classname = layoutFile.onlyFileName();
1249 // this will update an existing layout if that layout has been loaded before.
1250 LayoutFileIndex name = bcl.addLocalLayout(
1251 classname.substr(0, classname.size() - 7),
1252 layoutFile.onlyPath().absFilename());
1255 Alert::error(_("Error"),
1256 _("Unable to read local layout file."));
1260 // do not trigger classChanged if there is no change.
1261 if (latexModule->classCO->currentText() == toqstr(name))
1265 int idx = latexModule->classCO->findText(toqstr(name));
1267 classes_model_.insertRow(0, toqstr(name), name);
1268 latexModule->classCO->setCurrentIndex(0);
1270 latexModule->classCO->setCurrentIndex(idx);
1276 void GuiDocument::browseMaster()
1278 QString const title = qt_("Select master document");
1279 QString const dir1 = toqstr(lyxrc.document_path);
1280 QString const old = latexModule->childDocLE->text();
1281 QString const docpath = toqstr(support::onlyPath(buffer().absFileName()));
1282 QStringList const filter(qt_("LyX Files (*.lyx)"));
1283 QString file = browseRelFile(old, docpath, title, filter, false,
1284 qt_("Documents|#o#O"), toqstr(lyxrc.document_path));
1286 latexModule->childDocLE->setText(file);
1290 void GuiDocument::classChanged()
1292 int idx = latexModule->classCO->currentIndex();
1295 string const classname = classes_model_.getIDString(idx);
1297 // check whether the selected modules have changed.
1298 bool modulesChanged = false;
1299 unsigned int const srows = selectedModel()->rowCount();
1300 if (srows != bp_.getModules().size())
1301 modulesChanged = true;
1303 list<string>::const_iterator mit = bp_.getModules().begin();
1304 list<string>::const_iterator men = bp_.getModules().end();
1305 for (unsigned int i = 0; i < srows && mit != men; ++i, ++mit)
1306 if (selectedModel()->getIDString(i) != *mit) {
1307 modulesChanged = true;
1312 if (modulesChanged || lyxrc.auto_reset_options) {
1313 if (applyPB->isEnabled()) {
1314 int const ret = Alert::prompt(_("Unapplied changes"),
1315 _("Some changes in the dialog were not yet applied.\n"
1316 "If you do not apply now, they will be lost after this action."),
1317 1, 1, _("&Apply"), _("&Dismiss"));
1323 // We load the TextClass as soon as it is selected. This is
1324 // necessary so that other options in the dialog can be updated
1325 // according to the new class. Note, however, that, if you use
1326 // the scroll wheel when sitting on the combo box, we'll load a
1327 // lot of TextClass objects very quickly....
1328 if (!bp_.setBaseClass(classname)) {
1329 Alert::error(_("Error"), _("Unable to set document class."));
1332 if (lyxrc.auto_reset_options)
1333 bp_.useClassDefaults();
1335 // With the introduction of modules came a distinction between the base
1336 // class and the document class. The former corresponds to the main layout
1337 // file; the latter is that plus the modules (or the document-specific layout,
1338 // or whatever else there could be). Our parameters come from the document
1339 // class. So when we set the base class, we also need to recreate the document
1340 // class. Otherwise, we still have the old one.
1341 bp_.makeDocumentClass();
1342 // the new class may require some default modules.
1343 updateSelectedModules();
1349 // This is an insanely complicated attempt to make this sort of thing
1350 // work with RTL languages.
1351 docstring formatStrVec(vector<string> const & v, docstring const & s)
1353 //this mess formats the list as "v[0], v[1], ..., [s] v[n]"
1357 return from_ascii(v[0]);
1358 if (v.size() == 2) {
1359 docstring retval = _("%1$s and %2$s");
1360 retval = subst(retval, _("and"), s);
1361 return bformat(retval, from_ascii(v[0]), from_ascii(v[1]));
1363 // The idea here is to format all but the last two items...
1364 int const vSize = v.size();
1365 docstring t2 = _("%1$s, %2$s");
1366 docstring retval = from_ascii(v[0]);
1367 for (int i = 1; i < vSize - 2; ++i)
1368 retval = bformat(t2, retval, from_ascii(v[i]));
1369 //...and then to plug them, and the last two, into this schema
1370 docstring t = _("%1$s, %2$s, and %3$s");
1371 t = subst(t, _("and"), s);
1372 return bformat(t, retval, from_ascii(v[vSize - 2]), from_ascii(v[vSize - 1]));
1375 vector<string> idsToNames(vector<string> const & idList)
1377 vector<string> retval;
1378 vector<string>::const_iterator it = idList.begin();
1379 vector<string>::const_iterator end = idList.end();
1380 for (; it != end; ++it) {
1381 LyXModule const * const mod = moduleList[*it];
1383 retval.push_back(*it + " (Unavailable)");
1385 retval.push_back(mod->getName());
1392 void GuiDocument::modulesChanged()
1394 // update list of loaded modules
1395 bp_.clearLayoutModules();
1396 int const srows = modules_sel_model_.rowCount();
1397 vector<string> selModList;
1398 for (int i = 0; i < srows; ++i)
1399 bp_.addLayoutModule(modules_sel_model_.getIDString(i));
1401 // update the list of removed modules
1402 bp_.clearRemovedModules();
1403 list<string> const & reqmods = bp_.baseClass()->defaultModules();
1404 list<string>::const_iterator rit = reqmods.begin();
1405 list<string>::const_iterator ren = reqmods.end();
1407 // check each of the default modules
1408 for (; rit != ren; rit++) {
1409 list<string>::const_iterator mit = bp_.getModules().begin();
1410 list<string>::const_iterator men = bp_.getModules().end();
1412 for (; mit != men; mit++) {
1419 // the module isn't present so must have been removed by the user
1420 bp_.addRemovedModule(*rit);
1423 bp_.makeDocumentClass();
1428 void GuiDocument::updateModuleInfo()
1430 selectionManager->update();
1432 //Module description
1433 bool const focusOnSelected = selectionManager->selectedFocused();
1434 QListView const * const lv =
1435 focusOnSelected ? modulesModule->selectedLV : modulesModule->availableLV;
1436 if (lv->selectionModel()->selectedIndexes().isEmpty()) {
1437 modulesModule->infoML->document()->clear();
1440 QModelIndex const & idx = lv->selectionModel()->currentIndex();
1441 GuiIdListModel const & idModel =
1442 focusOnSelected ? modules_sel_model_ : modules_av_model_;
1443 string const modName = idModel.getIDString(idx.row());
1444 docstring desc = getModuleDescription(modName);
1446 vector<string> pkgList = getPackageList(modName);
1447 docstring pkgdesc = formatStrVec(pkgList, _("and"));
1448 if (!pkgdesc.empty()) {
1451 desc += bformat(_("Package(s) required: %1$s."), pkgdesc);
1454 pkgList = getRequiredList(modName);
1455 if (!pkgList.empty()) {
1456 vector<string> const reqDescs = idsToNames(pkgList);
1457 pkgdesc = formatStrVec(reqDescs, _("or"));
1460 desc += bformat(_("Module required: %1$s."), pkgdesc);
1463 pkgList = getExcludedList(modName);
1464 if (!pkgList.empty()) {
1465 vector<string> const reqDescs = idsToNames(pkgList);
1466 pkgdesc = formatStrVec(reqDescs, _( "and"));
1469 desc += bformat(_("Modules excluded: %1$s."), pkgdesc);
1472 if (!isModuleAvailable(modName)) {
1475 desc += _("WARNING: Some required packages are unavailable!");
1478 modulesModule->infoML->document()->setPlainText(toqstr(desc));
1482 void GuiDocument::updateNumbering()
1484 DocumentClass const & tclass = documentClass();
1486 numberingModule->tocTW->setUpdatesEnabled(false);
1487 numberingModule->tocTW->clear();
1489 int const depth = numberingModule->depthSL->value();
1490 int const toc = numberingModule->tocSL->value();
1491 QString const no = qt_("No");
1492 QString const yes = qt_("Yes");
1493 QTreeWidgetItem * item = 0;
1495 DocumentClass::const_iterator lit = tclass.begin();
1496 DocumentClass::const_iterator len = tclass.end();
1497 for (; lit != len; ++lit) {
1498 int const toclevel = lit->toclevel;
1499 if (toclevel != Layout::NOT_IN_TOC && lit->labeltype == LABEL_COUNTER) {
1500 item = new QTreeWidgetItem(numberingModule->tocTW);
1501 item->setText(0, toqstr(translateIfPossible(lit->name())));
1502 item->setText(1, (toclevel <= depth) ? yes : no);
1503 item->setText(2, (toclevel <= toc) ? yes : no);
1507 numberingModule->tocTW->setUpdatesEnabled(true);
1508 numberingModule->tocTW->update();
1512 void GuiDocument::apply(BufferParams & params)
1515 preambleModule->apply(params);
1518 params.setCiteEngine(ENGINE_BASIC);
1520 if (biblioModule->citeNatbibRB->isChecked()) {
1521 bool const use_numerical_citations =
1522 biblioModule->citeStyleCO->currentIndex();
1523 if (use_numerical_citations)
1524 params.setCiteEngine(ENGINE_NATBIB_NUMERICAL);
1526 params.setCiteEngine(ENGINE_NATBIB_AUTHORYEAR);
1528 } else if (biblioModule->citeJurabibRB->isChecked())
1529 params.setCiteEngine(ENGINE_JURABIB);
1531 params.use_bibtopic =
1532 biblioModule->bibtopicCB->isChecked();
1534 // language & quotes
1535 if (langModule->defaultencodingRB->isChecked()) {
1536 params.inputenc = "auto";
1538 int i = langModule->encodingCO->currentIndex();
1540 params.inputenc = "default";
1542 QString const enc_gui =
1543 langModule->encodingCO->currentText();
1544 Encodings::const_iterator it = encodings.begin();
1545 Encodings::const_iterator const end = encodings.end();
1547 for (; it != end; ++it) {
1548 if (qt_(it->guiName()) == enc_gui) {
1549 params.inputenc = it->latexName();
1555 // should not happen
1556 lyxerr << "GuiDocument::apply: Unknown encoding! Resetting to default" << endl;
1557 params.inputenc = "default";
1562 InsetQuotes::QuoteLanguage lga = InsetQuotes::EnglishQuotes;
1563 switch (langModule->quoteStyleCO->currentIndex()) {
1565 lga = InsetQuotes::EnglishQuotes;
1568 lga = InsetQuotes::SwedishQuotes;
1571 lga = InsetQuotes::GermanQuotes;
1574 lga = InsetQuotes::PolishQuotes;
1577 lga = InsetQuotes::FrenchQuotes;
1580 lga = InsetQuotes::DanishQuotes;
1583 params.quotes_language = lga;
1585 QString const lang = langModule->languageCO->itemData(
1586 langModule->languageCO->currentIndex()).toString();
1587 params.language = lyx::languages.getLanguage(fromqstr(lang));
1590 if (params.documentClass().hasTocLevels()) {
1591 params.tocdepth = numberingModule->tocSL->value();
1592 params.secnumdepth = numberingModule->depthSL->value();
1596 params.user_defined_bullet(0) = bulletsModule->bullet(0);
1597 params.user_defined_bullet(1) = bulletsModule->bullet(1);
1598 params.user_defined_bullet(2) = bulletsModule->bullet(2);
1599 params.user_defined_bullet(3) = bulletsModule->bullet(3);
1602 params.graphicsDriver =
1603 tex_graphics[latexModule->psdriverCO->currentIndex()];
1606 int idx = latexModule->classCO->currentIndex();
1608 string const classname = classes_model_.getIDString(idx);
1609 params.setBaseClass(classname);
1613 params.clearLayoutModules();
1614 int const srows = modules_sel_model_.rowCount();
1615 vector<string> selModList;
1616 for (int i = 0; i < srows; ++i)
1617 params.addLayoutModule(modules_sel_model_.getIDString(i));
1618 // update the list of removed modules
1619 params.clearRemovedModules();
1620 list<string> const & reqmods = params.baseClass()->defaultModules();
1621 list<string>::const_iterator rit = reqmods.begin();
1622 list<string>::const_iterator ren = reqmods.end();
1623 // check each of the required modules
1624 for (; rit != ren; rit++) {
1625 list<string>::const_iterator mit = params.getModules().begin();
1626 list<string>::const_iterator men = params.getModules().end();
1628 for (; mit != men; mit++) {
1635 // the module isn't present so must have been removed by the user
1636 params.addRemovedModule(*rit);
1640 if (mathsModule->amsautoCB->isChecked()) {
1641 params.use_amsmath = BufferParams::package_auto;
1643 if (mathsModule->amsCB->isChecked())
1644 params.use_amsmath = BufferParams::package_on;
1646 params.use_amsmath = BufferParams::package_off;
1649 if (mathsModule->esintautoCB->isChecked())
1650 params.use_esint = BufferParams::package_auto;
1652 if (mathsModule->esintCB->isChecked())
1653 params.use_esint = BufferParams::package_on;
1655 params.use_esint = BufferParams::package_off;
1658 if (pageLayoutModule->pagestyleCO->currentIndex() == 0)
1659 params.pagestyle = "default";
1661 QString style_gui = pageLayoutModule->pagestyleCO->currentText();
1662 for (size_t i = 0; i != pagestyles.size(); ++i)
1663 if (pagestyles[i].second == style_gui)
1664 params.pagestyle = pagestyles[i].first;
1667 switch (textLayoutModule->lspacingCO->currentIndex()) {
1669 params.spacing().set(Spacing::Single);
1672 params.spacing().set(Spacing::Onehalf);
1675 params.spacing().set(Spacing::Double);
1678 params.spacing().set(Spacing::Other,
1679 fromqstr(textLayoutModule->lspacingLE->text()));
1683 if (textLayoutModule->twoColumnCB->isChecked())
1688 // text should have passed validation
1689 params.listings_params =
1690 InsetListingsParams(fromqstr(textLayoutModule->listingsED->toPlainText())).params();
1692 if (textLayoutModule->indentRB->isChecked())
1693 params.paragraph_separation = BufferParams::ParagraphIndentSeparation;
1695 params.paragraph_separation = BufferParams::ParagraphSkipSeparation;
1697 switch (textLayoutModule->skipCO->currentIndex()) {
1699 params.setDefSkip(VSpace(VSpace::SMALLSKIP));
1702 params.setDefSkip(VSpace(VSpace::MEDSKIP));
1705 params.setDefSkip(VSpace(VSpace::BIGSKIP));
1710 widgetsToLength(textLayoutModule->skipLE,
1711 textLayoutModule->skipLengthCO)
1713 params.setDefSkip(vs);
1717 // DocumentDefskipCB assures that this never happens
1718 // so Assert then !!! - jbl
1719 params.setDefSkip(VSpace(VSpace::MEDSKIP));
1724 fromqstr(latexModule->optionsLE->text());
1726 params.use_default_options =
1727 latexModule->defaultOptionsCB->isChecked();
1729 if (latexModule->childDocGB->isChecked())
1731 fromqstr(latexModule->childDocLE->text());
1733 params.master = string();
1735 params.float_placement = floatModule->get();
1739 tex_fonts_roman[fontModule->fontsRomanCO->currentIndex()];
1742 tex_fonts_sans[fontModule->fontsSansCO->currentIndex()];
1744 params.fontsTypewriter =
1745 tex_fonts_monospaced[fontModule->fontsTypewriterCO->currentIndex()];
1748 fromqstr(fontModule->cjkFontLE->text());
1750 params.fontsSansScale = fontModule->scaleSansSB->value();
1752 params.fontsTypewriterScale = fontModule->scaleTypewriterSB->value();
1754 params.fontsSC = fontModule->fontScCB->isChecked();
1756 params.fontsOSF = fontModule->fontOsfCB->isChecked();
1758 params.fontsDefaultFamily = GuiDocument::fontfamilies[
1759 fontModule->fontsDefaultCO->currentIndex()];
1761 if (fontModule->fontsizeCO->currentIndex() == 0)
1762 params.fontsize = "default";
1765 fromqstr(fontModule->fontsizeCO->currentText());
1768 params.papersize = PAPER_SIZE(
1769 pageLayoutModule->papersizeCO->currentIndex());
1771 // custom, A3, B3 and B4 paper sizes need geometry
1772 int psize = pageLayoutModule->papersizeCO->currentIndex();
1773 bool geom_papersize = (psize == 1 || psize == 5 || psize == 8 || psize == 9);
1775 params.paperwidth = widgetsToLength(pageLayoutModule->paperwidthLE,
1776 pageLayoutModule->paperwidthUnitCO);
1778 params.paperheight = widgetsToLength(pageLayoutModule->paperheightLE,
1779 pageLayoutModule->paperheightUnitCO);
1781 if (pageLayoutModule->facingPagesCB->isChecked())
1782 params.sides = TwoSides;
1784 params.sides = OneSide;
1786 if (pageLayoutModule->landscapeRB->isChecked())
1787 params.orientation = ORIENTATION_LANDSCAPE;
1789 params.orientation = ORIENTATION_PORTRAIT;
1792 params.use_geometry = !marginsModule->marginCB->isChecked()
1795 Ui::MarginsUi const * m = marginsModule;
1797 params.leftmargin = widgetsToLength(m->innerLE, m->innerUnit);
1798 params.topmargin = widgetsToLength(m->topLE, m->topUnit);
1799 params.rightmargin = widgetsToLength(m->outerLE, m->outerUnit);
1800 params.bottommargin = widgetsToLength(m->bottomLE, m->bottomUnit);
1801 params.headheight = widgetsToLength(m->headheightLE, m->headheightUnit);
1802 params.headsep = widgetsToLength(m->headsepLE, m->headsepUnit);
1803 params.footskip = widgetsToLength(m->footskipLE, m->footskipUnit);
1804 params.columnsep = widgetsToLength(m->columnsepLE, m->columnsepUnit);
1806 branchesModule->apply(params);
1809 PDFOptions & pdf = params.pdfoptions();
1810 pdf.use_hyperref = pdfSupportModule->use_hyperrefGB->isChecked();
1811 pdf.title = fromqstr(pdfSupportModule->titleLE->text());
1812 pdf.author = fromqstr(pdfSupportModule->authorLE->text());
1813 pdf.subject = fromqstr(pdfSupportModule->subjectLE->text());
1814 pdf.keywords = fromqstr(pdfSupportModule->keywordsLE->text());
1816 pdf.bookmarks = pdfSupportModule->bookmarksGB->isChecked();
1817 pdf.bookmarksnumbered = pdfSupportModule->bookmarksnumberedCB->isChecked();
1818 pdf.bookmarksopen = pdfSupportModule->bookmarksopenGB->isChecked();
1819 pdf.bookmarksopenlevel = pdfSupportModule->bookmarksopenlevelSB->value();
1821 pdf.breaklinks = pdfSupportModule->breaklinksCB->isChecked();
1822 pdf.pdfborder = pdfSupportModule->pdfborderCB->isChecked();
1823 pdf.pdfusetitle = pdfSupportModule->pdfusetitleCB->isChecked();
1824 pdf.colorlinks = pdfSupportModule->colorlinksCB->isChecked();
1826 backref_opts[pdfSupportModule->backrefCO->currentIndex()];
1827 if (pdfSupportModule->fullscreenCB->isChecked())
1828 pdf.pagemode = pdf.pagemode_fullscreen;
1830 pdf.pagemode.clear();
1831 pdf.quoted_options = pdf.quoted_options_check(
1832 fromqstr(pdfSupportModule->optionsLE->text()));
1836 void GuiDocument::paramsToDialog()
1838 // set the default unit
1839 Length::UNIT defaultUnit = Length::CM;
1840 switch (lyxrc.default_papersize) {
1841 case PAPER_DEFAULT: break;
1843 case PAPER_USLETTER:
1845 case PAPER_USEXECUTIVE:
1846 defaultUnit = Length::IN;
1855 defaultUnit = Length::CM;
1862 preambleModule->update(bp_, id());
1865 biblioModule->citeDefaultRB->setChecked(
1866 bp_.citeEngine() == ENGINE_BASIC);
1868 biblioModule->citeNatbibRB->setChecked(
1869 bp_.citeEngine() == ENGINE_NATBIB_NUMERICAL ||
1870 bp_.citeEngine() == ENGINE_NATBIB_AUTHORYEAR);
1872 biblioModule->citeStyleCO->setCurrentIndex(
1873 bp_.citeEngine() == ENGINE_NATBIB_NUMERICAL);
1875 biblioModule->citeJurabibRB->setChecked(
1876 bp_.citeEngine() == ENGINE_JURABIB);
1878 biblioModule->bibtopicCB->setChecked(
1881 // language & quotes
1882 int const pos = langModule->languageCO->findData(toqstr(
1883 bp_.language->lang()));
1884 langModule->languageCO->setCurrentIndex(pos);
1886 langModule->quoteStyleCO->setCurrentIndex(
1887 bp_.quotes_language);
1889 bool default_enc = true;
1890 if (bp_.inputenc != "auto") {
1891 default_enc = false;
1892 if (bp_.inputenc == "default") {
1893 langModule->encodingCO->setCurrentIndex(0);
1896 Encodings::const_iterator it = encodings.begin();
1897 Encodings::const_iterator const end = encodings.end();
1898 for (; it != end; ++it) {
1899 if (it->latexName() == bp_.inputenc) {
1900 enc_gui = it->guiName();
1904 int const i = langModule->encodingCO->findText(
1907 langModule->encodingCO->setCurrentIndex(i);
1909 // unknown encoding. Set to default.
1913 langModule->defaultencodingRB->setChecked(default_enc);
1914 langModule->otherencodingRB->setChecked(!default_enc);
1917 int const min_toclevel = documentClass().min_toclevel();
1918 int const max_toclevel = documentClass().max_toclevel();
1919 if (documentClass().hasTocLevels()) {
1920 numberingModule->setEnabled(true);
1921 numberingModule->depthSL->setMinimum(min_toclevel - 1);
1922 numberingModule->depthSL->setMaximum(max_toclevel);
1923 numberingModule->depthSL->setValue(bp_.secnumdepth);
1924 numberingModule->tocSL->setMaximum(min_toclevel - 1);
1925 numberingModule->tocSL->setMaximum(max_toclevel);
1926 numberingModule->tocSL->setValue(bp_.tocdepth);
1929 numberingModule->setEnabled(false);
1930 numberingModule->tocTW->clear();
1934 bulletsModule->setBullet(0, bp_.user_defined_bullet(0));
1935 bulletsModule->setBullet(1, bp_.user_defined_bullet(1));
1936 bulletsModule->setBullet(2, bp_.user_defined_bullet(2));
1937 bulletsModule->setBullet(3, bp_.user_defined_bullet(3));
1938 bulletsModule->init();
1941 int nitem = findToken(tex_graphics, bp_.graphicsDriver);
1943 latexModule->psdriverCO->setCurrentIndex(nitem);
1946 mathsModule->amsCB->setChecked(
1947 bp_.use_amsmath == BufferParams::package_on);
1948 mathsModule->amsautoCB->setChecked(
1949 bp_.use_amsmath == BufferParams::package_auto);
1951 mathsModule->esintCB->setChecked(
1952 bp_.use_esint == BufferParams::package_on);
1953 mathsModule->esintautoCB->setChecked(
1954 bp_.use_esint == BufferParams::package_auto);
1956 switch (bp_.spacing().getSpace()) {
1957 case Spacing::Other: nitem = 3; break;
1958 case Spacing::Double: nitem = 2; break;
1959 case Spacing::Onehalf: nitem = 1; break;
1960 case Spacing::Default: case Spacing::Single: nitem = 0; break;
1964 string const & layoutID = bp_.baseClassID();
1965 setLayoutComboByIDString(layoutID);
1967 updatePagestyle(documentClass().opt_pagestyle(),
1970 textLayoutModule->lspacingCO->setCurrentIndex(nitem);
1971 if (bp_.spacing().getSpace() == Spacing::Other) {
1972 textLayoutModule->lspacingLE->setText(
1973 toqstr(bp_.spacing().getValueAsString()));
1977 if (bp_.paragraph_separation == BufferParams::ParagraphIndentSeparation)
1978 textLayoutModule->indentRB->setChecked(true);
1980 textLayoutModule->skipRB->setChecked(true);
1983 switch (bp_.getDefSkip().kind()) {
1984 case VSpace::SMALLSKIP:
1987 case VSpace::MEDSKIP:
1990 case VSpace::BIGSKIP:
1993 case VSpace::LENGTH:
1996 string const length = bp_.getDefSkip().asLyXCommand();
1997 lengthToWidgets(textLayoutModule->skipLE,
1998 textLayoutModule->skipLengthCO,
1999 length, defaultUnit);
2006 textLayoutModule->skipCO->setCurrentIndex(skip);
2009 textLayoutModule->twoColumnCB->setChecked(
2012 // break listings_params to multiple lines
2014 InsetListingsParams(bp_.listings_params).separatedParams();
2015 textLayoutModule->listingsED->setPlainText(toqstr(lstparams));
2017 if (!bp_.options.empty()) {
2018 latexModule->optionsLE->setText(
2019 toqstr(bp_.options));
2021 latexModule->optionsLE->setText(QString());
2025 latexModule->defaultOptionsCB->setChecked(
2026 bp_.use_default_options);
2028 if (!documentClass().options().empty()) {
2029 latexModule->defaultOptionsLE->setText(
2030 toqstr(documentClass().options()));
2032 latexModule->defaultOptionsLE->setText(
2033 toqstr(_("[No options predefined]")));
2036 latexModule->defaultOptionsLE->setEnabled(
2037 bp_.use_default_options
2038 && !documentClass().options().empty());
2040 latexModule->defaultOptionsCB->setEnabled(
2041 !documentClass().options().empty());
2043 if (!bp_.master.empty()) {
2044 latexModule->childDocGB->setChecked(true);
2045 latexModule->childDocLE->setText(
2046 toqstr(bp_.master));
2048 latexModule->childDocLE->setText(QString());
2049 latexModule->childDocGB->setChecked(false);
2052 floatModule->set(bp_.float_placement);
2055 updateFontsize(documentClass().opt_fontsize(),
2058 int n = findToken(tex_fonts_roman, bp_.fontsRoman);
2060 fontModule->fontsRomanCO->setCurrentIndex(n);
2064 n = findToken(tex_fonts_sans, bp_.fontsSans);
2066 fontModule->fontsSansCO->setCurrentIndex(n);
2070 n = findToken(tex_fonts_monospaced, bp_.fontsTypewriter);
2072 fontModule->fontsTypewriterCO->setCurrentIndex(n);
2076 if (!bp_.fontsCJK.empty())
2077 fontModule->cjkFontLE->setText(
2078 toqstr(bp_.fontsCJK));
2080 fontModule->cjkFontLE->setText(QString());
2082 fontModule->fontScCB->setChecked(bp_.fontsSC);
2083 fontModule->fontOsfCB->setChecked(bp_.fontsOSF);
2084 fontModule->scaleSansSB->setValue(bp_.fontsSansScale);
2085 fontModule->scaleTypewriterSB->setValue(bp_.fontsTypewriterScale);
2086 n = findToken(GuiDocument::fontfamilies, bp_.fontsDefaultFamily);
2088 fontModule->fontsDefaultCO->setCurrentIndex(n);
2091 int const psize = bp_.papersize;
2092 pageLayoutModule->papersizeCO->setCurrentIndex(psize);
2093 setCustomPapersize(psize);
2095 bool const landscape =
2096 bp_.orientation == ORIENTATION_LANDSCAPE;
2097 pageLayoutModule->landscapeRB->setChecked(landscape);
2098 pageLayoutModule->portraitRB->setChecked(!landscape);
2100 pageLayoutModule->facingPagesCB->setChecked(
2101 bp_.sides == TwoSides);
2104 lengthToWidgets(pageLayoutModule->paperwidthLE,
2105 pageLayoutModule->paperwidthUnitCO, bp_.paperwidth, defaultUnit);
2107 lengthToWidgets(pageLayoutModule->paperheightLE,
2108 pageLayoutModule->paperheightUnitCO, bp_.paperheight, defaultUnit);
2111 Ui::MarginsUi * m = marginsModule;
2113 setMargins(!bp_.use_geometry);
2115 lengthToWidgets(m->topLE, m->topUnit,
2116 bp_.topmargin, defaultUnit);
2118 lengthToWidgets(m->bottomLE, m->bottomUnit,
2119 bp_.bottommargin, defaultUnit);
2121 lengthToWidgets(m->innerLE, m->innerUnit,
2122 bp_.leftmargin, defaultUnit);
2124 lengthToWidgets(m->outerLE, m->outerUnit,
2125 bp_.rightmargin, defaultUnit);
2127 lengthToWidgets(m->headheightLE, m->headheightUnit,
2128 bp_.headheight, defaultUnit);
2130 lengthToWidgets(m->headsepLE, m->headsepUnit,
2131 bp_.headsep, defaultUnit);
2133 lengthToWidgets(m->footskipLE, m->footskipUnit,
2134 bp_.footskip, defaultUnit);
2136 lengthToWidgets(m->columnsepLE, m->columnsepUnit,
2137 bp_.columnsep, defaultUnit);
2139 branchesModule->update(bp_);
2142 PDFOptions const & pdf = bp_.pdfoptions();
2143 pdfSupportModule->use_hyperrefGB->setChecked(pdf.use_hyperref);
2144 pdfSupportModule->titleLE->setText(toqstr(pdf.title));
2145 pdfSupportModule->authorLE->setText(toqstr(pdf.author));
2146 pdfSupportModule->subjectLE->setText(toqstr(pdf.subject));
2147 pdfSupportModule->keywordsLE->setText(toqstr(pdf.keywords));
2149 pdfSupportModule->bookmarksGB->setChecked(pdf.bookmarks);
2150 pdfSupportModule->bookmarksnumberedCB->setChecked(pdf.bookmarksnumbered);
2151 pdfSupportModule->bookmarksopenGB->setChecked(pdf.bookmarksopen);
2153 pdfSupportModule->bookmarksopenlevelSB->setValue(pdf.bookmarksopenlevel);
2155 pdfSupportModule->breaklinksCB->setChecked(pdf.breaklinks);
2156 pdfSupportModule->pdfborderCB->setChecked(pdf.pdfborder);
2157 pdfSupportModule->pdfusetitleCB->setChecked(pdf.pdfusetitle);
2158 pdfSupportModule->colorlinksCB->setChecked(pdf.colorlinks);
2160 n = findToken(backref_opts, pdf.backref);
2162 pdfSupportModule->backrefCO->setCurrentIndex(n);
2164 pdfSupportModule->fullscreenCB->setChecked
2165 (pdf.pagemode == pdf.pagemode_fullscreen);
2167 pdfSupportModule->optionsLE->setText(
2168 toqstr(pdf.quoted_options));
2172 void GuiDocument::applyView()
2178 void GuiDocument::saveDocDefault()
2180 // we have to apply the params first
2186 void GuiDocument::updateAvailableModules()
2188 modules_av_model_.clear();
2189 list<modInfoStruct> const & modInfoList = getModuleInfo();
2190 list<modInfoStruct>::const_iterator mit = modInfoList.begin();
2191 list<modInfoStruct>::const_iterator men = modInfoList.end();
2192 for (int i = 0; mit != men; ++mit, ++i)
2193 modules_av_model_.insertRow(i, mit->name, mit->id,
2198 void GuiDocument::updateSelectedModules()
2200 modules_sel_model_.clear();
2201 list<modInfoStruct> const selModList = getSelectedModules();
2202 list<modInfoStruct>::const_iterator mit = selModList.begin();
2203 list<modInfoStruct>::const_iterator men = selModList.end();
2204 for (int i = 0; mit != men; ++mit, ++i)
2205 modules_sel_model_.insertRow(i, mit->name, mit->id,
2210 void GuiDocument::updateContents()
2212 // Nothing to do here as the document settings is not cursor dependant.
2217 void GuiDocument::useClassDefaults()
2219 if (applyPB->isEnabled()) {
2220 int const ret = Alert::prompt(_("Unapplied changes"),
2221 _("Some changes in the dialog were not yet applied.\n"
2222 "If you do not apply now, they will be lost after this action."),
2223 1, 1, _("&Apply"), _("&Dismiss"));
2228 int idx = latexModule->classCO->currentIndex();
2229 string const classname = classes_model_.getIDString(idx);
2230 if (!bp_.setBaseClass(classname)) {
2231 Alert::error(_("Error"), _("Unable to set document class."));
2234 bp_.useClassDefaults();
2239 void GuiDocument::setLayoutComboByIDString(string const & idString)
2241 int idx = classes_model_.findIDString(idString);
2243 Alert::warning(_("Can't set layout!"),
2244 bformat(_("Unable to set layout for ID: %1$s"), from_utf8(idString)));
2246 latexModule->classCO->setCurrentIndex(idx);
2250 bool GuiDocument::isValid()
2252 return validateListingsParameters().isEmpty()
2253 && (textLayoutModule->skipCO->currentIndex() != 3
2254 || !textLayoutModule->skipLE->text().isEmpty());
2258 char const * const GuiDocument::fontfamilies[5] = {
2259 "default", "rmdefault", "sfdefault", "ttdefault", ""
2263 char const * GuiDocument::fontfamilies_gui[5] = {
2264 N_("Default"), N_("Roman"), N_("Sans Serif"), N_("Typewriter"), ""
2268 bool GuiDocument::initialiseParams(string const &)
2270 BufferView const * view = bufferview();
2272 bp_ = BufferParams();
2276 bp_ = view->buffer().params();
2278 updateAvailableModules();
2279 updateSelectedModules();
2280 //FIXME It'd be nice to make sure here that the selected
2281 //modules are consistent: That required modules are actually
2282 //selected, and that we don't have conflicts. If so, we could
2283 //at least pop up a warning.
2289 void GuiDocument::clearParams()
2291 bp_ = BufferParams();
2295 BufferId GuiDocument::id() const
2297 BufferView const * const view = bufferview();
2298 return view? &view->buffer() : 0;
2302 list<GuiDocument::modInfoStruct> const & GuiDocument::getModuleInfo()
2304 return moduleNames_;
2308 list<GuiDocument::modInfoStruct> const GuiDocument::getSelectedModules()
2310 list<string> const & mods = params().getModules();
2311 list<string>::const_iterator it = mods.begin();
2312 list<string>::const_iterator end = mods.end();
2313 list<modInfoStruct> mInfo;
2314 for (; it != end; ++it) {
2317 LyXModule * mod = moduleList[*it];
2319 m.name = qt_(mod->getName());
2321 m.name = toqstr(*it) + toqstr(" (") + qt_("Not Found") + toqstr(")");
2328 DocumentClass const & GuiDocument::documentClass() const
2330 return bp_.documentClass();
2334 static void dispatch_bufferparams(Dialog const & dialog,
2335 BufferParams const & bp, FuncCode lfun)
2338 ss << "\\begin_header\n";
2340 ss << "\\end_header\n";
2341 dialog.dispatch(FuncRequest(lfun, ss.str()));
2345 void GuiDocument::dispatchParams()
2347 // This must come first so that a language change is correctly noticed
2350 // Apply the BufferParams. Note that this will set the base class
2351 // and then update the buffer's layout.
2352 dispatch_bufferparams(*this, params(), LFUN_BUFFER_PARAMS_APPLY);
2354 if (!params().master.empty()) {
2355 FileName const master_file = support::makeAbsPath(params().master,
2356 support::onlyPath(buffer().absFileName()));
2357 if (isLyXFilename(master_file.absFilename())) {
2358 Buffer * master = checkAndLoadLyXFile(master_file);
2359 const_cast<Buffer &>(buffer()).setParent(master);
2363 // Generate the colours requested by each new branch.
2364 BranchList & branchlist = params().branchlist();
2365 if (!branchlist.empty()) {
2366 BranchList::const_iterator it = branchlist.begin();
2367 BranchList::const_iterator const end = branchlist.end();
2368 for (; it != end; ++it) {
2369 docstring const & current_branch = it->branch();
2370 Branch const * branch = branchlist.find(current_branch);
2371 string const x11hexname = X11hexname(branch->color());
2372 // display the new color
2373 docstring const str = current_branch + ' ' + from_ascii(x11hexname);
2374 dispatch(FuncRequest(LFUN_SET_COLOR, str));
2377 // Open insets of selected branches, close deselected ones
2378 dispatch(FuncRequest(LFUN_ALL_INSETS_TOGGLE,
2381 // FIXME: If we used an LFUN, we would not need those two lines:
2382 BufferView * bv = const_cast<BufferView *>(bufferview());
2383 bv->processUpdateFlags(Update::Force | Update::FitCursor);
2387 void GuiDocument::setLanguage() const
2389 Language const * const newL = bp_.language;
2390 if (buffer().params().language == newL)
2393 string const & lang_name = newL->lang();
2394 dispatch(FuncRequest(LFUN_BUFFER_LANGUAGE, lang_name));
2398 void GuiDocument::saveAsDefault() const
2400 dispatch_bufferparams(*this, params(), LFUN_BUFFER_SAVE_AS_DEFAULT);
2404 bool GuiDocument::isFontAvailable(string const & font) const
2406 if (font == "default" || font == "cmr"
2407 || font == "cmss" || font == "cmtt")
2408 // these are standard
2410 if (font == "lmodern" || font == "lmss" || font == "lmtt")
2411 return LaTeXFeatures::isAvailable("lmodern");
2412 if (font == "times" || font == "palatino"
2413 || font == "helvet" || font == "courier")
2414 return LaTeXFeatures::isAvailable("psnfss");
2415 if (font == "cmbr" || font == "cmtl")
2416 return LaTeXFeatures::isAvailable("cmbright");
2417 if (font == "utopia")
2418 return LaTeXFeatures::isAvailable("utopia")
2419 || LaTeXFeatures::isAvailable("fourier");
2420 if (font == "beraserif" || font == "berasans"
2421 || font == "beramono")
2422 return LaTeXFeatures::isAvailable("bera");
2423 return LaTeXFeatures::isAvailable(font);
2427 bool GuiDocument::providesOSF(string const & font) const
2430 return isFontAvailable("eco");
2431 if (font == "palatino")
2432 return isFontAvailable("mathpazo");
2437 bool GuiDocument::providesSC(string const & font) const
2439 if (font == "palatino")
2440 return isFontAvailable("mathpazo");
2441 if (font == "utopia")
2442 return isFontAvailable("fourier");
2447 bool GuiDocument::providesScale(string const & font) const
2449 return font == "helvet" || font == "luximono"
2450 || font == "berasans" || font == "beramono";
2454 void GuiDocument::loadModuleInfo()
2456 moduleNames_.clear();
2457 LyXModuleList::const_iterator it = moduleList.begin();
2458 LyXModuleList::const_iterator end = moduleList.end();
2459 for (; it != end; ++it) {
2462 m.name = qt_(it->getName());
2463 // this is supposed to give us the first sentence of the description
2464 QString desc = qt_(it->getDescription());
2465 int const pos = desc.indexOf(".");
2467 desc.truncate(pos + 1);
2468 m.description = desc;
2469 moduleNames_.push_back(m);
2474 Dialog * createGuiDocument(GuiView & lv) { return new GuiDocument(lv); }
2477 } // namespace frontend
2480 #include "GuiDocument_moc.cpp"