]> git.lyx.org Git - lyx.git/blobdiff - src/table.C
Baruch's graphic-inset patch.
[lyx.git] / src / table.C
index 5156e53ba78d6d1f1d779aa11fa8fabce2c1f1a6..e9972a7e7bbc56f5053f885508dcf54246c3b549 100644 (file)
 
 #include <config.h>
 
-#include <cstdlib>
-#include "table.h"
-#include "vspace.h"
-#include "layout.h"
-#include "support/lstrings.h"
 #include <algorithm>
-using std::max;
+#include <cstdlib>
 
 #ifdef __GNUG__
 #pragma implementation
 #endif
 
-#ifdef USE_OSTREAM_ONLY
+#include "table.h"
+#include "debug.h"
+#include "vspace.h"
+#include "layout.h"
+#include "support/lstrings.h"
 #include "support/lyxmanip.h"
-#else
-extern void addNewlineAndDepth(string & file, int depth); // Jug 990923
-#endif
+#include "support/LAssert.h"
+#include "lyx_gui_misc.h"
+
+using std::ostream;
+using std::istream;
+using std::getline;
+using std::max;
+using std::endl;
 
 static int const WIDTH_OF_LINE = 5;
 
+/// Define a few methods for the inner structs
+
+LyXTable::cellstruct::cellstruct() 
+{
+       cellno = 0; //should be initilaized correctly later.
+       width_of_cell = 0;
+       multicolumn = LyXTable::CELL_NORMAL;
+       alignment = LYX_ALIGN_CENTER;
+       top_line = true;
+       bottom_line = false;
+       has_cont_row = false;
+       rotate = false;
+       linebreaks = false;
+}
+
+LyXTable::cellstruct::~cellstruct() 
+{
+}
+
+LyXTable::cellstruct & 
+  LyXTable::cellstruct::operator=(cellstruct const & cs)
+{
+       cellno = cs.cellno;
+       width_of_cell = cs.width_of_cell;
+       multicolumn = cs.multicolumn;
+       alignment = cs.alignment;
+       top_line = cs.top_line;
+       bottom_line = cs.bottom_line;
+       has_cont_row = cs.has_cont_row;
+       rotate = cs.rotate;
+       linebreaks = cs.linebreaks;
+       return *this;
+}
+
+LyXTable::rowstruct::rowstruct() 
+{
+       top_line = true;
+       bottom_line = false;
+       is_cont_row = false;
+       ascent_of_row = 0;
+       descent_of_row = 0;
+       newpage = false;
+}
+
+// Nothing to do, but gcc 2.7.2.3 wants one... (JMarc)
+LyXTable::rowstruct::~rowstruct() 
+{
+}
+
+LyXTable::rowstruct & 
+  LyXTable::rowstruct::operator=(rowstruct const & rs)
+{
+       top_line = rs.top_line;
+       bottom_line = rs.bottom_line;
+       is_cont_row = rs.is_cont_row;
+       ascent_of_row = rs.ascent_of_row;
+       descent_of_row = rs.descent_of_row;
+       newpage = rs.newpage;
+       return *this;
+}
+
+LyXTable::columnstruct::columnstruct() 
+{
+        left_line = true;
+        right_line = false;
+        alignment = LYX_ALIGN_CENTER;
+        width_of_column = 0;
+}
+
+LyXTable::columnstruct::~columnstruct() 
+{
+}
+
+LyXTable::columnstruct & 
+  LyXTable::columnstruct::operator=(columnstruct const & cs)
+{
+        left_line = cs.left_line;
+        right_line = cs.right_line;
+        alignment = cs.alignment;
+        width_of_column = cs.width_of_column;
+       p_width = cs.p_width;
+       align_special = cs.align_special;
+       return *this;
+}
+
 /* konstruktor */
 LyXTable::LyXTable(int rows_arg, int columns_arg)
 {
-       Init(rows_arg, columns_arg);
+    Init(rows_arg, columns_arg);
 }
 
 
