commit 9dcb24d578cfc9df5b70bbf3f13a95cd63ac3213
Author: Juergen Spitzmueller <[email protected]>
Date: Sun Jul 1 19:18:38 2018 +0200
Support varwidth's V tabular column type
This effectively enables linebreaks, multipars and layout changes in
non-fixed width (i.e., standard) table columns.
Fixes: #6577
TODO: metrics are wrong (too wide) on screen with linebreaks.
---
development/FORMAT | 5 +
lib/doc/LaTeXConfig.lyx | 31 +++++++-
lib/lyx2lyx/lyx_2_4.py | 112 ++++++++++++++++++++++++--
src/TextMetrics.cpp | 5 +-
src/TextMetrics.h | 3 +-
src/insets/InsetTabular.cpp | 189 ++++++++++++++++++++++++++++++++-----------
src/insets/InsetTabular.h | 31 +++++---
src/tex2lyx/TODO.txt | 1 +
src/version.h | 4 +-
9 files changed, 307 insertions(+), 74 deletions(-)
diff --git a/development/FORMAT b/development/FORMAT
index 1a160e0..ef3d7f8 100644
--- a/development/FORMAT
+++ b/development/FORMAT
@@ -7,6 +7,11 @@ changes happened in particular if possible. A good example
would be
-----------------------
+2018-07-01 Jürgen Spitzmüller <[email protected]>
+ * format incremented to 555: Support varwidth's V tabular column type.
+ This effectively enables linebreaks, multipars and layout changes in
+ non-fixed width (i.e., standard) table columns.
+
2018-06-23 Jürgen Spitzmüller <[email protected]>
* format incremented to 554: Support tabularx and xltabular:
- add column flag "varwidth=true", which will output column type 'X'
diff --git a/lib/doc/LaTeXConfig.lyx b/lib/doc/LaTeXConfig.lyx
index 341e273..e20623e 100644
--- a/lib/doc/LaTeXConfig.lyx
+++ b/lib/doc/LaTeXConfig.lyx
@@ -5431,6 +5431,35 @@ varioref
the page of the referred label.
\end_layout
+\begin_layout Subsubsection
+varwidth
+\end_layout
+
+\begin_layout Description
+Found:
+\begin_inset Info
+type "package"
+arg "varwidth"
+\end_inset
+
+
+\end_layout
+
+\begin_layout Description
+CTAN:
+\family typewriter
+macros/latex/contrib/varwidth/
+\end_layout
+
+\begin_layout Description
+Notes: The package
+\family sans
+varwidth
+\family default
+\color none
+ is needed to allow for line and paragraph breaks in standard tabular columns.
+\end_layout
+
\begin_layout Subsection
xltabular
\end_layout
@@ -6750,7 +6779,7 @@ Notes: The package
varwidth
\family default
\color none
- is used to produce minipages variable (i.
+ is used to produce minipages of variable (i.
\begin_inset space \thinspace{}
\end_inset
diff --git a/lib/lyx2lyx/lyx_2_4.py b/lib/lyx2lyx/lyx_2_4.py
index 32c6c33..9b388aa 100644
--- a/lib/lyx2lyx/lyx_2_4.py
+++ b/lib/lyx2lyx/lyx_2_4.py
@@ -24,14 +24,14 @@ import sys, os
# Uncomment only what you need to import, please.
-from parser_tools import (find_end_of_inset, find_end_of_layout, find_token,
-get_bool_value, get_value, get_quoted_value)
+from parser_tools import (count_pars_in_inset, find_end_of_inset,
find_end_of_layout,
+find_token, get_bool_value, get_option_value, get_value, get_quoted_value)
# del_token, del_value, del_complete_lines,
# find_complete_lines, find_end_of,
# find_re, find_substring, find_token_backwards,
# get_containing_inset, get_containing_layout,
# is_in_inset, set_bool_value
-# find_tokens, find_token_exact, check_token, get_option_value
+# find_tokens, find_token_exact, check_token
from lyx2lyx_tools import (put_cmd_in_ert, add_to_preamble)
# revert_font_attrs, insert_to_preamble, latex_length
@@ -118,15 +118,15 @@ def revert_paratype(document):
document.header[i1] =
document.header[i1].replace("PTSerif-TLF", "default")
if j!= -1:
if sfoption != "":
- add_to_preamble(document, ["\\usepackage[" + sfoption +
"]{PTSans}"])
+ add_to_preamble(document, ["\\usepackage[" + sfoption +
"]{PTSans}"])
else:
- add_to_preamble(document, ["\\usepackage{PTSans}"])
+ add_to_preamble(document, ["\\usepackage{PTSans}"])
document.header[j] = document.header[j].replace("PTSans-TLF",
"default")
if k!= -1:
if ttoption != "":
- add_to_preamble(document, ["\\usepackage[" + ttoption +
"]{PTMono}"])
+ add_to_preamble(document, ["\\usepackage[" + ttoption +
"]{PTMono}"])
else:
- add_to_preamble(document, ["\\usepackage{PTMono}"])
+ add_to_preamble(document, ["\\usepackage{PTMono}"])
document.header[k] = document.header[k].replace("PTMono-TLF",
"default")
@@ -345,6 +345,100 @@ def revert_stretchcolumn(document):
i = i + 1
+def revert_vcolumns(document):
+ " Revert standard columns with line breaks etc. "
+ i = 0
+ needvarwidth = False
+ needarray = False
+ try:
+ while True:
+ i = find_token(document.body, "\\begin_inset Tabular", i)
+ if i == -1:
+ return
+ j = find_end_of_inset(document.body, i)
+ if j == -1:
+ document.warning("Malformed LyX document: Could not find end
of tabular.")
+ i += 1
+ continue
+
+ # Collect necessary column information
+ m = i + 1
+ nrows = int(document.body[i+1].split('"')[3])
+ ncols = int(document.body[i+1].split('"')[5])
+ col_info = []
+ for k in range(ncols):
+ m = find_token(document.body, "<column", m)
+ width = get_option_value(document.body[m], 'width')
+ varwidth = get_option_value(document.body[m], 'varwidth')
+ alignment = get_option_value(document.body[m], 'alignment')
+ special = get_option_value(document.body[m], 'special')
+ col_info.append([width, varwidth, alignment, special, m])
+
+ # Now parse cells
+ m = i + 1
+ lines = []
+ for row in range(nrows):
+ for col in range(ncols):
+ m = find_token(document.body, "<cell", m)
+ multicolumn = get_option_value(document.body[m],
'multicolumn')
+ multirow = get_option_value(document.body[m], 'multirow')
+ width = get_option_value(document.body[m], 'width')
+ rotate = get_option_value(document.body[m], 'rotate')
+ # Check for: linebreaks, multipars, non-standard
environments
+ begcell = m
+ endcell = find_token(document.body, "</cell>", begcell)
+ vcand = False
+ if find_token(document.body, "\\begin_inset Newline",
begcell, endcell) != -1:
+ vcand = True
+ elif count_pars_in_inset(document.body, begcell + 2) > 1:
+ vcand = True
+ elif get_value(document.body, "\\begin_layout", begcell)
!= "Plain Layout":
+ vcand = True
+ if vcand and rotate == "" and ((multicolumn == "" and
multirow == "") or width == ""):
+ if col_info[col][0] == "" and col_info[col][1] == ""
and col_info[col][3] == "":
+ needvarwidth = True
+ alignment = col_info[col][2]
+ col_line = col_info[col][4]
+ vval = ""
+ if alignment == "center":
+ vval = ">{\\centering}"
+ elif alignment == "left":
+ vval = ">{\\raggedright}"
+ elif alignment == "right":
+ vval = ">{\\raggedleft}"
+ if vval != "":
+ needarray = True
+ vval += "V{\\linewidth}"
+
+ document.body[col_line] =
document.body[col_line][:-1] + " special=\"" + vval + "\">"
+ # ERT newlines and linebreaks (since LyX < 2.4
automatically inserts parboxes
+ # with newlines, and we do not want that)
+ while True:
+ endcell = find_token(document.body, "</cell>",
begcell)
+ linebreak = False
+ nl = find_token(document.body, "\\begin_inset
Newline newline", begcell, endcell)
+ if nl == -1:
+ nl = find_token(document.body,
"\\begin_inset Newline linebreak", begcell, endcell)
+ if nl == -1:
+ break
+ linebreak = True
+ nle = find_end_of_inset(document.body, nl)
+ del(document.body[nle:nle+1])
+ if linebreak:
+ document.body[nl:nl+1] =
put_cmd_in_ert("\\linebreak{}")
+ else:
+ document.body[nl:nl+1] =
put_cmd_in_ert("\\\\")
+ m += 1
+
+ i = j + 1
+
+ finally:
+ if needarray == True:
+ add_to_preamble(document, ["\\usepackage{array}"])
+ if needvarwidth == True:
+ add_to_preamble(document, ["\\usepackage{varwidth}"])
+
+
##
# Conversion hub
#
@@ -360,10 +454,12 @@ convert = [
[551, []],
[552, []],
[553, []],
- [554, []]
+ [554, []],
+ [555, []]
]
revert = [
+ [554, [revert_vcolumns]],
[553, [revert_stretchcolumn]],
[552, [revert_tuftecite]],
[551, [revert_floatpclass, revert_floatalignment]],
diff --git a/src/TextMetrics.cpp b/src/TextMetrics.cpp
index 98e3483..5035187 100644
--- a/src/TextMetrics.cpp
+++ b/src/TextMetrics.cpp
@@ -160,7 +160,8 @@ ParagraphMetrics & TextMetrics::parMetrics(pit_type pit,
bool redo)
}
-bool TextMetrics::metrics(MetricsInfo & mi, Dimension & dim, int min_width)
+bool TextMetrics::metrics(MetricsInfo & mi, Dimension & dim, int min_width,
+ bool const expand_on_multipars)
{
LBUFERR(mi.base.textwidth > 0);
max_width_ = mi.base.textwidth;
@@ -170,7 +171,7 @@ bool TextMetrics::metrics(MetricsInfo & mi, Dimension &
dim, int min_width)
dim_ = Dimension();
dim_.wid = min_width;
pit_type const npar = text_->paragraphs().size();
- if (npar > 1)
+ if (npar > 1 && expand_on_multipars)
// If there is more than one row, expand the text to
// the full allowable width.
dim_.wid = max_width_;
diff --git a/src/TextMetrics.h b/src/TextMetrics.h
index 369f07a..6802488 100644
--- a/src/TextMetrics.h
+++ b/src/TextMetrics.h
@@ -55,7 +55,8 @@ public:
/// compute text metrics.
- bool metrics(MetricsInfo & mi, Dimension & dim, int min_width = 0);
+ bool metrics(MetricsInfo & mi, Dimension & dim, int min_width = 0,
+ bool const expand_on_multipars = true);
///
void newParMetricsDown();
diff --git a/src/insets/InsetTabular.cpp b/src/insets/InsetTabular.cpp
index afdd3d7..a25f4d6 100644
--- a/src/insets/InsetTabular.cpp
+++ b/src/insets/InsetTabular.cpp
@@ -917,8 +917,11 @@ void Tabular::updateIndexes()
// reset column and row of cells and update their width and alignment
for (row_type row = 0; row < nrows(); ++row)
for (col_type column = 0; column < ncols(); ++column) {
- if (isPartOfMultiColumn(row, column))
+ if (isPartOfMultiColumn(row, column)) {
+
cell_info[row][column].inset->toggleMultiCol(true);
continue;
+ }
+ cell_info[row][column].inset->toggleMultiCol(false);
// columnofcell needs to be called before setting width
and aligment
// multirow cells inherit the width from the column
width
if (!isPartOfMultiRow(row, column)) {
@@ -926,8 +929,11 @@ void Tabular::updateIndexes()
rowofcell[i] = row;
}
setFixedWidth(row, column);
- if (isPartOfMultiRow(row, column))
+ if (isPartOfMultiRow(row, column)) {
+
cell_info[row][column].inset->toggleMultiRow(true);
continue;
+ }
+ cell_info[row][column].inset->toggleMultiRow(false);
cell_info[row][column].inset->setContentAlignment(
getAlignment(cellIndex(row, column)));
++i;
@@ -1130,14 +1136,16 @@ void Tabular::setVAlignment(idx_type cell, VAlignment
align,
namespace {
/**
- * Allow line and paragraph breaks for fixed width cells or disallow them,
- * merge cell paragraphs and reset layout to standard for variable width
- * cells.
+ * Allow line and paragraph breaks for fixed width multicol/multirow cells
+ * or disallow them, merge cell paragraphs and reset layout to standard
+ * for variable width multicol cells.
*/
-void toggleFixedWidth(Cursor & cur, InsetTableCell * inset, bool fixedWidth)
+void toggleFixedWidth(Cursor & cur, InsetTableCell * inset,
+ bool const fixedWidth, bool const multicol,
+ bool const multirow)
{
inset->toggleFixedWidth(fixedWidth);
- if (fixedWidth)
+ if (!multirow && (fixedWidth || !multicol))
return;
// merge all paragraphs to one
@@ -1145,6 +1153,19 @@ void toggleFixedWidth(Cursor & cur, InsetTableCell *
inset, bool fixedWidth)
while (inset->paragraphs().size() > 1)
mergeParagraph(bp, inset->paragraphs(), 0);
+ // This is relevant for multirows
+ if (fixedWidth)
+ return;
+
+ // remove newlines
+ ParagraphList::iterator pit = inset->paragraphs().begin();
+ for (; pit != inset->paragraphs().end(); ++pit) {
+ for (pos_type j = 0; j != pit->size(); ++j) {
+ if (pit->isNewline(j))
+ pit->eraseChar(j, bp.track_changes);
+ }
+ }
+
// reset layout
cur.push(*inset);
// undo information has already been recorded
@@ -1171,16 +1192,13 @@ void Tabular::setColumnPWidth(Cursor & cur, idx_type
cell,
idx_type const cidx = cellIndex(r, c);
// because of multicolumns
toggleFixedWidth(cur, cellInset(cidx).get(),
- !getPWidth(cidx).zero());
+ !getPWidth(cidx).zero(), isMultiColumn(cidx),
+ isMultiRow(cidx));
if (isMultiRow(cidx))
setAlignment(cidx, LYX_ALIGN_LEFT, false);
}
- // cur paragraph can become invalid after paragraphs were merged
- if (cur.pit() > cur.lastpit())
- cur.pit() = cur.lastpit();
- // cur position can become invalid after newlines were removed
- if (cur.pos() > cur.lastpos())
- cur.pos() = cur.lastpos();
+ // cur can become invalid after paragraphs were merged
+ cur.fixIfBroken();
}
@@ -1201,13 +1219,10 @@ bool Tabular::setMColumnPWidth(Cursor & cur, idx_type
cell,
return false;
cellInfo(cell).p_width = width;
- toggleFixedWidth(cur, cellInset(cell).get(), !width.zero());
- // cur paragraph can become invalid after paragraphs were merged
- if (cur.pit() > cur.lastpit())
- cur.pit() = cur.lastpit();
- // cur position can become invalid after newlines were removed
- if (cur.pos() > cur.lastpos())
- cur.pos() = cur.lastpos();
+ toggleFixedWidth(cur, cellInset(cell).get(), !width.zero(),
+ isMultiColumn(cell), isMultiRow(cell));
+ // cur can become invalid after paragraphs were merged
+ cur.fixIfBroken();
return true;
}
@@ -1717,6 +1732,16 @@ bool Tabular::hasVarwidthColumn() const
}
+bool Tabular::isVTypeColumn(col_type c) const
+{
+ for (row_type r = 0; r < nrows(); ++r) {
+ idx_type idx = cellIndex(r, c);
+ if (getRotateCell(idx) == 0 && useBox(idx) == BOX_VARWIDTH)
+ return true;
+ }
+ return false;
+}
+
Tabular::CellData const & Tabular::cellInfo(idx_type cell) const
{
@@ -1730,7 +1755,7 @@ Tabular::CellData & Tabular::cellInfo(idx_type cell)
}
-Tabular::idx_type Tabular::setMultiColumn(idx_type cell, idx_type number,
+Tabular::idx_type Tabular::setMultiColumn(Cursor & cur, idx_type cell,
idx_type number,
bool const right_border)
{
idx_type const col = cellColumn(cell);
@@ -1745,6 +1770,14 @@ Tabular::idx_type Tabular::setMultiColumn(idx_type cell,
idx_type number,
if (column_info[col].alignment != LYX_ALIGN_DECIMAL)
cs.alignment = column_info[col].alignment;
setRightLine(cell, right_border);
+ // non-fixed width multicolumns cannot have multiple paragraphs
+ if (getPWidth(cell).zero()) {
+ toggleFixedWidth(cur, cellInset(cell).get(),
+ !getPWidth(cell).zero(), isMultiColumn(cell),
+ isMultiRow(cell));
+ // cur can become invalid after paragraphs were merged
+ cur.fixIfBroken();
+ }
idx_type lastcell = cellIndex(row, col + number - 1);
for (idx_type i = 1; i < lastcell - cell + 1; ++i) {
@@ -1773,7 +1806,7 @@ bool Tabular::hasMultiRow(row_type r) const
return false;
}
-Tabular::idx_type Tabular::setMultiRow(idx_type cell, idx_type number,
+Tabular::idx_type Tabular::setMultiRow(Cursor & cur, idx_type cell, idx_type
number,
bool const bottom_border,
LyXAlignment const halign)
{
@@ -1796,6 +1829,15 @@ Tabular::idx_type Tabular::setMultiRow(idx_type cell,
idx_type number,
else
cs.alignment = LYX_ALIGN_LEFT;
+ // Multirows cannot have multiple paragraphs
+ if (getPWidth(cell).zero()) {
+ toggleFixedWidth(cur, cellInset(cell).get(),
+ !getPWidth(cell).zero(),
+ isMultiColumn(cell), isMultiRow(cell));
+ // cur can become invalid after paragraphs were merged
+ cur.fixIfBroken();
+ }
+
// set the bottom line of the last selected cell
setBottomLine(cell, bottom_border);
@@ -1949,7 +1991,7 @@ Tabular::BoxType Tabular::getUsebox(idx_type cell) const
return BOX_NONE;
if (cellInfo(cell).usebox > 1)
return cellInfo(cell).usebox;
- return useParbox(cell);
+ return useBox(cell);
}
@@ -2078,11 +2120,11 @@ bool Tabular::haveLTLastFoot(bool withcaptions) const
}
-Tabular::idx_type Tabular::setLTCaption(row_type row, bool what)
+Tabular::idx_type Tabular::setLTCaption(Cursor & cur, row_type row, bool what)
{
idx_type i = getFirstCellInRow(row);
if (what) {
- setMultiColumn(i, numberOfCellsInRow(row), false);
+ setMultiColumn(cur, i, numberOfCellsInRow(row), false);
setTopLine(i, false);
setBottomLine(i, false);
setLeftLine(i, false);
@@ -2490,7 +2532,7 @@ void Tabular::TeXCellPreamble(otexstream & os, idx_type
cell,
}
os << "]{" << from_ascii(getPWidth(cell).asLatexString())
<< "}\n";
- } else if (getUsebox(cell) == BOX_VARWIDTH) {
+ } else if (getRotateCell(cell) != 0 && getUsebox(cell) == BOX_VARWIDTH)
{
os << "\\begin{varwidth}[";
switch (valign) {
case LYX_VALIGN_TOP:
@@ -2520,7 +2562,7 @@ void Tabular::TeXCellPostamble(otexstream & os, idx_type
cell,
os << '}';
else if (getUsebox(cell) == BOX_MINIPAGE)
os << breakln << "\\end{minipage}";
- else if (getUsebox(cell) == BOX_VARWIDTH)
+ else if (getRotateCell(cell) != 0 && getUsebox(cell) == BOX_VARWIDTH)
os << breakln << "\\end{varwidth}";
if (getRotateCell(cell) != 0)
os << breakln << "\\end{turn}";
@@ -2964,6 +3006,25 @@ void Tabular::latex(otexstream & os, OutputParams const
& runparams) const
break;
}
os << 'X';
+ } else if (isVTypeColumn(c)) {
+ switch (column_info[c].alignment) {
+ case LYX_ALIGN_LEFT:
+ os << ">{\\raggedright}";
+ break;
+ case LYX_ALIGN_RIGHT:
+ os << ">{\\raggedleft}";
+ break;
+ case LYX_ALIGN_CENTER:
+ os << ">{\\centering}";
+ break;
+ case LYX_ALIGN_NONE:
+ case LYX_ALIGN_BLOCK:
+ case LYX_ALIGN_LAYOUT:
+ case LYX_ALIGN_SPECIAL:
+ case LYX_ALIGN_DECIMAL:
+ break;
+ }
+ os << "V{\\linewidth}";
} else {
switch (column_info[c].alignment) {
case LYX_ALIGN_LEFT:
@@ -3588,7 +3649,8 @@ void Tabular::validate(LaTeXFeatures & features) const
if (getUsebox(cell) == BOX_VARWIDTH)
features.require("varwidth");
if (getVAlignment(cell) != LYX_VALIGN_TOP
- || !getPWidth(cell).zero())
+ || !getPWidth(cell).zero()
+ || isVTypeColumn(cellColumn(cell)))
features.require("array");
// Tell footnote that we need a savenote
// environment in non-long tables or
@@ -3604,17 +3666,19 @@ void Tabular::validate(LaTeXFeatures & features) const
}
-Tabular::BoxType Tabular::useParbox(idx_type cell) const
+Tabular::BoxType Tabular::useBox(idx_type cell) const
{
ParagraphList const & parlist = cellInset(cell)->paragraphs();
+ if (parlist.size() > 1)
+ return BOX_VARWIDTH;
+
ParagraphList::const_iterator cit = parlist.begin();
ParagraphList::const_iterator end = parlist.end();
- bool const turned = getRotateCell(cell) != 0;
for (; cit != end; ++cit)
for (int i = 0; i < cit->size(); ++i)
- if (cit->isNewline(i))
- return turned ? BOX_VARWIDTH : BOX_PARBOX;
+ if (cit->isNewline(i) || cit->layout().isEnvironment())
+ return BOX_VARWIDTH;
return BOX_NONE;
}
@@ -3628,13 +3692,13 @@ Tabular::BoxType Tabular::useParbox(idx_type cell) const
InsetTableCell::InsetTableCell(Buffer * buf)
: InsetText(buf, InsetText::PlainLayout), isFixedWidth(false),
- contentAlign(LYX_ALIGN_CENTER)
+ isMultiColumn(false), isMultiRow(false),
contentAlign(LYX_ALIGN_CENTER)
{}
bool InsetTableCell::forcePlainLayout(idx_type) const
{
- return !isFixedWidth;
+ return isMultiRow || (isMultiColumn && !isFixedWidth);
}
@@ -3701,6 +3765,34 @@ docstring InsetTableCell::xhtml(XHTMLStream & xs,
OutputParams const & rp) const
}
+void InsetTableCell::metrics(MetricsInfo & mi, Dimension & dim) const
+{
+ TextMetrics & tm = mi.base.bv->textMetrics(&text());
+
+ // Hand font through to contained lyxtext:
+ tm.font_.fontInfo() = mi.base.font;
+ mi.base.textwidth -= 2 * TEXT_TO_INSET_OFFSET;
+
+ // This can happen when a layout has a left and right margin,
+ // and the view is made very narrow. We can't do better than
+ // to draw it partly out of view (bug 5890).
+ if (mi.base.textwidth < 1)
+ mi.base.textwidth = 1;
+
+ // We tell metrics here not to expand on multiple pars
+ // This is the difference to InsetText::Metrics
+ // FIXME: pars with newlines are still too wide!
+ if (hasFixedWidth())
+ tm.metrics(mi, dim, mi.base.textwidth, false);
+ else
+ tm.metrics(mi, dim, 0, false);
+ mi.base.textwidth += 2 * TEXT_TO_INSET_OFFSET;
+ dim.asc += TEXT_TO_INSET_OFFSET;
+ dim.des += TEXT_TO_INSET_OFFSET;
+ dim.wid += 2 * TEXT_TO_INSET_OFFSET;
+}
+
+
/////////////////////////////////////////////////////////////////////
//
@@ -3921,8 +4013,7 @@ void InsetTabular::metrics(MetricsInfo & mi, Dimension &
dim) const
}
-bool InsetTabular::isCellSelected(Cursor & cur, row_type row, col_type col)
- const
+bool InsetTabular::isCellSelected(Cursor & cur, row_type row, col_type col)
const
{
if (&cur.inset() == this && cur.selection()) {
if (cur.selIsMultiCell()) {
@@ -5190,13 +5281,13 @@ bool InsetTabular::getStatus(Cursor & cur, FuncRequest
const & cmd,
return true;
}
// fall through
- case LFUN_NEWLINE_INSERT: {
- if (tabular.getPWidth(cur.idx()).zero()) {
+ case LFUN_NEWLINE_INSERT:
+ if ((tabular.isMultiColumn(cur.idx()) ||
tabular.isMultiRow(cur.idx()))
+ && tabular.getPWidth(cur.idx()).zero()) {
status.setEnabled(false);
return true;
- } else
- return cell(cur.idx())->getStatus(cur, cmd, status);
- }
+ }
+ return cell(cur.idx())->getStatus(cur, cmd, status);
case LFUN_NEWPAGE_INSERT:
status.setEnabled(false);
@@ -5863,7 +5954,7 @@ void InsetTabular::tabularFeatures(Cursor & cur,
// just multicol for one single cell
// check whether we are completely in a multicol
if (!tabular.isMultiColumn(cur.idx()))
- tabular.setMultiColumn(cur.idx(), 1,
+ tabular.setMultiColumn(cur, cur.idx(), 1,
tabular.rightLine(cur.idx()));
break;
}
@@ -5872,7 +5963,7 @@ void InsetTabular::tabularFeatures(Cursor & cur,
idx_type const s_start = cur.selBegin().idx();
row_type const col_start = tabular.cellColumn(s_start);
row_type const col_end = tabular.cellColumn(cur.selEnd().idx());
- cur.idx() = tabular.setMultiColumn(s_start, col_end - col_start
+ 1,
+ cur.idx() = tabular.setMultiColumn(cur, s_start, col_end -
col_start + 1,
tabular.rightLine(cur.selEnd().idx()));
cur.pit() = 0;
cur.pos() = 0;
@@ -5918,7 +6009,7 @@ void InsetTabular::tabularFeatures(Cursor & cur,
// just multirow for one single cell
// check whether we are completely in a multirow
if (!tabular.isMultiRow(cur.idx()))
- tabular.setMultiRow(cur.idx(), 1,
+ tabular.setMultiRow(cur, cur.idx(), 1,
tabular.bottomLine(cur.idx()),
tabular.getAlignment(cur.idx()));
break;
@@ -5928,7 +6019,7 @@ void InsetTabular::tabularFeatures(Cursor & cur,
idx_type const s_start = cur.selBegin().idx();
row_type const row_start = tabular.cellRow(s_start);
row_type const row_end = tabular.cellRow(cur.selEnd().idx());
- cur.idx() = tabular.setMultiRow(s_start, row_end - row_start +
1,
+ cur.idx() = tabular.setMultiRow(cur, s_start, row_end -
row_start + 1,
tabular.bottomLine(cur.selEnd().idx()),
tabular.getAlignment(cur.selEnd().idx()));
cur.pit() = 0;
@@ -6141,7 +6232,7 @@ void InsetTabular::tabularFeatures(Cursor & cur,
case Tabular::SET_LTCAPTION: {
if (tabular.ltCaption(row))
break;
- cur.idx() = tabular.setLTCaption(row, true);
+ cur.idx() = tabular.setLTCaption(cur, row, true);
cur.pit() = 0;
cur.pos() = 0;
cur.selection(false);
@@ -6157,7 +6248,7 @@ void InsetTabular::tabularFeatures(Cursor & cur,
case Tabular::UNSET_LTCAPTION: {
if (!tabular.ltCaption(row))
break;
- cur.idx() = tabular.setLTCaption(row, false);
+ cur.idx() = tabular.setLTCaption(cur, row, false);
cur.pit() = 0;
cur.pos() = 0;
cur.selection(false);
@@ -6457,7 +6548,7 @@ bool InsetTabular::allowParagraphCustomization(idx_type
cell) const
bool InsetTabular::forcePlainLayout(idx_type cell) const
{
- return !tabular.getPWidth(cell).zero();
+ return tabular.isMultiColumn(cell) && !tabular.getPWidth(cell).zero();
}
diff --git a/src/insets/InsetTabular.h b/src/insets/InsetTabular.h
index cd25c4e..b915181 100644
--- a/src/insets/InsetTabular.h
+++ b/src/insets/InsetTabular.h
@@ -63,6 +63,10 @@ public:
///
void toggleFixedWidth(bool fw) { isFixedWidth = fw; }
///
+ void toggleMultiCol(bool m) { isMultiColumn = m; }
+ ///
+ void toggleMultiRow(bool m) { isMultiRow = m; }
+ ///
void setContentAlignment(LyXAlignment al) {contentAlign = al; }
/// writes the contents of the cell as a string, optionally
/// descending into insets
@@ -72,14 +76,17 @@ public:
///
void addToToc(DocIterator const & di, bool output_active,
UpdateType utype, TocBackend & backend) const;
+ ///
+ void metrics(MetricsInfo &, Dimension &) const;
private:
/// unimplemented
InsetTableCell();
/// unimplemented
void operator=(InsetTableCell const &);
// FIXME
- // This boolean is supposed to track whether the cell has had its
- // width explicitly set. We need to know this to determine whether
+ // These booleans are supposed to track whether the cell has had its
+ // width explicitly set and whether it is part of a multicolumn,
respectively.
+ // We need to know this to determine whether
// layout changes and paragraph customization are allowed---that is,
// we need it in forcePlainLayout() and allowParagraphCustomization().
// Unfortunately, that information is not readily available in
@@ -102,6 +109,10 @@ private:
// --rgh
///
bool isFixedWidth;
+ ///
+ bool isMultiColumn;
+ ///
+ bool isMultiRow;
// FIXME: Here the thoughts from the comment above also apply.
///
LyXAlignment contentAlign;
@@ -120,11 +131,7 @@ private:
/// Is the width forced to some value?
bool hasFixedWidth() const { return isFixedWidth; }
/// Can the cell contain several paragraphs?
- /** FIXME this is wrong for multirows, that are limited to one
- * paragraph. However, we cannot test for this (see the big
- * comment above).
- */
- bool allowMultiPar() const { return isFixedWidth; }
+ bool allowMultiPar() const { return !isMultiRow && (!isMultiColumn ||
isFixedWidth); }
};
@@ -534,7 +541,9 @@ public:
///
bool hasVarwidthColumn() const;
///
- idx_type setMultiColumn(idx_type cell, idx_type number,
+ bool isVTypeColumn(col_type cell) const;
+ ///
+ idx_type setMultiColumn(Cursor & cur, idx_type cell, idx_type number,
bool const right_border);
///
void unsetMultiColumn(idx_type cell);
@@ -547,7 +556,7 @@ public:
///
bool hasMultiRow(row_type r) const;
///
- idx_type setMultiRow(idx_type cell, idx_type number,
+ idx_type setMultiRow(Cursor & cur, idx_type cell, idx_type number,
bool const bottom_border,
LyXAlignment const halign);
///
@@ -595,7 +604,7 @@ public:
///
bool getLTNewPage(row_type row) const;
///
- idx_type setLTCaption(row_type row, bool what);
+ idx_type setLTCaption(Cursor & cur, row_type row, bool what);
///
bool ltCaption(row_type row) const;
///
@@ -804,7 +813,7 @@ public:
///
idx_type rowSpan(idx_type cell) const;
///
- BoxType useParbox(idx_type cell) const;
+ BoxType useBox(idx_type cell) const;
///
// helper function for Latex
///
diff --git a/src/tex2lyx/TODO.txt b/src/tex2lyx/TODO.txt
index d55dae0..d93b5fa 100644
--- a/src/tex2lyx/TODO.txt
+++ b/src/tex2lyx/TODO.txt
@@ -59,6 +59,7 @@ Format LaTeX feature LyX feature
546 Landscape support
\begin{landscape}...\end{landscape} \begin_inset Flex Landscape
with longtable content: <features rotate ="90"...>
+555 V column type (varwidth package) Automatically detected with
newlines, paragraph breaks and environment content in cells of rows
diff --git a/src/version.h b/src/version.h
index 1020e3e..ba838b4 100644
--- a/src/version.h
+++ b/src/version.h
@@ -32,8 +32,8 @@ extern char const * const lyx_version_info;
// Do not remove the comment below, so we get merge conflict in
// independent branches. Instead add your own.
-#define LYX_FORMAT_LYX 554 // spitz: tabularx/xltabular
-#define LYX_FORMAT_TEX2LYX 554
+#define LYX_FORMAT_LYX 555 // spitz: varwidth V columns
+#define LYX_FORMAT_TEX2LYX 555
#if LYX_FORMAT_TEX2LYX != LYX_FORMAT_LYX
#ifndef _MSC_VER