3 * This file is part of LyX, the document processor.
4 * Licence details can be found in the file COPYING.
7 * \author Jürgen Spitzmüller
11 * Full author contact details are available in file CREDITS.
16 #include "GuiTabular.h"
18 #include "GuiApplication.h"
19 #include "GuiSetBorder.h"
21 #include "LengthCombo.h"
22 #include "qt_helpers.h"
23 #include "Validator.h"
25 #include "BufferView.h"
27 #include "FuncRequest.h"
28 #include "FuncStatus.h"
32 #include "insets/InsetTabular.h"
34 #include "support/debug.h"
37 #include <QPushButton>
38 #include <QRadioButton>
46 GuiTabular::GuiTabular(QWidget * parent)
47 : InsetParamsWidget(parent)
51 tabularWidthED->setValidator(unsignedLengthValidator(tabularWidthED));
52 columnWidthED->setValidator(unsignedLengthValidator(columnWidthED));
53 multirowOffsetED->setValidator(new LengthValidator(multirowOffsetED));
54 topspaceED->setValidator(new LengthValidator(topspaceED));
55 bottomspaceED->setValidator(new LengthValidator(bottomspaceED));
56 interlinespaceED->setValidator(new LengthValidator(interlinespaceED));
58 tabularWidthUnitLC->setCurrentItem(Length::defaultUnit());
59 columnWidthUnitLC->setCurrentItem(Length::defaultUnit());
60 multirowOffsetUnitLC->setCurrentItem(Length::defaultUnit());
61 topspaceUnitLC->setCurrentItem(Length::defaultUnit());
62 bottomspaceUnitLC->setCurrentItem(Length::defaultUnit());
63 interlinespaceUnitLC->setCurrentItem(Length::defaultUnit());
65 connect(topspaceED, SIGNAL(textEdited(const QString &)),
66 this, SLOT(checkEnabled()));
67 connect(topspaceUnitLC, SIGNAL(selectionChanged(lyx::Length::UNIT)),
68 this, SLOT(checkEnabled()));
69 connect(bottomspaceED, SIGNAL(textEdited(const QString &)),
70 this, SLOT(checkEnabled()));
71 connect(bottomspaceUnitLC, SIGNAL(selectionChanged(lyx::Length::UNIT)),
72 this, SLOT(checkEnabled()));
73 connect(interlinespaceED, SIGNAL(textEdited(const QString &)),
74 this, SLOT(checkEnabled()));
75 connect(interlinespaceUnitLC, SIGNAL(selectionChanged(lyx::Length::UNIT)),
76 this, SLOT(checkEnabled()));
77 connect(booktabsRB, SIGNAL(clicked(bool)),
78 this, SLOT(checkEnabled()));
79 connect(borderDefaultRB, SIGNAL(clicked(bool)),
80 this, SLOT(checkEnabled()));
81 connect(borderSetPB, SIGNAL(clicked()),
82 this, SLOT(borderSet_clicked()));
83 connect(borderUnsetPB, SIGNAL(clicked()),
84 this, SLOT(borderUnset_clicked()));
85 connect(hAlignCO, SIGNAL(activated(int)),
86 this, SLOT(checkEnabled()));
87 connect(vAlignCO, SIGNAL(activated(int)),
88 this, SLOT(checkEnabled()));
89 connect(multicolumnCB, SIGNAL(clicked()),
90 this, SLOT(checkEnabled()));
91 connect(multirowCB, SIGNAL(clicked()),
92 this, SLOT(checkEnabled()));
93 connect(multirowOffsetED, SIGNAL(textEdited(const QString &)),
94 this, SLOT(checkEnabled()));
95 connect(multirowOffsetUnitLC, SIGNAL(selectionChanged(lyx::Length::UNIT)),
96 this, SLOT(checkEnabled()));
97 connect(newpageCB, SIGNAL(clicked()),
98 this, SLOT(checkEnabled()));
99 connect(headerStatusCB, SIGNAL(clicked()),
100 this, SLOT(checkEnabled()));
101 connect(headerBorderAboveCB, SIGNAL(clicked()),
102 this, SLOT(checkEnabled()));
103 connect(headerBorderBelowCB, SIGNAL(clicked()),
104 this, SLOT(checkEnabled()));
105 connect(firstheaderStatusCB, SIGNAL(clicked()),
106 this, SLOT(checkEnabled()));
107 connect(firstheaderBorderAboveCB, SIGNAL(clicked()),
108 this, SLOT(checkEnabled()));
109 connect(firstheaderBorderBelowCB, SIGNAL(clicked()),
110 this, SLOT(checkEnabled()));
111 connect(firstheaderNoContentsCB, SIGNAL(clicked()),
112 this, SLOT(checkEnabled()));
113 connect(footerStatusCB, SIGNAL(clicked()),
114 this, SLOT(checkEnabled()));
115 connect(footerBorderAboveCB, SIGNAL(clicked()),
116 this, SLOT(checkEnabled()));
117 connect(footerBorderBelowCB, SIGNAL(clicked()),
118 this, SLOT(checkEnabled()));
119 connect(lastfooterStatusCB, SIGNAL(clicked()),
120 this, SLOT(checkEnabled()));
121 connect(lastfooterBorderAboveCB, SIGNAL(clicked()),
122 this, SLOT(checkEnabled()));
123 connect(lastfooterBorderBelowCB, SIGNAL(clicked()),
124 this, SLOT(checkEnabled()));
125 connect(lastfooterNoContentsCB, SIGNAL(clicked()),
126 this, SLOT(checkEnabled()));
127 connect(captionStatusCB, SIGNAL(clicked()),
128 this, SLOT(checkEnabled()));
129 connect(specialAlignmentED, SIGNAL(editingFinished()),
130 this, SLOT(checkEnabled()));
131 connect(columnWidthED, SIGNAL(textEdited(const QString &)),
132 this, SLOT(checkEnabled()));
133 connect(columnWidthUnitLC, SIGNAL(selectionChanged(lyx::Length::UNIT)),
134 this, SLOT(checkEnabled()));
135 connect(borders, SIGNAL(topSet(bool)),
136 this, SLOT(checkEnabled()));
137 connect(borders, SIGNAL(bottomSet(bool)),
138 this, SLOT(checkEnabled()));
139 connect(borders, SIGNAL(rightSet(bool)),
140 this, SLOT(checkEnabled()));
141 connect(borders, SIGNAL(leftSet(bool)),
142 this, SLOT(checkEnabled()));
143 connect(rotateTabularCB, SIGNAL(clicked()),
144 this, SLOT(checkEnabled()));
145 connect(rotateCellCB, SIGNAL(clicked()),
146 this, SLOT(checkEnabled()));
147 connect(TableAlignCO, SIGNAL(activated(int)),
148 this, SLOT(checkEnabled()));
149 connect(longTabularCB, SIGNAL(clicked()),
150 this, SLOT(checkEnabled()));
151 connect(leftRB, SIGNAL(clicked()),
152 this, SLOT(checkEnabled()));
153 connect(centerRB, SIGNAL(clicked()),
154 this, SLOT(checkEnabled()));
155 connect(rightRB, SIGNAL(clicked()),
156 this, SLOT(checkEnabled()));
157 connect(tabularWidthED, SIGNAL(textEdited(const QString &)),
158 this, SLOT(checkEnabled()));
160 decimalPointED->setInputMask("X; ");
161 decimalPointED->setMaxLength(1);
163 // initialize the length validator
164 addCheckedWidget(columnWidthED, columnWidthLA);
165 addCheckedWidget(multirowOffsetED, multirowOffsetLA);
166 addCheckedWidget(topspaceED, topspaceLA);
167 addCheckedWidget(bottomspaceED, bottomspaceLA);
168 addCheckedWidget(interlinespaceED, interlinespaceLA);
169 addCheckedWidget(tabularWidthED, tabularWidthLA);
173 void GuiTabular::on_topspaceCO_activated(int index)
175 bool const enable = (index == 2);
176 topspaceED->setEnabled(enable);
177 topspaceUnitLC->setEnabled(enable);
181 void GuiTabular::on_bottomspaceCO_activated(int index)
183 bool const enable = (index == 2);
184 bottomspaceED->setEnabled(enable);
185 bottomspaceUnitLC->setEnabled(enable);
189 void GuiTabular::on_interlinespaceCO_activated(int index)
191 bool const enable = (index == 2);
192 interlinespaceED->setEnabled(enable);
193 interlinespaceUnitLC->setEnabled(enable);
197 void GuiTabular::checkEnabled()
199 // if there is a LaTeX argument, the width and alignment will be overwritten
200 // therefore disable them in this case
201 columnWidthED->setEnabled(specialAlignmentED->text().isEmpty());
202 // if the column has a width, multirows are always left-aligned
203 // therefore disable hAlignCB in this case
204 hAlignCO->setEnabled(!(multirowCB->isChecked()
205 && !widgetsToLength(columnWidthED, columnWidthUnitLC).empty())
206 && specialAlignmentED->text().isEmpty());
208 hAlignCO->itemData(hAlignCO->currentIndex()).toString() == QString("decimal");
209 decimalPointED->setEnabled(dalign);
210 decimalLA->setEnabled(dalign);
212 bool const setwidth = TableAlignCO->currentText() == qt_("Middle")
213 && !longTabularCB->isChecked() && !rotateTabularCB->isChecked();
214 tabularWidthLA->setEnabled(setwidth);
215 tabularWidthED->setEnabled(setwidth);
216 tabularWidthUnitLC->setEnabled(setwidth);
218 bool const is_tabular_star = !tabularWidthED->text().isEmpty();
219 rotateTabularCB->setDisabled(is_tabular_star);
221 bool const enable_valign =
222 !multirowCB->isChecked()
223 && !widgetsToLength(columnWidthED, columnWidthUnitLC).empty()
224 && specialAlignmentED->text().isEmpty();
225 vAlignCO->setEnabled(enable_valign);
226 vAlignLA->setEnabled(enable_valign);
228 topspaceED->setEnabled(topspaceCO->currentIndex() == 2);
229 topspaceED->setEnabled(topspaceCO->currentIndex() == 2);
230 topspaceUnitLC->setEnabled(topspaceCO->currentIndex() == 2);
231 bottomspaceED->setEnabled(bottomspaceCO->currentIndex() == 2);
232 bottomspaceUnitLC->setEnabled(bottomspaceCO->currentIndex() == 2);
233 interlinespaceED->setEnabled(interlinespaceCO->currentIndex() == 2);
234 interlinespaceUnitLC->setEnabled(interlinespaceCO->currentIndex() == 2);
236 // setting as longtable is not allowed when table is inside a float
237 longTabularCB->setEnabled(!is_tabular_star && funcEnabled(Tabular::SET_LONGTABULAR));
238 bool const longtabular = longTabularCB->isChecked();
239 longtableGB->setEnabled(true);
240 newpageCB->setEnabled(longtabular);
241 alignmentGB->setEnabled(longtabular);
242 // longtables and tabular* cannot have a vertical alignment
243 TableAlignLA->setDisabled(is_tabular_star || longtabular);
244 TableAlignCO->setDisabled(is_tabular_star || longtabular);
246 // FIXME: This Dialog is really horrible, disabling/enabling a checkbox
247 // depending on the cursor position is very very unintuitive...
248 // We need some edit boxes to show which rows are header/footer/etc
249 // without having to move the cursor first.
250 headerStatusCB->setEnabled(longtabular
251 && (headerStatusCB->isChecked() ?
252 funcEnabled(Tabular::UNSET_LTHEAD) :
253 funcEnabled(Tabular::SET_LTHEAD)));
254 headerBorderAboveCB->setEnabled(longtabular
255 && headerStatusCB->isChecked());
256 headerBorderBelowCB->setEnabled(longtabular
257 && headerStatusCB->isChecked());
259 // first header can only be suppressed when there is a header
260 // firstheader_suppressable_ is set in paramsToDialog
261 firstheaderNoContentsCB->setEnabled(longtabular && firstheader_suppressable_);
262 // check if setting a first header is allowed
263 // additionally check firstheaderNoContentsCB because when this is
264 // the case a first header makes no sense
265 firstheaderStatusCB->setEnabled((firstheaderStatusCB->isChecked() ?
266 funcEnabled(Tabular::UNSET_LTFIRSTHEAD) :
267 funcEnabled(Tabular::SET_LTFIRSTHEAD))
268 && longtabular && !firstheaderNoContentsCB->isChecked());
269 firstheaderBorderAboveCB->setEnabled(longtabular
270 && firstheaderStatusCB->isChecked());
271 firstheaderBorderBelowCB->setEnabled(longtabular
272 && firstheaderStatusCB->isChecked());
274 footerStatusCB->setEnabled(longtabular
275 && (footerStatusCB->isChecked() ?
276 funcEnabled(Tabular::UNSET_LTFOOT) :
277 funcEnabled(Tabular::SET_LTFOOT)));
278 footerBorderAboveCB->setEnabled(longtabular
279 && footerBorderAboveCB->isChecked());
280 footerBorderBelowCB->setEnabled(longtabular
281 && footerBorderAboveCB->isChecked());
283 // last footer can only be suppressed when there is a footer
284 // lastfooter_suppressable_ is set in paramsToDialog
285 lastfooterNoContentsCB->setEnabled(longtabular && lastfooter_suppressable_);
286 // check if setting a last footer is allowed
287 // additionally check lastfooterNoContentsCB because when this is
288 // the case a last footer makes no sense
289 lastfooterStatusCB->setEnabled((lastfooterStatusCB->isChecked() ?
290 funcEnabled(Tabular::UNSET_LTLASTFOOT) :
291 funcEnabled(Tabular::SET_LTLASTFOOT))
292 && longtabular && !lastfooterNoContentsCB->isChecked());
293 lastfooterBorderAboveCB->setEnabled(longtabular
294 && lastfooterBorderAboveCB->isChecked());
295 lastfooterBorderBelowCB->setEnabled(longtabular
296 && lastfooterBorderAboveCB->isChecked());
298 captionStatusCB->setEnabled(funcEnabled(Tabular::TOGGLE_LTCAPTION)
301 multicolumnCB->setEnabled(funcEnabled(Tabular::MULTICOLUMN));
302 multirowCB->setEnabled(funcEnabled(Tabular::MULTIROW));
303 bool const enable_mr = multirowCB->isChecked();
304 multirowOffsetLA->setEnabled(enable_mr);
305 multirowOffsetED->setEnabled(enable_mr);
306 multirowOffsetUnitLC->setEnabled(enable_mr);
312 void GuiTabular::borderSet_clicked()
314 borders->setTop(true);
315 borders->setBottom(true);
316 borders->setLeft(true);
317 borders->setRight(true);
318 // repaint the setborder widget
324 void GuiTabular::borderUnset_clicked()
326 borders->setTop(false);
327 borders->setBottom(false);
328 borders->setLeft(false);
329 borders->setRight(false);
330 // repaint the setborder widget
336 static void setParam(string & param_str, Tabular::Feature f, string const & arg = string())
339 param_str += featureAsString(f) + ' ' + arg;
343 void GuiTabular::setHAlign(string & param_str) const
345 Tabular::Feature num = Tabular::ALIGN_LEFT;
346 Tabular::Feature multi_num = Tabular::M_ALIGN_LEFT;
348 fromqstr(hAlignCO->itemData(hAlignCO->currentIndex()).toString());
349 if (align == "left") {
350 num = Tabular::ALIGN_LEFT;
351 multi_num = Tabular::M_ALIGN_LEFT;
352 } else if (align == "center") {
353 num = Tabular::ALIGN_CENTER;
354 multi_num = Tabular::M_ALIGN_CENTER;
355 } else if (align == "right") {
356 num = Tabular::ALIGN_RIGHT;
357 multi_num = Tabular::M_ALIGN_RIGHT;
358 } else if (align == "justified") {
359 num = Tabular::ALIGN_BLOCK;
360 //multi_num: no equivalent
361 } else if (align == "decimal") {
362 num = Tabular::ALIGN_DECIMAL;
363 //multi_num: no equivalent
366 if (multicolumnCB->isChecked())
367 setParam(param_str, multi_num);
369 setParam(param_str, num);
373 void GuiTabular::setVAlign(string & param_str) const
375 int const align = vAlignCO->currentIndex();
376 enum VALIGN { TOP, MIDDLE, BOTTOM };
380 case 0: v = TOP; break;
381 case 1: v = MIDDLE; break;
382 case 2: v = BOTTOM; break;
385 Tabular::Feature num = Tabular::VALIGN_MIDDLE;
386 Tabular::Feature multi_num = Tabular::M_VALIGN_MIDDLE;
390 num = Tabular::VALIGN_TOP;
391 multi_num = Tabular::M_VALIGN_TOP;
394 num = Tabular::VALIGN_MIDDLE;
395 multi_num = Tabular::M_VALIGN_MIDDLE;
398 num = Tabular::VALIGN_BOTTOM;
399 multi_num = Tabular::M_VALIGN_BOTTOM;
402 if (multicolumnCB->isChecked() || multirowCB->isChecked())
403 setParam(param_str, multi_num);
405 setParam(param_str, num);
409 void GuiTabular::setTableAlignment(string & param_str) const
411 int const align = TableAlignCO->currentIndex();
413 case 0: setParam(param_str, Tabular::TABULAR_VALIGN_TOP);
415 case 1: setParam(param_str, Tabular::TABULAR_VALIGN_MIDDLE);
417 case 2: setParam(param_str, Tabular::TABULAR_VALIGN_BOTTOM);
423 docstring GuiTabular::dialogToParams() const
425 // FIXME: We should use Tabular directly.
426 string param_str = "tabular from-dialog";
429 string tabwidth = widgetsToLength(tabularWidthED, tabularWidthUnitLC);
430 if (tabwidth.empty())
432 setParam(param_str, Tabular::SET_TABULAR_WIDTH, tabwidth);
434 // apply the fixed width values
435 // this must be done before applying the column alignment
436 // because its value influences the alignment of multirow cells
437 string width = widgetsToLength(columnWidthED, columnWidthUnitLC);
440 if (multicolumnCB->isChecked())
441 setParam(param_str, Tabular::SET_MPWIDTH, width);
443 setParam(param_str, Tabular::SET_PWIDTH, width);
445 // apply the column alignment
446 // multirows inherit the alignment from the column; if a column width
447 // is set, multicolumns are always left-aligned so that in this case
448 // its alignment must not be applied (see bug #8084)
449 if (!(multirowCB->isChecked() && width != "0pt"))
450 setHAlign(param_str);
452 // SET_DECIMAL_POINT must come after setHAlign() (ALIGN_DECIMAL)
453 string decimal_point = fromqstr(decimalPointED->text());
454 if (decimal_point.empty())
455 decimal_point = lyxrc.default_decimal_point;
456 setParam(param_str, Tabular::SET_DECIMAL_POINT, decimal_point);
458 setVAlign(param_str);
459 setTableAlignment(param_str);
461 if (booktabsRB->isChecked())
462 setParam(param_str, Tabular::SET_BOOKTABS);
464 setParam(param_str, Tabular::UNSET_BOOKTABS);
467 switch (topspaceCO->currentIndex()) {
469 setParam(param_str, Tabular::SET_TOP_SPACE, "none");
472 setParam(param_str, Tabular::SET_TOP_SPACE, "default");
475 if (!topspaceED->text().isEmpty())
476 setParam(param_str, Tabular::SET_TOP_SPACE,
477 widgetsToLength(topspaceED, topspaceUnitLC));
482 switch (bottomspaceCO->currentIndex()) {
484 setParam(param_str, Tabular::SET_BOTTOM_SPACE, "none");
487 setParam(param_str, Tabular::SET_BOTTOM_SPACE, "default");
490 if (!bottomspaceED->text().isEmpty())
491 setParam(param_str, Tabular::SET_BOTTOM_SPACE,
492 widgetsToLength(bottomspaceED,
498 switch (interlinespaceCO->currentIndex()) {
500 setParam(param_str, Tabular::SET_INTERLINE_SPACE, "none");
503 setParam(param_str, Tabular::SET_INTERLINE_SPACE, "default");
506 if (!interlinespaceED->text().isEmpty())
507 setParam(param_str, Tabular::SET_INTERLINE_SPACE,
508 widgetsToLength(interlinespaceED,
509 interlinespaceUnitLC));
514 if (borders->getTop() && borders->getBottom() && borders->getLeft()
515 && borders->getRight())
516 setParam(param_str, Tabular::SET_ALL_LINES);
517 else if (!borders->getTop() && !borders->getBottom() && !borders->getLeft()
518 && !borders->getRight())
519 setParam(param_str, Tabular::UNSET_ALL_LINES);
521 setParam(param_str, Tabular::SET_LINE_LEFT,
522 borders->getLeft() ? "true" : "false");
523 setParam(param_str, Tabular::SET_LINE_RIGHT,
524 borders->getRight() ? "true" : "false");
525 setParam(param_str, Tabular::SET_LINE_TOP,
526 borders->getTop() ? "true" : "false");
527 setParam(param_str, Tabular::SET_LINE_BOTTOM,
528 borders->getBottom() ? "true" : "false");
531 // apply the special alignment
532 string special = fromqstr(specialAlignmentED->text());
535 if (multicolumnCB->isChecked())
536 setParam(param_str, Tabular::SET_SPECIAL_MULTICOLUMN, special);
538 setParam(param_str, Tabular::SET_SPECIAL_COLUMN, special);
541 if (multicolumnCB->isChecked())
542 setParam(param_str, Tabular::SET_MULTICOLUMN);
544 setParam(param_str, Tabular::UNSET_MULTICOLUMN);
546 // apply the multirow offset
547 string mroffset = widgetsToLength(multirowOffsetED, multirowOffsetUnitLC);
548 if (mroffset.empty())
550 if (multirowCB->isChecked())
551 setParam(param_str, Tabular::SET_MROFFSET, mroffset);
553 if (multirowCB->isChecked())
554 setParam(param_str, Tabular::SET_MULTIROW);
556 setParam(param_str, Tabular::UNSET_MULTIROW);
558 if (rotateTabularCB->isChecked())
559 setParam(param_str, Tabular::SET_ROTATE_TABULAR);
561 setParam(param_str, Tabular::UNSET_ROTATE_TABULAR);
563 if (rotateCellCB->isChecked())
564 setParam(param_str, Tabular::SET_ROTATE_CELL);
566 setParam(param_str, Tabular::UNSET_ROTATE_CELL);
568 if (longTabularCB->isChecked())
569 setParam(param_str, Tabular::SET_LONGTABULAR);
571 setParam(param_str, Tabular::UNSET_LONGTABULAR);
573 if (newpageCB->isChecked())
574 setParam(param_str, Tabular::SET_LTNEWPAGE);
576 if (captionStatusCB->isChecked())
577 setParam(param_str, Tabular::SET_LTCAPTION);
579 setParam(param_str, Tabular::UNSET_LTCAPTION);
581 if (headerStatusCB->isChecked())
582 setParam(param_str, Tabular::SET_LTHEAD, "none");
584 setParam(param_str, Tabular::UNSET_LTHEAD, "none");
586 if (headerBorderAboveCB->isChecked())
587 setParam(param_str, Tabular::SET_LTHEAD, "dl_above");
589 setParam(param_str, Tabular::UNSET_LTHEAD, "dl_above");
591 if (headerBorderBelowCB->isChecked())
592 setParam(param_str, Tabular::SET_LTHEAD, "dl_below");
594 setParam(param_str, Tabular::UNSET_LTHEAD, "dl_below");
595 if (firstheaderBorderAboveCB->isChecked())
596 setParam(param_str, Tabular::SET_LTFIRSTHEAD, "dl_above");
598 setParam(param_str, Tabular::UNSET_LTFIRSTHEAD, "dl_above");
599 if (firstheaderBorderBelowCB->isChecked())
600 setParam(param_str, Tabular::SET_LTFIRSTHEAD, "dl_below");
602 setParam(param_str, Tabular::UNSET_LTFIRSTHEAD, "dl_below");
603 if (firstheaderStatusCB->isChecked())
604 setParam(param_str, Tabular::SET_LTFIRSTHEAD, "none");
606 setParam(param_str, Tabular::UNSET_LTFIRSTHEAD, "none");
607 if (firstheaderNoContentsCB->isChecked())
608 setParam(param_str, Tabular::SET_LTFIRSTHEAD, "empty");
610 setParam(param_str, Tabular::UNSET_LTFIRSTHEAD, "empty");
611 if (footerStatusCB->isChecked())
612 setParam(param_str, Tabular::SET_LTFOOT, "none");
614 setParam(param_str, Tabular::UNSET_LTFOOT, "none");
615 if (footerBorderAboveCB->isChecked())
616 setParam(param_str, Tabular::SET_LTFOOT, "dl_above");
618 setParam(param_str, Tabular::UNSET_LTFOOT, "dl_above");
619 if (footerBorderBelowCB->isChecked())
620 setParam(param_str, Tabular::SET_LTFOOT, "dl_below");
622 setParam(param_str, Tabular::UNSET_LTFOOT, "dl_below");
623 if (lastfooterStatusCB->isChecked())
624 setParam(param_str, Tabular::SET_LTLASTFOOT, "none");
626 setParam(param_str, Tabular::UNSET_LTLASTFOOT, "none");
627 if (lastfooterBorderAboveCB->isChecked())
628 setParam(param_str, Tabular::SET_LTLASTFOOT, "dl_above");
630 setParam(param_str, Tabular::UNSET_LTLASTFOOT, "dl_above");
631 if (lastfooterBorderBelowCB->isChecked())
632 setParam(param_str, Tabular::SET_LTLASTFOOT, "dl_below");
634 setParam(param_str, Tabular::UNSET_LTLASTFOOT, "dl_below");
635 if (lastfooterNoContentsCB->isChecked())
636 setParam(param_str, Tabular::SET_LTLASTFOOT, "empty");
638 setParam(param_str, Tabular::UNSET_LTLASTFOOT, "empty");
640 if (leftRB->isChecked())
641 setParam(param_str, Tabular::LONGTABULAR_ALIGN_LEFT);
642 else if (centerRB->isChecked())
643 setParam(param_str, Tabular::LONGTABULAR_ALIGN_CENTER);
644 else if (rightRB->isChecked())
645 setParam(param_str, Tabular::LONGTABULAR_ALIGN_RIGHT);
647 return from_utf8(param_str);
651 static Length getColumnPWidth(Tabular const & t, size_t cell)
653 return t.column_info[t.cellColumn(cell)].p_width;
657 static Length getMColumnPWidth(Tabular const & t, size_t cell)
659 if (t.isMultiColumn(cell) || t.isMultiRow(cell))
660 return t.cellInfo(cell).p_width;
665 static Length getMROffset(Tabular const & t, size_t cell)
667 if (t.isMultiRow(cell))
668 return t.cellInfo(cell).mroffset;
673 static docstring getAlignSpecial(Tabular const & t, size_t cell, int what)
675 if (what == Tabular::SET_SPECIAL_MULTICOLUMN)
676 return t.cellInfo(cell).align_special;
677 return t.column_info[t.cellColumn(cell)].align_special;
681 void GuiTabular::paramsToDialog(Inset const * inset)
683 InsetTabular const * itab = static_cast<InsetTabular const *>(inset);
684 // Copy Tabular of current inset.
685 Tabular const & tabular = itab->tabular;
687 BufferView const * bv = guiApp->currentView()->currentBufferView();
688 size_t const cell = bv->cursor().idx();
690 Tabular::row_type const row = tabular.cellRow(cell);
691 Tabular::col_type const col = tabular.cellColumn(cell);
693 tabularRowED->setText(QString::number(row + 1));
694 tabularColumnED->setText(QString::number(col + 1));
696 bool const multicol = tabular.isMultiColumn(cell);
697 multicolumnCB->setChecked(multicol);
699 bool const multirow = tabular.isMultiRow(cell);
700 multirowCB->setChecked(multirow);
702 rotateCellCB->setChecked(tabular.getRotateCell(cell));
703 rotateTabularCB->setChecked(tabular.rotate);
705 longTabularCB->setChecked(tabular.is_long_tabular);
707 borders->setTop(tabular.topLine(cell));
708 borders->setBottom(tabular.bottomLine(cell));
709 borders->setLeft(tabular.leftLine(cell));
710 borders->setRight(tabular.rightLine(cell));
711 // repaint the setborder widget
714 Length::UNIT const default_unit = Length::defaultUnit();
716 ///////////////////////////////////
717 // Set width and alignment
719 Length const tabwidth = tabular.tabularWidth();
721 tabularWidthED->clear();
723 lengthToWidgets(tabularWidthED, tabularWidthUnitLC,
724 tabwidth.asString(), default_unit);
729 special = getAlignSpecial(tabular, cell,
730 Tabular::SET_SPECIAL_MULTICOLUMN);
731 pwidth = getMColumnPWidth(tabular, cell);
733 special = getAlignSpecial(tabular, cell,
734 Tabular::SET_SPECIAL_COLUMN);
735 pwidth = getColumnPWidth(tabular, cell);
739 columnWidthED->clear();
741 colwidth = pwidth.asString();
742 lengthToWidgets(columnWidthED, columnWidthUnitLC,
743 colwidth, default_unit);
747 mroffset = getMROffset(tabular, cell);
750 multirowOffsetED->clear();
752 offset = mroffset.asString();
753 lengthToWidgets(multirowOffsetED, multirowOffsetUnitLC,
754 offset, default_unit);
756 specialAlignmentED->setText(toqstr(special));
757 ///////////////////////////////////
760 borderDefaultRB->setChecked(!tabular.use_booktabs);
761 booktabsRB->setChecked(tabular.use_booktabs);
763 if (tabular.row_info[row].top_space.empty()
764 && !tabular.row_info[row].top_space_default) {
765 topspaceCO->setCurrentIndex(0);
766 } else if (tabular.row_info[row].top_space_default) {
767 topspaceCO->setCurrentIndex(1);
769 topspaceCO->setCurrentIndex(2);
770 lengthToWidgets(topspaceED,
772 tabular.row_info[row].top_space.asString(),
776 if (tabular.row_info[row].bottom_space.empty()
777 && !tabular.row_info[row].bottom_space_default) {
778 bottomspaceCO->setCurrentIndex(0);
779 } else if (tabular.row_info[row].bottom_space_default) {
780 bottomspaceCO->setCurrentIndex(1);
782 bottomspaceCO->setCurrentIndex(2);
783 lengthToWidgets(bottomspaceED,
785 tabular.row_info[row].bottom_space.asString(),
789 if (tabular.row_info[row].interline_space.empty()
790 && !tabular.row_info[row].interline_space_default) {
791 interlinespaceCO->setCurrentIndex(0);
792 } else if (tabular.row_info[row].interline_space_default) {
793 interlinespaceCO->setCurrentIndex(1);
795 interlinespaceCO->setCurrentIndex(2);
796 lengthToWidgets(interlinespaceED,
797 interlinespaceUnitLC,
798 tabular.row_info[row].interline_space.asString(),
803 hAlignCO->addItem(qt_("Left"), toqstr("left"));
804 hAlignCO->addItem(qt_("Center"), toqstr("center"));
805 hAlignCO->addItem(qt_("Right"), toqstr("right"));
806 if (!multicol && !pwidth.zero())
807 hAlignCO->addItem(qt_("Justified"), toqstr("justified"));
809 hAlignCO->addItem(qt_("At Decimal Separator"), toqstr("decimal"));
812 switch (tabular.getAlignment(cell)) {
816 case LYX_ALIGN_CENTER:
819 case LYX_ALIGN_RIGHT:
822 case LYX_ALIGN_BLOCK:
824 if (!multicol && !pwidth.zero())
828 case LYX_ALIGN_DECIMAL:
835 // we should never end up here
838 hAlignCO->setCurrentIndex(hAlignCO->findData(toqstr(align)));
841 QString decimal_point = toqstr(tabular.column_info[col].decimal_point);
842 if (decimal_point.isEmpty())
843 decimal_point = toqstr(from_utf8(lyxrc.default_decimal_point));
844 decimalPointED->setText(decimal_point);
847 switch (tabular.getVAlignment(cell)) {
848 case Tabular::LYX_VALIGN_TOP:
851 case Tabular::LYX_VALIGN_MIDDLE:
854 case Tabular::LYX_VALIGN_BOTTOM:
863 vAlignCO->setCurrentIndex(valign);
866 switch (tabular.tabular_valignment) {
867 case Tabular::LYX_VALIGN_TOP:
870 case Tabular::LYX_VALIGN_MIDDLE:
873 case Tabular::LYX_VALIGN_BOTTOM:
880 TableAlignCO->setCurrentIndex(tableValign);
882 if (!tabular.is_long_tabular) {
883 headerStatusCB->setChecked(false);
884 headerBorderAboveCB->setChecked(false);
885 headerBorderBelowCB->setChecked(false);
886 firstheaderStatusCB->setChecked(false);
887 firstheaderBorderAboveCB->setChecked(false);
888 firstheaderBorderBelowCB->setChecked(false);
889 firstheaderNoContentsCB->setChecked(false);
890 footerStatusCB->setChecked(false);
891 footerBorderAboveCB->setChecked(false);
892 footerBorderBelowCB->setChecked(false);
893 lastfooterStatusCB->setChecked(false);
894 lastfooterBorderAboveCB->setChecked(false);
895 lastfooterBorderBelowCB->setChecked(false);
896 lastfooterNoContentsCB->setChecked(false);
897 newpageCB->setChecked(false);
898 captionStatusCB->blockSignals(true);
899 captionStatusCB->setChecked(false);
900 captionStatusCB->blockSignals(false);
904 // longtables cannot have a vertical alignment
905 TableAlignCO->setCurrentIndex(Tabular::LYX_VALIGN_MIDDLE);
907 switch (tabular.longtabular_alignment) {
908 case Tabular::LYX_LONGTABULAR_ALIGN_LEFT:
909 leftRB->setChecked(true);
911 case Tabular::LYX_LONGTABULAR_ALIGN_CENTER:
912 centerRB->setChecked(true);
914 case Tabular::LYX_LONGTABULAR_ALIGN_RIGHT:
915 rightRB->setChecked(true);
918 centerRB->setChecked(true);
921 captionStatusCB->blockSignals(true);
922 captionStatusCB->setChecked(tabular.ltCaption(row));
923 captionStatusCB->blockSignals(false);
927 bool row_set = tabular.getRowOfLTHead(row, ltt);
928 headerStatusCB->setChecked(row_set);
930 headerBorderAboveCB->setChecked(ltt.topDL);
931 headerBorderBelowCB->setChecked(ltt.bottomDL);
934 headerBorderAboveCB->setChecked(false);
935 headerBorderBelowCB->setChecked(false);
936 firstheaderNoContentsCB->setChecked(false);
940 row_set = tabular.getRowOfLTFirstHead(row, ltt);
941 firstheaderStatusCB->setChecked(row_set);
942 if (ltt.set && (!ltt.empty || !use_empty)) {
943 firstheaderBorderAboveCB->setChecked(ltt.topDL);
944 firstheaderBorderBelowCB->setChecked(ltt.bottomDL);
946 firstheaderBorderAboveCB->setChecked(false);
947 firstheaderBorderBelowCB->setChecked(false);
950 row_set = tabular.getRowOfLTFoot(row, ltt);
951 footerStatusCB->setChecked(row_set);
953 footerBorderAboveCB->setChecked(ltt.topDL);
954 footerBorderBelowCB->setChecked(ltt.bottomDL);
957 footerBorderAboveCB->setChecked(false);
958 footerBorderBelowCB->setChecked(false);
959 lastfooterNoContentsCB->setChecked(false);
963 row_set = tabular.getRowOfLTLastFoot(row, ltt);
964 lastfooterStatusCB->setChecked(row_set);
965 if (ltt.set && (!ltt.empty || !use_empty)) {
966 lastfooterBorderAboveCB->setChecked(ltt.topDL);
967 lastfooterBorderBelowCB->setChecked(ltt.bottomDL);
969 lastfooterBorderAboveCB->setChecked(false);
970 lastfooterBorderBelowCB->setChecked(false);
972 newpageCB->setChecked(tabular.getLTNewPage(row));
974 // first header can only be suppressed when there is a header
975 firstheader_suppressable_ = tabular.haveLTHead()
976 && !tabular.haveLTFirstHead();
977 // last footer can only be suppressed when there is a footer
978 lastfooter_suppressable_ = tabular.haveLTFoot()
979 && !tabular.haveLTLastFoot();
981 // after setting the features, check if they are enabled
986 bool GuiTabular::funcEnabled(Tabular::Feature f) const
988 string cmd = "tabular " + featureAsString(f);
989 return getStatus(FuncRequest(LFUN_INSET_MODIFY, cmd)).enabled();
993 } // namespace frontend
996 #include "moc_GuiTabular.cpp"