+LyXTable::LyXTable(LyXTable const & lt)
+{
+    Init(lt.rows, lt.columns);
+    
+    operator=(lt);
+}
+
 LyXTable::LyXTable(LyXLex & lex)
 {
-       istream & is = lex.getStream();
-       Read(is);
+    istream & is = lex.getStream();
+    Read(is);
 }
 
 
-LyXTable::~LyXTable() {
-       delete[] rowofcell;
-       delete[] columnofcell;
-       delete[] column_info;
-        delete[] row_info;
-       for (int i = 0; i < rows; ++i) {
-               delete[] cell_info[i]; // verify that this shoudn't be freed with delete
-       }
-       delete[] cell_info;
+LyXTable::~LyXTable()
+{
+    delete[] rowofcell;
+    delete[] columnofcell;
+    delete[] column_info;
+    delete[] row_info;
+    for (int i = 0; i < rows; ++i) {
+       delete[] cell_info[i];
+    }
+    delete[] cell_info;
 }
 
 
+LyXTable & LyXTable::operator=(LyXTable const & lt)
+{
+    // If this and lt is not of the same size we have a serious bug
+    // So then it is ok to throw an exception, or for now
+    // call abort()
+    Assert(rows == lt.rows && columns == lt.columns);
+
+    int row = 0, column = 0;
+    
+    for (row = 0; row < rows; ++row) {
+        for (column = 0; column < columns; ++column) {
+            cell_info[row][column] = lt.cell_info[row][column];
+        }
+    }
+    
+    for (row = 0; row < rows; ++row) {
+        row_info[row] = lt.row_info[row];
+    }
+    
+    for (column = 0; column < columns; ++column) {
+       column_info[column] = lt.column_info[column];
+    }
+
+    SetLongTable(lt.is_long_table);
+    rotate = lt.rotate;
+    Reinit();
+    
+    return *this;
+}
+
 LyXTable * LyXTable::Clone()
 {
     LyXTable * result = new LyXTable(rows, columns);
-    int row, column;;
+    int row, column;
 
     for (row = 0; row < rows; ++row) {
         for (column = 0; column < columns; ++column) {
@@ -100,32 +227,14 @@ void LyXTable::Init(int rows_arg, int columns_arg)
     int cellno = 0;
     for (i = 0; i < rows; ++i) {
         cell_info[i] = new cellstruct[columns];
-        row_info[i].top_line = true;
-        row_info[i].bottom_line = false;
-        row_info[i].is_cont_row = false;
-        row_info[i].newpage = false;
         for (j = 0; j < columns; ++j) {
             cell_info[i][j].cellno = cellno++;
-            cell_info[i][j].width_of_cell = 0;
-            cell_info[i][j].multicolumn = LyXTable::CELL_NORMAL;
-            cell_info[i][j].alignment = LYX_ALIGN_CENTER;
-            cell_info[i][j].top_line = row_info[i].top_line;
-            cell_info[i][j].bottom_line = row_info[i].bottom_line;
-            cell_info[i][j].has_cont_row = false;
-            cell_info[i][j].rotate = false;
-            cell_info[i][j].linebreaks = false;
         }
     }
     row_info[i-1].bottom_line = true;
     row_info[0].bottom_line = true;
 
     for (i = 0; i < columns; ++i) {
-        column_info[i].left_line = true;
-        column_info[i].right_line = false;
-        column_info[i].alignment = LYX_ALIGN_CENTER;
-        // set width_of_column to zero before it is used in
-        // calculate_width_of_column() (thornley)
-        column_info[i].width_of_column = 0;
         calculate_width_of_column(i);
     }
     column_info[i-1].right_line = true;
@@ -778,7 +887,7 @@ void LyXTable::calculate_width_of_table()
 }
 
 
-int LyXTable::row_of_cell(int cell) 
+int LyXTable::row_of_cell(int cell) const
 {
     if (cell >= numberofcells)
         return rows-1;
@@ -788,7 +897,7 @@ int LyXTable::row_of_cell(int cell)
 }
 
 
-int LyXTable::column_of_cell(int cell)
+int LyXTable::column_of_cell(int cell) const
 {
     if (cell >= numberofcells)
         return columns-1;
@@ -809,29 +918,30 @@ int LyXTable::right_column_of_cell(int cell)
 }
 
 
-void LyXTable::Write(ostream & os)
+void LyXTable::Write(ostream & os, bool old_format)
 {
-    int i, j;
-    os << "multicol5\n"
-       << rows << " " << columns << " " << is_long_table << " "
-       << rotate << " " << endhead << " " << endfirsthead << " "
-       << endfoot << " " << endlastfoot << "\n";
-    for (i = 0; i < rows; ++i) {
+    if (old_format) {
+       int i, j;
+       os << "multicol5\n"
+          << rows << " " << columns << " " << is_long_table << " "
+          << rotate << " " << endhead << " " << endfirsthead << " "
+          << endfoot << " " << endlastfoot << "\n";
+       for (i = 0; i < rows; ++i) {
            os << row_info[i].top_line << " "
               << row_info[i].bottom_line << " "
               << row_info[i].is_cont_row << " "
               << row_info[i].newpage << "\n";
-    }
-    for (i = 0; i < columns; ++i) {
+       }
+       for (i = 0; i < columns; ++i) {
            os << column_info[i].alignment << " "
               << column_info[i].left_line << " "
               << column_info[i].right_line << " \""
               << VSpace(column_info[i].p_width).asLyXCommand() << "\" \""
               << column_info[i].align_special << "\"\n";
-    }
+       }
 
-    for (i = 0; i < rows; ++i) {
-        for (j = 0; j < columns; ++j) {
+       for (i = 0; i < rows; ++i) {
+           for (j = 0; j < columns; ++j) {
                os << cell_info[i][j].multicolumn << " "
                   << cell_info[i][j].alignment << " "
                   << cell_info[i][j].top_line << " "
@@ -841,7 +951,10 @@ void LyXTable::Write(ostream & os)
                   << cell_info[i][j].linebreaks << " \""
                   << cell_info[i][j].align_special << "\" \""
                   << cell_info[i][j].p_width << "\"\n";
-        }
+           }
+       }
+    } else {
+       lyxerr << "New format type not yet implemented!!!\n" << endl;
     }
 }
 
@@ -864,18 +977,19 @@ void LyXTable::Read(istream & is)
        int h = 0;
        
        string s;
-       getline(is, s);
+       while(!s.length())
+           getline(is, s);
        if (s.length() > 8)
                version = atoi(s.c_str() + 8);
        else
                version = 1;
-#ifdef WITH_WARNINGS
-#warning Insert a error message window here that this format is not supported anymore
-#endif
        if (version < 5) {
                lyxerr << "Tabular format < 5 is not supported anymore\n"
                        "Get an older version of LyX (< 1.1.x) for conversion!"
                       << endl;
+               WriteAlert(_("Warning:"),
+                          _("Tabular format < 5 is not supported anymore\n"),
+                          _("Get an older version of LyX (< 1.1.x) for conversion!"));
                if (version > 2) {
                        is >> rows_arg >> columns_arg >> is_long_table_arg
                           >> rotate_arg >> a >> b >> c >> d;
@@ -956,7 +1070,6 @@ void LyXTable::Read(istream & is)
 }
 
 
-#ifdef USE_OSTREAM_ONLY
 // cell <0 will tex the preamble
 // returns the number of printed newlines
 int LyXTable::TexEndOfCell(ostream & os, int cell)
@@ -1255,8 +1368,8 @@ int LyXTable::TexEndOfCell(ostream & os, int cell)
                os << "\\multicolumn{"
                   << cells_in_multicolumn(nvcell)
                   << "}{";
-            if (!cellinfo_of_cell(cell+1)->align_special.empty()) {
-                   os << cellinfo_of_cell(cell+1)->align_special
+            if (!cellinfo_of_cell(nvcell)->align_special.empty()) {
+                   os << cellinfo_of_cell(nvcell)->align_special
                       << "}{";
             } else {
                 if (LeftLine(nvcell))
@@ -1285,350 +1398,13 @@ int LyXTable::TexEndOfCell(ostream & os, int cell)
             }
         }
         if (nvcell < numberofcells && Linebreaks(nvcell)) {
-//            !column_info[column_of_cell(nvcell)].p_width.empty()) {
-               os << "\\parbox{"
+               os << "\\parbox[t]{"
                   << GetPWidth(nvcell)
                   << "}{\\smallskip{}";
        }
     }
     return ret;
 }
-#else
-// cell <0 will tex the preamble
-// returns the number of printed newlines
-int LyXTable::TexEndOfCell(string & file, int cell)
-{
-    int i;
-    int ret = 0;
-    int tmp; // tmp2;
-    int fcell, nvcell;
-    if (ShouldBeVeryLastCell(cell)) {
-        // the very end at the very beginning
-        if (Linebreaks(cell))
-            file += "\\smallskip{}}";
-        if (IsMultiColumn(cell))
-            file += '}';
-        if (RotateCell(cell)) {
-            file += "\n\\end{sideways}";
-            ++ret;
-        }
-        file += "\\\\\n";
-        ++ret;
-    
-        tmp = 0;
-        fcell = cell; 
-        while (!IsFirstCell(fcell)) --fcell;
-        for (i = 0; i < NumberOfCellsInRow(fcell); ++i) {
-            if (BottomLine(fcell + i))
-                ++tmp;
-        }
-        if (tmp == NumberOfCellsInRow(fcell)) {
-            file += "\\hline ";
-        } else {
-            tmp = 0;
-            for (i = 0; i < NumberOfCellsInRow(fcell); ++i) {
-                if (BottomLine(fcell + i)) {
-                   file += "\\cline{";
-                   file += tostr(column_of_cell(fcell + i) + 1);
-                   file += '-';
-                   file += tostr(right_column_of_cell(fcell + i) + 1);
-                   file += "} ";
-                    tmp = 1;
-                }
-            }
-        }
-        if (tmp){
-            file += '\n';
-            ++ret;
-        }
-        if (is_long_table)
-            file += "\\end{longtable}";
-        else
-            file += "\\end{tabular}";
-        if (rotate) {
-            file += "\n\\end{sideways}";
-            ++ret;
-        }
-    } else {
-        nvcell = NextVirtualCell(cell + 1);
-        if (cell < 0){
-            // preamble
-            if (rotate) {
-                file += "\\begin{sideways}\n";
-                ++ret;
-            }
-            if (is_long_table)
-                file += "\\begin{longtable}{";
-            else
-                file += "\\begin{tabular}{";
-            for (i = 0; i < columns; ++i) {
-                if (column_info[i].left_line)
-                   file += '|';
-                if (!column_info[i].align_special.empty()) {
-                    file += column_info[i].align_special.c_str();
-                } else if (!column_info[i].p_width.empty()) {
-                    file += "p{";
-                    file += column_info[i].p_width;
-                    file += '}';
-                } else {
-                    switch (column_info[i].alignment) {
-                      case LYX_ALIGN_LEFT:
-                          file += 'l';
-                          break;
-                      case LYX_ALIGN_RIGHT:
-                          file += 'r';
-                          break;
-                      default:
-                          file += 'c';
-                          break;
-                    }
-                }
-                if (column_info[i].right_line)
-                    file += '|';
-            }
-            file += "}\n";
-            ++ret;
-            tmp = 0;
-            if (GetNumberOfCells()) {
-                fcell = 0;
-                for (i = 0; i < NumberOfCellsInRow(fcell); ++i) {
-                    if (TopLine(fcell + i))
-                        ++tmp;
-                }
-                if (tmp == NumberOfCellsInRow(fcell)){
-                    file += "\\hline ";
-                } else {
-                    tmp = 0;
-                    for (i = 0; i < NumberOfCellsInRow(fcell); ++i) {
-                        if (TopLine(fcell + i)) {
-                           file += "\\cline{";
-                           file += tostr(column_of_cell(fcell + i) + 1);
-                           file += '-';
-                           file += tostr(right_column_of_cell(fcell + i) + 1);
-                           file += "} ";
-                            tmp = 1;
-                        }
-                    }
-                }
-                if (tmp){
-                    file += '\n';
-                    ++ret;
-                }
-            }
-            if (RotateCell(0)) {
-                file += "\\begin{sideways}\n";
-                ++ret;
-            }
-        } else {
-            // usual cells
-            if (Linebreaks(cell))
-                file += "\\smallskip{}}";
-            if (IsMultiColumn(cell)){
-                file += '}';
-            }
-            if (RotateCell(cell)) {
-                file += "\n\\end{sideways}";
-                ++ret;
-            }
-            if (IsLastCell(cell)) {
-                int row = row_of_cell(cell);
-                string hline1, hline2;
-                bool print_hline = true;
-                bool flag1 = IsLongTable() &&
-                    ((row == endhead) || (row == endfirsthead) ||
-                     (row == endfoot) || (row == endlastfoot));
-                ++row;
-                bool flag2 = IsLongTable() &&
-                    ((row <= endhead) || (row <= endfirsthead) ||
-                     (row <= endfoot) || (row <= endlastfoot));
-                --row;
-                // print the bottom hline only if (otherwise it is doubled):
-                // - is no LongTable
-                // - there IS a first-header
-                // - the next row is no special header/footer
-                //   & this row is no special header/footer
-                // - the next row is a special header/footer
-                //   & this row is a special header/footer
-                bool pr_top_hline = (flag1 && flag2) || (!flag1 && !flag2) ||
-                    (endfirsthead == endhead);
-                file += "\\\\\n";
-                ++ret;
-                tmp = 0;
-                fcell = cell;
-                while (!IsFirstCell(fcell))
-                    --fcell;
-                for (i = 0; i < NumberOfCellsInRow(cell); ++i) {
-                    if (BottomLine(fcell + i))
-                        ++tmp;
-                }
-                if (tmp == NumberOfCellsInRow(cell)){
-                    file += "\\hline ";
-                    hline1 = "\\hline ";
-                } else {
-                    tmp = 0;
-                    for (i = 0; i < NumberOfCellsInRow(fcell); ++i) {
-                        if (BottomLine(fcell + i)){
-                            file += "\\cline{";
-                            file += tostr(column_of_cell(fcell + i) + 1);
-                            file += '-';
-                            file += tostr(right_column_of_cell(fcell + i) + 1);
-                            file += "} ";
-                            hline1 += "\\cline{";
-                            hline1 += tostr(column_of_cell(fcell + i) + 1);
-                            hline1 += '-';
-                            hline1 += tostr(right_column_of_cell(fcell + i) + 1);
-                            hline1 += "} ";
-                            tmp = 1;
-                        }
-                    }
-                }
-                if (tmp){
-                    file += '\n';
-                    ++ret;
-                }
-                if (IsLongTable() && (row == endfoot)) {
-                    file += "\\endfoot\n";
-                    ++ret;
-                    print_hline = false; // no double line below footer
-                }
-                if (IsLongTable() && (row == endlastfoot)) {
-                    file += "\\endlastfoot\n";
-                    ++ret;
-                    print_hline = false; // no double line below footer
-                }
-                if (IsLongTable() && row_info[row].newpage) {
-                    file += "\\newpage\n";
-                    ++ret;
-                    print_hline = false; // no line below a \\newpage-command
-                }
-                tmp = 0;
-                if (nvcell < numberofcells && (cell < GetNumberOfCells() - 1) &&
-                    !ShouldBeVeryLastCell(cell)) {
-                    fcell = nvcell;
-                    for (i = 0; i < NumberOfCellsInRow(fcell); ++i) {
-                        if (TopLine(fcell + i))
-                            ++tmp;
-                    }
-                    if (tmp == NumberOfCellsInRow(fcell)) {
-                        if (print_hline)
-                            file += "\\hline ";
-                        hline2 = "\\hline ";
-                    } else {
-                        tmp = 0;
-                        for (i = 0; i < NumberOfCellsInRow(fcell); ++i) {
-                            if (TopLine(fcell + i)) {
-                                if (print_hline) {
-                                   file += "\\cline{";
-                                   file += tostr(column_of_cell(fcell+i)+1);
-                                   file += '-';
-                                   file += tostr(right_column_of_cell(fcell+i)+1);
-                                   file += "} ";
-                               }
-                                hline2 += "\\cline{";
-                                hline2 += tostr(column_of_cell(fcell+i)+1);
-                                hline2 += '-';
-                                hline2 += tostr(right_column_of_cell(fcell+i)+1);
-                                hline2 += "} ";
-                                tmp = 1;
-                            }
-                        }
-                    }
-                    if (tmp && print_hline){
-                        file += '\n';
-                        ++ret;
-                    }
-                }
-                // the order here is important as if one defines two
-                // or more things in one line only the first entry is
-                // displayed the other are set to an empty-row. This
-                // is important if I have a footer and want that the
-                // lastfooter is NOT displayed!!!
-                bool sflag2 = (row == endhead) || (row == endfirsthead) ||
-                    (row == endfoot) || (row == endlastfoot);
-                --row;
-//                sflag2 = IsLongTable() && (row >= 0) &&
-//                    (sflag2 || (row == endhead) || (row == endfirsthead));
-                row += 2;
-                bool sflag1 = IsLongTable() && (row != endhead) &&
-                    (row != endfirsthead) &&
-                    ((row == endfoot) || (row == endlastfoot));
-                --row;
-                if (IsLongTable() && (row == endhead)) {
-                   file += "\\endhead\n";
-                    ++ret;
-                }
-                if (IsLongTable() && (row == endfirsthead)) {
-                    file += "\\endfirsthead\n";
-                    ++ret;
-                }
-                if (sflag1) { // add the \hline for next foot row
-                    if (!hline1.empty()) {
-                        file += hline1 + '\n';
-                        ++ret;
-                    }
-                }
-                // add the \hline for the first row
-                if (pr_top_hline && sflag2) {
-                    if (!hline2.empty()) {
-                        file += hline2 + '\n';
-                        ++ret;
-                    }
-                }
-                if (nvcell < numberofcells && RotateCell(nvcell)) {
-                    file += "\\begin{sideways}\n";
-                    ++ret;
-                }
-            } else {
-                file += "&\n";
-                ++ret;
-                if (nvcell < numberofcells && RotateCell(nvcell)) {
-                    file += "\\begin{sideways}\n";
-                    ++ret;
-                }
-            }
-        }
-        if (nvcell < numberofcells && IsMultiColumn(nvcell)) {
-            file += "\\multicolumn{";
-           file += tostr(cells_in_multicolumn(nvcell));
-           file += "}{";
-            if (!cellinfo_of_cell(cell+1)->align_special.empty()) {
-                file += cellinfo_of_cell(cell+1)->align_special;
-                file += "}{";
-            } else {
-                if (LeftLine(nvcell))
-                    file += '|';
-                if (!GetPWidth(nvcell).empty()) {
-                    file += "p{";
-                    file += GetPWidth(nvcell);
-                    file += '}';
-                } else {
-                    switch (GetAlignment(nvcell)) {
-                      case LYX_ALIGN_LEFT: file += 'l'; break;
-                      case LYX_ALIGN_RIGHT: file += 'r'; break;
-                      default:  file += 'c'; break;
-                    }
-                }
-                if (RightLine(nvcell))
-                    file += '|';
-                //if (column_of_cell(cell+2)!= 0 && LeftLine(cell+2))
-                if (((nvcell+1) < numberofcells) &&
-                    (NextVirtualCell(nvcell+1) < numberofcells) &&
-                    (column_of_cell(NextVirtualCell(nvcell+1))!= 0) &&
-                    LeftLine(NextVirtualCell(nvcell+1)))
-                    file += '|';
-                file += "}{";
-            }
-        }
-        if (nvcell < numberofcells && Linebreaks(nvcell)) {
-//            !column_info[column_of_cell(nvcell)].p_width.empty()) {
-            file += "\\parbox{";
-           file += GetPWidth(nvcell);
-           file += "}{\\smallskip{}";
-       }
-    }
-    return ret;
-}
-#endif
 
 
 #if 0
@@ -1772,10 +1548,9 @@ char const *LyXTable::getDocBookAlign(int cell, bool isColumn)
 }
 
 
-#ifdef USE_OSTREAM_ONLY
 // cell <0 will tex the preamble
 // returns the number of printed newlines
-int LyXTable::DocBookEndOfCell(ostream & os, int cell, int &depth)
+int LyXTable::DocBookEndOfCell(ostream & os, int cell, int & depth)
 {
     int i;
     int ret = 0;
@@ -1894,129 +1669,6 @@ int LyXTable::DocBookEndOfCell(ostream & os, int cell, int &depth)
     }
     return ret;
 }
-#else
-// cell <0 will tex the preamble
-// returns the number of printed newlines
-int LyXTable::DocBookEndOfCell(string & file, int cell, int &depth)
-{
-    int i;
-    int ret = 0;
-    //int tmp; // tmp2; // unused
-    int nvcell; // fcell; // unused
-    if (ShouldBeVeryLastCell(cell)) {
-       addNewlineAndDepth(file,--depth);
-        file += "</ENTRY>";
-       addNewlineAndDepth(file,--depth);
-        file += "</ROW>";
-       addNewlineAndDepth(file,--depth);
-        file += "</TBODY>";
-       addNewlineAndDepth(file,--depth);
-        if (is_long_table)
-            file += "</TGROUP>";
-        else
-            file += "</TGROUP>";
-       addNewlineAndDepth(file,--depth);
-        ret += 4;
-    } else {
-        nvcell = NextVirtualCell(cell+1);
-        if (cell < 0) {
-            // preamble
-            if (is_long_table)
-                file += "<TGROUP ";
-            else
-                file += "<TGROUP ";
-            file += "COLS='";
-            file += tostr(columns);
-            file += "' COLSEP='1' ROWSEP='1'>";
-           addNewlineAndDepth(file,++depth);
-            ++ret;
-            for (i = 0; i < columns; ++i) {
-                file += "<COLSPEC ALIGN='";
-               file += getDocBookAlign(i, true);
-               file += "' COLNAME='col";
-                file += tostr(i+1);
-                file += "' COLNUM='";
-                file += tostr(i+1);
-               file += "' COLSEP='";
-               if (i == (columns-1)) {
-                    file += '1';
-               } else {
-                   if (column_info[i].right_line ||
-                       column_info[i+1].left_line)
-                       file += '1';
-                   else
-                       file += '0';
-               }
-               file += "'>";
-               addNewlineAndDepth(file, depth);
-                ++ret;
-#ifdef NOT_HANDLED_YET_AS_I_DONT_KNOW_HOW
-                if (column_info[i].left_line)
-                    file += '|';
-#endif
-            }
-            file += "<TBODY>";
-           addNewlineAndDepth(file,++depth);
-            file += "<ROW>";
-           addNewlineAndDepth(file,++depth);
-            file += "<ENTRY ALIGN='";
-            file += getDocBookAlign(0);
-           file += "'";
-           if (IsMultiColumn(0)) {
-               file += " NAMEST='col1' NAMEEND='col";
-               file += tostr(cells_in_multicolumn(0));
-               file += "'";
-           }
-            file += ">";
-           addNewlineAndDepth(file,++depth);
-            ret += 3;
-        } else {
-            if (IsLastCell(cell)) {
-               addNewlineAndDepth(file,--depth);
-                file += "</ENTRY>";
-               addNewlineAndDepth(file,--depth);
-                file += "</ROW>";
-               addNewlineAndDepth(file, depth);
-               file += "<ROW>";
-               addNewlineAndDepth(file,++depth);
-                file += "<ENTRY ALIGN='";
-                file += getDocBookAlign(cell+1);
-                file += "' VALIGN='middle'";
-               if (IsMultiColumn(cell+1)) {
-                   file += " NAMEST='col";
-                   file += tostr(column_of_cell(cell+1) + 1);
-                   file += "' NAMEEND='col";
-                   file += tostr(column_of_cell(cell+1) +
-                       cells_in_multicolumn(cell+1));
-                   file += "'";
-               }
-               file += ">";
-               addNewlineAndDepth(file,++depth);
-                ret += 4;
-            } else {
-               addNewlineAndDepth(file,--depth);
-                file += "</ENTRY>";
-               addNewlineAndDepth(file, depth);
-                file += "<ENTRY ALIGN='";
-                file += getDocBookAlign(cell+1);
-                file += "' VALIGN='middle'";
-               if (IsMultiColumn(cell+1)) {
-                   file += " NAMEST='col";
-                   file += tostr(column_of_cell(cell+1) + 1);
-                   file += "' NAMEEND='col";
-                   file += tostr(column_of_cell(cell+1) +
-                       cells_in_multicolumn(cell+1));
-                   file += "'";
-               }
-               file += ">";
-               addNewlineAndDepth(file,++depth);
-                ret += 3;
-            }
-        }
-    }
-    return ret;
-}
-#endif
 
 
 bool LyXTable::IsMultiColumn(int cell)
@@ -2374,3 +2026,55 @@ bool LyXTable::LTNewPage(int cell)
 {
     return row_info[row_of_cell(cell)].newpage;
 }
+
+void LyXTable::SetAscentOfRow(int row, int height)
+{
+    if (row >= rows)
+        return;
+    row_info[row].ascent_of_row = height;
+}
+
+void LyXTable::SetDescentOfRow(int row, int height)
+{
+    if (row >= rows)
+        return;
+    row_info[row].descent_of_row = height;
+}
+
+int LyXTable::AscentOfRow(int row)
+{
+    if (row >= rows)
+        return 0;
+    return row_info[row].ascent_of_row;
+}
+
+int LyXTable::DescentOfRow(int row)
+{
+    if (row >= rows)
+        return 0;
+    return row_info[row].descent_of_row;
+}
+
+int LyXTable::HeightOfTable()
+{
+    int
+        height,
+        row;
+
+    for(row=0,height=0;(row<rows); ++row)
+        height += AscentOfRow(row) + DescentOfRow(row) +
+           AdditionalHeight(GetCellNumber(0,row));
+    return height;
+}
+
+bool LyXTable::IsPartOfMultiColumn(int row, int column)
+{
+    if ((row >= rows) || (column >= columns))
+        return false;
+    return (cell_info[row][column].multicolumn==CELL_PART_OF_MULTICOLUMN);
+}
+
+int LyXTable::Latex(ostream &)
+{
+    return 0;
+}