]> git.lyx.org Git - lyx.git/blobdiff - src/text.C
Point fix, earlier forgotten
[lyx.git] / src / text.C
index 714fce983818d6fb25e82b1780f67ebbab0ecfc7..b558bd680bd85cf59d01cf5ed6777ffc78bb4f77 100644 (file)
@@ -1,12 +1,18 @@
-/* This file is part of
- * ======================================================
+/**
+ * \file text.C
+ * This file is part of LyX, the document processor.
+ * Licence details can be found in the file COPYING.
  *
- *           LyX, The Document Processor
+ * \author Asger Alstrup
+ * \author Lars Gullik Bjønnes
+ * \author Jean-Marc Lasgouttes
+ * \author John Levon
+ * \author André Pönitz
+ * \author Dekel Tsur
+ * \author Jürgen Vigna
  *
- *           Copyright 1995 Matthias Ettrich
- *           Copyright 1995-2001 The LyX Team.
- *
- * ====================================================== */
+ * Full author contact details are available in file CREDITS.
+ */
 
 #include <config.h>
 
@@ -63,6 +69,8 @@ extern int const CHANGEBAR_MARGIN = 10;
 /// left margin
 extern int const LEFT_MARGIN = PAPER_MARGIN + CHANGEBAR_MARGIN;
 
+
+
 int bibitemMaxWidth(BufferView *, LyXFont const &);
 
 
@@ -82,61 +90,16 @@ BufferView * LyXText::bv() const
 
 void LyXText::updateRowPositions()
 {
-       RowList::iterator rit = rows().begin();
-       RowList::iterator rend = rows().end();
-       for (int y = 0; rit != rend ; ++rit) {
-               rit->y(y);
-               y += rit->height();
-       }
-}
-
-
-int LyXText::top_y() const
-{
-       if (anchor_row_ == rowlist_.end())
-               return 0;
-
-       return anchor_row_->y() + anchor_row_offset_;
-}
-
-
-void LyXText::top_y(int newy)
-{
-       if (rows().empty())
-               return;
-
-       if (isInInset()) {
-               anchor_row_ = rows().begin();
-               anchor_row_offset_ = newy;
-               return;
-       }
-
-       lyxerr[Debug::GUI] << "setting top y = " << newy << endl;
-
-       int y = newy;
-       RowList::iterator rit = getRowNearY(y);
-
-       if (rit == anchor_row_ && anchor_row_offset_ == newy - y) {
-               lyxerr[Debug::GUI] << "top_y to same value, skipping update" << endl;
-               return;
+       ParagraphList::iterator pit = ownerParagraphs().begin();
+       ParagraphList::iterator end = ownerParagraphs().end();
+       for (height = 0; pit != end; ++pit) {
+               RowList::iterator rit = pit->rows.begin();
+               RowList::iterator rend = pit->rows.end();
+               for ( ; rit != rend ; rit = ++rit) {
+                       rit->y(height);
+                       height += rit->height();
+               }
        }
-
-       anchor_row_ = rit;
-       anchor_row_offset_ = newy - y;
-       lyxerr[Debug::GUI] << "changing reference to row: " << &*anchor_row_
-              << " offset: " << anchor_row_offset_ << endl;
-}
-
-
-void LyXText::anchor_row(RowList::iterator rit)
-{
-       int old_y = top_y();
-       anchor_row_offset_ = 0;
-       anchor_row_ = rit;
-       anchor_row_offset_ = old_y - top_y();
-       lyxerr[Debug::GUI] << "anchor_row(): changing reference to row: "
-                          << &*anchor_row_ << " offset: "
-                          << anchor_row_offset_ << endl;
 }
 
 
@@ -224,17 +187,20 @@ int LyXText::singleWidth(ParagraphList::iterator pit, pos_type pos) const
                return 0;
 
        char const c = pit->getChar(pos);
-       return singleWidth(pit, pos, c);
+       LyXFont const & font = getFont(pit, pos);
+       return singleWidth(pit, pos, c, font);
 }
 
 
 int LyXText::singleWidth(ParagraphList::iterator pit,
-                        pos_type pos, char c) const
+                        pos_type pos, char c, LyXFont const & font) const
 {
-       if (pos >= pit->size())
+       if (pos >= pit->size()) {
+               lyxerr << "in singleWidth(), pos: " << pos << endl;
+               Assert(false);
                return 0;
+       }
 
-       LyXFont const & font = getFont(pit, pos);
 
        // The most common case is handled first (Asger)
        if (IsPrintable(c)) {
@@ -255,26 +221,12 @@ int LyXText::singleWidth(ParagraphList::iterator pit,
 
        if (c == Paragraph::META_INSET) {
                InsetOld * tmpinset = pit->getInset(pos);
-               if (tmpinset) {
-                       if (tmpinset->lyxCode() == InsetOld::HFILL_CODE) {
-                               // Because of the representation as vertical lines
-                               return 3;
-                       }
-#if 0
-#warning enabling this fixes the 'insets of width 0 on load' problem
-                       // this IS needed otherwise on initialitation we don't get the fill
-                       // of the row right (ONLY on initialization if we read a file!)
-                       // should be changed! (Jug 20011204)
-                       //tmpinset->update(bv());
-                       Dimension dim;
-                       MetricsInfo mi(bv(), font, workWidth());
-                       tmpinset->metrics(mi, dim);
-                       return dim.wid;
-#else
-                       return tmpinset->width();
-#endif
+               Assert(tmpinset);
+               if (tmpinset->lyxCode() == InsetOld::HFILL_CODE) {
+                       // Because of the representation as vertical lines
+                       return 3;
                }
-               return 0;
+               return tmpinset->width();
        }
 
        if (IsSeparatorChar(c))
@@ -317,8 +269,8 @@ bool LyXText::bidi_InRange(lyx::pos_type pos) const
 }
 
 
-void LyXText::computeBidiTables(ParagraphList::iterator row_par,
-   Buffer const * buf, RowList::iterator row) const
+void LyXText::computeBidiTables(ParagraphList::iterator pit,
+   Buffer const & buf, RowList::iterator row) const
 {
        bidi_same_direction = true;
        if (!lyxrc.rtl_support) {
@@ -326,7 +278,7 @@ void LyXText::computeBidiTables(ParagraphList::iterator row_par,
                return;
        }
 
-       InsetOld * inset = row_par->inInset();
+       InsetOld * inset = pit->inInset();
        if (inset && inset->owner() &&
            inset->owner()->lyxCode() == InsetOld::ERT_CODE) {
                bidi_start = -1;
@@ -334,7 +286,7 @@ void LyXText::computeBidiTables(ParagraphList::iterator row_par,
        }
 
        bidi_start = row->pos();
-       bidi_end = lastPrintablePos(*this, row_par, row);
+       bidi_end = lastPrintablePos(*pit, row);
 
        if (bidi_start > bidi_end) {
                bidi_start = -1;
@@ -356,25 +308,25 @@ void LyXText::computeBidiTables(ParagraphList::iterator row_par,
 
        pos_type stack[2];
        bool const rtl_par =
-               row_par->isRightToLeftPar(buf->params);
+               pit->isRightToLeftPar(buf.params);
        int level = 0;
        bool rtl = false;
        bool rtl0 = false;
-       pos_type const body_pos = row_par->beginningOfBody();
+       pos_type const body_pos = pit->beginningOfBody();
 
        for (pos_type lpos = bidi_start; lpos <= bidi_end; ++lpos) {
-               bool is_space = row_par->isLineSeparator(lpos);
+               bool is_space = pit->isLineSeparator(lpos);
                pos_type const pos =
                        (is_space && lpos + 1 <= bidi_end &&
-                        !row_par->isLineSeparator(lpos + 1) &&
-                        !row_par->isNewline(lpos + 1))
+                        !pit->isLineSeparator(lpos + 1) &&
+                        !pit->isNewline(lpos + 1))
                        ? lpos + 1 : lpos;
-               LyXFont font = row_par->getFontSettings(buf->params, pos);
+               LyXFont font = pit->getFontSettings(buf.params, pos);
                if (pos != lpos && 0 < lpos && rtl0 && font.isRightToLeft() &&
                    font.number() == LyXFont::ON &&
-                   row_par->getFontSettings(buf->params, lpos - 1).number()
+                   pit->getFontSettings(buf.params, lpos - 1).number()
                    == LyXFont::ON) {
-                       font = row_par->getFontSettings(buf->params, lpos);
+                       font = pit->getFontSettings(buf.params, lpos);
                        is_space = false;
                }
 
@@ -445,7 +397,7 @@ void LyXText::computeBidiTables(ParagraphList::iterator row_par,
 
 
 // This method requires a previous call to ComputeBidiTables()
-bool LyXText::isBoundary(Buffer const * buf, Paragraph const & par,
+bool LyXText::isBoundary(Buffer const & buf, Paragraph const & par,
                         pos_type pos) const
 {
        if (!lyxrc.rtl_support || pos == 0)
@@ -460,12 +412,12 @@ bool LyXText::isBoundary(Buffer const * buf, Paragraph const & par,
        bool const rtl = bidi_level(pos - 1) % 2;
        bool const rtl2 = bidi_InRange(pos)
                ? bidi_level(pos) % 2
-               : par.isRightToLeftPar(buf->params);
+               : par.isRightToLeftPar(buf.params);
        return rtl != rtl2;
 }
 
 
-bool LyXText::isBoundary(Buffer const * buf, Paragraph const & par,
+bool LyXText::isBoundary(Buffer const & buf, Paragraph const & par,
                         pos_type pos, LyXFont const & font) const
 {
        if (!lyxrc.rtl_support)
@@ -474,21 +426,13 @@ bool LyXText::isBoundary(Buffer const * buf, Paragraph const & par,
        bool const rtl = font.isVisibleRightToLeft();
        bool const rtl2 = bidi_InRange(pos)
                ? bidi_level(pos) % 2
-               : par.isRightToLeftPar(buf->params);
+               : par.isRightToLeftPar(buf.params);
        return rtl != rtl2;
 }
 
 
 int LyXText::leftMargin(ParagraphList::iterator pit, Row const & row) const
 {
-       InsetOld * ins;
-
-       if (row.pos() < pit->size())
-               if (pit->getChar(row.pos()) == Paragraph::META_INSET &&
-                   (ins = pit->getInset(row.pos())) &&
-                   (ins->needFullRow() || ins->display()))
-                       return LEFT_MARGIN;
-
        LyXTextClass const & tclass =
                bv()->buffer()->params.getLyXTextClass();
        LyXLayout_ptr const & layout = pit->layout();
@@ -605,8 +549,8 @@ int LyXText::leftMargin(ParagraphList::iterator pit, Row const & row) const
                // are *NOT* allowed in the LaTeX realisation of this layout.
 
                // find the first row of this paragraph
-               RowList::iterator rit = beginRow(pit);
-               RowList::iterator end = endRow(pit);
+               RowList::iterator rit = pit->rows.begin();
+               RowList::iterator end = pit->rows.end();
                int minfill = rit->fill();
                for ( ; rit != end; ++rit)
                        if (rit->fill() < minfill)
@@ -663,16 +607,8 @@ int LyXText::leftMargin(ParagraphList::iterator pit, Row const & row) const
 
 
 int LyXText::rightMargin(ParagraphList::iterator pit,
-       Buffer const & buf, Row const & row) const
+       Buffer const & buf, Row const &) const
 {
-       InsetOld * ins;
-
-       if (row.pos() < pit->size())
-               if ((pit->getChar(row.pos()) == Paragraph::META_INSET) &&
-                   (ins = pit->getInset(row.pos())) &&
-                   (ins->needFullRow() || ins->display()))
-                       return PAPER_MARGIN;
-
        LyXTextClass const & tclass = buf.params.getLyXTextClass();
        LyXLayout_ptr const & layout = pit->layout();
 
@@ -720,7 +656,8 @@ pos_type LyXText::rowBreakPoint(ParagraphList::iterator pit,
        Row const & row) const
 {
        // maximum pixel width of a row.
-       int width = workWidth() - rightMargin(pit, *bv()->buffer(), row);
+       int width = workWidth()
+               - rightMargin(pit, *bv()->buffer(), row);
 
        // inset->textWidth() returns -1 via workWidth(),
        // but why ?
@@ -749,7 +686,6 @@ pos_type LyXText::rowBreakPoint(ParagraphList::iterator pit,
 
        // pixel width since last breakpoint
        int chunkwidth = 0;
-       bool fullrow = false;
 
        pos_type i = pos;
 
@@ -764,6 +700,10 @@ pos_type LyXText::rowBreakPoint(ParagraphList::iterator pit,
                }
 
                char const c = pit->getChar(i);
+               if (i > endPosOfFontSpan) {
+                       font = getFont(pit, i);
+                       endPosOfFontSpan = pit->getEndPosOfFontSpan(i);
+               }
 
                int thiswidth;
 
@@ -775,43 +715,21 @@ pos_type LyXText::rowBreakPoint(ParagraphList::iterator pit,
                        int left_margin = labelEnd(pit, row);
                        if (thiswidth + x < left_margin)
                                thiswidth = left_margin - x;
-                       thiswidth += singleWidth(pit, i, c);
+                       thiswidth += singleWidth(pit, i, c, font);
                } else {
-                       // Manual inlined optimised version of common case of "thiswidth = singleWidth(pit, i, c);"
-                       if (IsPrintable(c)) {
-                               if (pos > endPosOfFontSpan) {
-                                       // We need to get the next font
-                                       font = getFont(pit, i);
-                                       endPosOfFontSpan = pit->getEndPosOfFontSpan(i);
-                               }
-                               if (! font.language()->RightToLeft()) {
-                                       thiswidth = font_metrics::width(c, font);
-                               } else {
-                                       // Fall-back to normal case
-                                       thiswidth = singleWidth(pit, i, c);
-                                       // And flush font cache
-                                       endPosOfFontSpan = 0;
-                               }
-                       } else {
-                               // Fall-back to normal case
-                               thiswidth = singleWidth(pit, i, c);
-                               // And flush font cache
-                               endPosOfFontSpan = 0;
-                       }
+                       thiswidth = singleWidth(pit, i, c, font);
                }
 
                x += thiswidth;
                chunkwidth += thiswidth;
 
                InsetOld * in = pit->isInset(i) ? pit->getInset(i) : 0;
-               fullrow = in && (in->display() || in->needFullRow());
 
                // break before a character that will fall off
                // the right of the row
                if (x >= width) {
-                       // if no break before or we are at an inset
-                       // that will take up a row, break here
-                       if (point == last || fullrow || chunkwidth >= (width - left)) {
+                       // if no break before, break here
+                       if (point == last || chunkwidth >= (width - left)) {
                                if (pos < i)
                                        point = i - 1;
                                else
@@ -829,24 +747,7 @@ pos_type LyXText::rowBreakPoint(ParagraphList::iterator pit,
                        continue;
                }
 
-               if (!fullrow)
-                       continue;
-
-               // full row insets start at a new row
-               if (i == pos) {
-                       if (pos < last - 1) {
-                               point = i;
-                               if (pit->isLineSeparator(i + 1))
-                                       ++point;
-                       } else {
-                               // to avoid extra rows
-                               point = last;
-                       }
-               } else {
-                       point = i - 1;
-               }
-
-               return point;
+               continue;
        }
 
        if (point == last && x >= width) {
@@ -861,7 +762,7 @@ pos_type LyXText::rowBreakPoint(ParagraphList::iterator pit,
        // manual labels cannot be broken in LaTeX. But we
        // want to make our on-screen rendering of footnotes
        // etc. still break
-       if (!fullrow && body_pos && point < body_pos)
+       if (body_pos && point < body_pos)
                point = body_pos - 1;
 
        return point;
@@ -877,7 +778,7 @@ int LyXText::fill(ParagraphList::iterator pit,
 
        int w;
        // get the pure distance
-       pos_type const last = lastPrintablePos(*this, pit, row);
+       pos_type const last = lastPrintablePos(*pit, row);
 
        LyXLayout_ptr const & layout = pit->layout();
 
@@ -906,30 +807,13 @@ int LyXText::fill(ParagraphList::iterator pit,
                                if (w < left_margin)
                                        w = left_margin;
                        }
-                       { // Manual inlined an optimised version of the common case of "w += singleWidth(pit, i);"
-                               char const c = pit->getChar(i);
-
-                               if (IsPrintable(c)) {
-                                       if (i > endPosOfFontSpan) {
-                                               // We need to get the next font
-                                               font = getFont(pit, i);
-                                               endPosOfFontSpan = pit->getEndPosOfFontSpan(i);
-                                       }
-                                       if (!font.language()->RightToLeft()) {
-                                               w += font_metrics::width(c, font);
-                                       } else {
-                                               // Fall-back to the normal case
-                                               w += singleWidth(pit, i, c);
-                                               // And flush font cache
-                                               endPosOfFontSpan = 0;
-                                       }
-                               } else {
-                                       // Fall-back to the normal case
-                                       w += singleWidth(pit, i, c);
-                                       // And flush font cache
-                                       endPosOfFontSpan = 0;
-                               }
+                       char const c = pit->getChar(i);
+                       if (IsPrintable(c) && i > endPosOfFontSpan) {
+                               // We need to get the next font
+                               font = getFont(pit, i);
+                               endPosOfFontSpan = pit->getEndPosOfFontSpan(i);
                        }
+                       w += singleWidth(pit, i, c, font);
                        ++i;
                }
        }
@@ -1005,8 +889,6 @@ LColor::color LyXText::backgroundColor() const
 
 void LyXText::setHeightOfRow(ParagraphList::iterator pit, RowList::iterator rit)
 {
-       Assert(rit != rows().end());
-
        // get the maximum ascent and the maximum descent
        double layoutasc = 0;
        double layoutdesc = 0;
@@ -1040,7 +922,7 @@ void LyXText::setHeightOfRow(ParagraphList::iterator pit, RowList::iterator rit)
        int maxdesc = int(font_metrics::maxDescent(font) *
                          layout->spacing.getValue() * spacing_val);
 
-       pos_type const pos_end = lastPos(*this, pit, rit);
+       pos_type const pos_end = lastPos(*pit, rit);
        int labeladdon = 0;
        int maxwidth = 0;
 
@@ -1068,7 +950,7 @@ void LyXText::setHeightOfRow(ParagraphList::iterator pit, RowList::iterator rit)
                                        maxwidth += font_metrics::width(c, font);
                                } else {
                                        // Fall-back to normal case
-                                       maxwidth += singleWidth(pit, pos, c);
+                                       maxwidth += singleWidth(pit, pos, c, font);
                                        // And flush font cache
                                        endPosOfFontSpan = 0;
                                }
@@ -1077,25 +959,13 @@ void LyXText::setHeightOfRow(ParagraphList::iterator pit, RowList::iterator rit)
                                if (par.isInset(pos)) {
                                        InsetOld const * tmpinset = par.getInset(pos);
                                        if (tmpinset) {
-#if 1 // this is needed for deep update on initialitation
-#warning inset->update FIXME
-                                               //tmpinset->update(bv());
-                                               LyXFont const tmpfont = getFont(pit, pos);
-                                               Dimension dim;
-                                               MetricsInfo mi(bv(), tmpfont, workWidth());
-                                               tmpinset->metrics(mi, dim);
-                                               maxwidth += dim.wid;
-                                               maxasc = max(maxasc, dim.asc);
-                                               maxdesc = max(maxdesc, dim.des);
-#else
                                                maxwidth += tmpinset->width();
                                                maxasc = max(maxasc, tmpinset->ascent());
                                                maxdesc = max(maxdesc, tmpinset->descent());
-#endif
                                        }
                                } else {
                                        // Fall-back to normal case
-                                       maxwidth += singleWidth(pit, pos, c);
+                                       maxwidth += singleWidth(pit, pos, c, font);
                                        // And flush font cache
                                        endPosOfFontSpan = 0;
                                }
@@ -1216,12 +1086,11 @@ void LyXText::setHeightOfRow(ParagraphList::iterator pit, RowList::iterator rit)
                                prev->getLabelWidthString() == pit->getLabelWidthString())
                        {
                                layoutasc = (layout->itemsep * defaultRowHeight());
-                       } else if (rit != rows().begin()) {
+                       } else if (rit != firstRow()) {
                                tmptop = layout->topsep;
 
-                               if (boost::prior(pit)->getDepth() >= pit->getDepth()) {
-                                       tmptop -= getPar(boost::prior(rit))->layout()->bottomsep;
-                               }
+                               //if (boost::prior(pit)->getDepth() >= pit->getDepth())
+                               //      tmptop -= getPar(previousRow(rit))->layout()->bottomsep;
 
                                if (tmptop > 0)
                                        layoutasc = (tmptop * defaultRowHeight());
@@ -1246,11 +1115,10 @@ void LyXText::setHeightOfRow(ParagraphList::iterator pit, RowList::iterator rit)
        }
 
        // is it a bottom line?
-       if (boost::next(rit) == endRow(pit)) {
+       if (boost::next(rit) == pit->rows.end()) {
                // the bottom margin
                ParagraphList::iterator nextpit = boost::next(pit);
-               if (nextpit == ownerParagraphs().end() &&
-                   !isInInset())
+               if (nextpit == ownerParagraphs().end() && !isInInset())
                        maxdesc += PAPER_MARGIN;
 
                // add the vertical spaces, that the user added
@@ -1302,31 +1170,22 @@ void LyXText::setHeightOfRow(ParagraphList::iterator pit, RowList::iterator rit)
        maxasc += int(layoutasc * 2 / (2 + pit->getDepth()));
        maxdesc += int(layoutdesc * 2 / (2 + pit->getDepth()));
 
-       // calculate the new height of the text
-       height -= rit->height();
-
        rit->height(maxasc + maxdesc + labeladdon);
        rit->baseline(maxasc + labeladdon);
-
-       height += rit->height();
-
        rit->top_of_text(rit->baseline() - font_metrics::maxAscent(font));
 
        double x = 0;
-       if (layout->margintype != MARGIN_RIGHT_ADDRESS_BOX) {
-               // this IS needed
-               rit->width(maxwidth);
-               double dummy;
-               prepareToPrint(pit, rit, x, dummy, dummy, dummy, false);
-       }
        rit->width(int(maxwidth + x));
        if (inset_owner) {
                width = max(0, workWidth());
-               RowList::iterator it = rows().begin();
-               RowList::iterator end = rows().end();
-               for (; it != end; ++it)
-                       if (it->width() > width)
-                               width = it->width();
+               RowList::iterator rit = firstRow();
+               RowList::iterator end = endRow();
+               ParagraphList::iterator it = ownerParagraphs().begin();
+               while (rit != end) {
+                       if (rit->width() > width)
+                               width = rit->width();
+                       nextRow(it, rit);
+               }
        }
 }
 
@@ -1371,6 +1230,12 @@ void LyXText::breakParagraph(ParagraphList & paragraphs, char keep_layout)
        ::breakParagraph(bv()->buffer()->params, paragraphs, cursor.par(),
                         cursor.pos(), keep_layout);
 
+#warning Trouble Point! (Lgb)
+       // When ::breakParagraph is called from within an inset we must
+       // ensure that the correct ParagraphList is used. Today that is not
+       // the case and the Buffer::paragraphs is used. Not good. (Lgb)
+       ParagraphList::iterator next_par = boost::next(cursor.par());
+
        // well this is the caption hack since one caption is really enough
        if (layout->labeltype == LABEL_SENSITIVE) {
                if (!cursor.pos())
@@ -1378,7 +1243,7 @@ void LyXText::breakParagraph(ParagraphList & paragraphs, char keep_layout)
                        cursor.par()->applyLayout(tclass.defaultLayout());
                else
                        // set to standard-layout
-                       boost::next(cursor.par())->applyLayout(tclass.defaultLayout());
+                       next_par->applyLayout(tclass.defaultLayout());
        }
 
        // if the cursor is at the beginning of a row without prior newline,
@@ -1391,19 +1256,12 @@ void LyXText::breakParagraph(ParagraphList & paragraphs, char keep_layout)
                cursorLeft(bv());
        }
 
-       removeParagraph(cursor.par(), cursorRow());
-
-#warning Trouble Point! (Lgb)
-       // When ::breakParagraph is called from within an inset we must
-       // ensure that the correct ParagraphList is used. Today that is not
-       // the case and the Buffer::paragraphs is used. Not good. (Lgb)
-       ParagraphList::iterator next_par = boost::next(cursor.par());
-
        while (!next_par->empty() && next_par->isNewline(0))
                next_par->erase(0);
 
-       insertParagraph(next_par, boost::next(cursorRow()));
        updateCounters();
+       redoParagraph(cursor.par());
+       redoParagraph(next_par);
 
        // This check is necessary. Otherwise the new empty paragraph will
        // be deleted automatically. And it is more friendly for the user!
@@ -1411,8 +1269,6 @@ void LyXText::breakParagraph(ParagraphList & paragraphs, char keep_layout)
                setCursor(next_par, 0);
        else
                setCursor(cursor.par(), 0);
-
-       redoParagraph(cursor.par());
 }
 
 
@@ -1533,7 +1389,7 @@ void LyXText::insertChar(char c)
 
 void LyXText::charInserted()
 {
-       // Here we could call FinishUndo for every 20 characters inserted.
+       // Here we could call finishUndo for every 20 characters inserted.
        // This is from my experience how emacs does it. (Lgb)
        static unsigned int counter;
        if (counter < 20) {
@@ -1546,17 +1402,13 @@ void LyXText::charInserted()
 
 
 void LyXText::prepareToPrint(ParagraphList::iterator pit,
-           RowList::iterator rit, double & x,
-                            double & fill_separator,
-                            double & fill_hfill,
-                            double & fill_label_hfill,
-                            bool bidi) const
+           RowList::iterator const rit) const
 {
        double w = rit->fill();
-       fill_hfill = 0;
-       fill_label_hfill = 0;
-       fill_separator = 0;
-       fill_label_hfill = 0;
+       double fill_hfill = 0;
+       double fill_label_hfill = 0;
+       double fill_separator = 0;
+       double x = 0;
 
        bool const is_rtl =
                pit->isRightToLeftPar(bv()->buffer()->params);
@@ -1571,7 +1423,7 @@ void LyXText::prepareToPrint(ParagraphList::iterator pit,
        if (layout->margintype == MARGIN_MANUAL
            && layout->labeltype == LABEL_MANUAL) {
                /// We might have real hfills in the label part
-               int nlh = numberOfLabelHfills(*this, pit, rit);
+               int nlh = numberOfLabelHfills(*pit, rit);
 
                // A manual label par (e.g. List) has an auto-hfill
                // between the label text and the body of the
@@ -1587,7 +1439,7 @@ void LyXText::prepareToPrint(ParagraphList::iterator pit,
        }
 
        // are there any hfills in the row?
-       int const nh = numberOfHfills(*this, pit, rit);
+       int const nh = numberOfHfills(*pit, rit);
 
        if (nh) {
                if (w > 0)
@@ -1604,15 +1456,7 @@ void LyXText::prepareToPrint(ParagraphList::iterator pit,
                } else {
                        align = pit->params().align();
                }
-
-               // center displayed insets
                InsetOld * inset = 0;
-               if (rit->pos() < pit->size()
-                   && pit->isInset(rit->pos())
-                   && (inset = pit->getInset(rit->pos()))
-                   && (inset->display())) // || (inset->scroll() < 0)))
-                   align = (inset->lyxCode() == InsetOld::MATHMACRO_CODE)
-                       ? LYX_ALIGN_BLOCK : LYX_ALIGN_CENTER;
                // ERT insets should always be LEFT ALIGNED on screen
                inset = pit->inInset();
                if (inset && inset->owner() &&
@@ -1623,17 +1467,14 @@ void LyXText::prepareToPrint(ParagraphList::iterator pit,
 
                switch (align) {
            case LYX_ALIGN_BLOCK:
-           {
-                       int const ns = numberOfSeparators(*this, pit, rit);
+               {
+                       int const ns = numberOfSeparators(*pit, rit);
                        RowList::iterator next_row = boost::next(rit);
                        if (ns
-                               && next_row != endRow(pit)
+                               && next_row != pit->rows.end()
                                && !pit->isNewline(next_row->pos() - 1)
-                         && !(pit->isInset(next_row->pos())
-                                    && pit->getInset(next_row->pos())
-                                    && pit->getInset(next_row->pos())->display())
                                ) {
-                               fill_separator = w / ns;
+                                       fill_separator = w / ns;
                        } else if (is_rtl) {
                                x += w;
                        }
@@ -1647,22 +1488,25 @@ void LyXText::prepareToPrint(ParagraphList::iterator pit,
                        break;
                }
        }
-       if (!bidi)
-               return;
 
-       computeBidiTables(pit, bv()->buffer(), rit);
+       computeBidiTables(pit, *bv()->buffer(), rit);
        if (is_rtl) {
                pos_type body_pos = pit->beginningOfBody();
-               pos_type last = lastPos(*this, pit, rit);
+               pos_type last = lastPos(*pit, rit);
 
                if (body_pos > 0 &&
-                   (body_pos - 1 > last ||
-                    !pit->isLineSeparator(body_pos - 1))) {
+                               (body_pos - 1 > last ||
+                                !pit->isLineSeparator(body_pos - 1))) {
                        x += font_metrics::width(layout->labelsep, getLabelFont(pit));
                        if (body_pos - 1 <= last)
                                x += fill_label_hfill;
                }
        }
+
+       rit->fill_hfill(fill_hfill);
+       rit->fill_label_hfill(fill_label_hfill);
+       rit->fill_separator(fill_separator);
+       rit->x(x);
 }
 
 
@@ -2065,7 +1909,7 @@ void LyXText::backspace()
                                cursorLeft(bv());
 
                                // the layout things can change the height of a row !
-                               setHeightOfRow(cursor.par(), cursorRow());
+                               redoParagraph();
                                return;
                        }
                }
@@ -2077,8 +1921,6 @@ void LyXText::backspace()
                }
 
                ParagraphList::iterator tmppit = cursor.par();
-               RowList::iterator tmprow = cursorRow();
-
                // We used to do cursorLeftIntern() here, but it is
                // not a good idea since it triggers the auto-delete
                // mechanism. So we do a cursorLeftIntern()-lite,
@@ -2093,7 +1935,7 @@ void LyXText::backspace()
                // Pasting is not allowed, if the paragraphs have different
                // layout. I think it is a real bug of all other
                // word processors to allow it. It confuses the user.
-               //Correction: Pasting is always allowed with standard-layout
+               // Correction: Pasting is always allowed with standard-layout
                LyXTextClass const & tclass =
                        bv()->buffer()->params.getLyXTextClass();
 
@@ -2101,8 +1943,6 @@ void LyXText::backspace()
                    && (cursor.par()->layout() == tmppit->layout()
                        || tmppit->layout() == tclass.defaultLayout())
                    && cursor.par()->getAlign() == tmppit->getAlign()) {
-                       removeParagraph(cursor.par(), tmprow);
-                       removeRow(tmprow);
                        mergeParagraph(bv()->buffer()->params,
                                bv()->buffer()->paragraphs, cursor.par());
 
@@ -2150,45 +1990,11 @@ RowList::iterator LyXText::getRow(LyXCursor const & cur) const
 RowList::iterator
 LyXText::getRow(ParagraphList::iterator pit, pos_type pos) const
 {
-       RowList::iterator rit = beginRow(pit);
-       RowList::iterator end = endRow(pit);
-
-#warning Why is this next thing needed? (Andre)
-       while (rit != end
-                    && rit->pos() < pos
-                    && boost::next(rit) != end
-                    && boost::next(rit)->pos() <= pos)
-               ++rit;
-
-       return rit;
-}
+       RowList::iterator rit = boost::prior(pit->rows.end());
+       RowList::iterator const begin = pit->rows.begin();
 
-
-// returns pointer to a specified row
-RowList::iterator
-LyXText::getRow(ParagraphList::iterator pit, pos_type pos, int & y) const
-{
-       y = 0;
-
-       if (rows().empty())
-               return firstRow();
-
-       RowList::iterator beg = beginRow(pit);
-       RowList::iterator end = endRow(pit);
-       RowList::iterator rit;
-
-       // find the first row of the specified paragraph
-       for (rit = firstRow(); rit != beg; rit = nextRow(rit))
-               y += rit->height();
-
-       // now find the wanted row
-       while (rit != end
-              && rit->pos() < pos
-              && boost::next(rit) != end
-              && boost::next(rit)->pos() <= pos) {
-               y += rit->height();
-               ++rit;
-       }
+       while (rit != begin && rit->pos() > pos)
+               --rit;
 
        return rit;
 }
@@ -2197,48 +2003,22 @@ LyXText::getRow(ParagraphList::iterator pit, pos_type pos, int & y) const
 // returns pointer to some fancy row 'below' specified row
 RowList::iterator LyXText::cursorIRow() const
 {
-       int y = 0;
-       return getRow(cursor.par(), cursor.pos(), y);
+       return getRow(cursor.par(), cursor.pos());
 }
 
 
-RowList::iterator LyXText::getRowNearY(int & y) const
+RowList::iterator LyXText::getRowNearY(int y,
+       ParagraphList::iterator & pit) const
 {
-       RowList::iterator rit = anchor_row_;
-       RowList::iterator const beg = rows().begin();
-       RowList::iterator const end = rows().end();
+       //lyxerr << "getRowNearY: y " << y << endl;
 
-       if (rows().empty()) {
-               y = 0;
-               return end;
-       }
-       if (rit == end)
-               rit = beg;
+       pit = boost::prior(ownerParagraphs().end());
 
-       int tmpy = rit->y();
+       RowList::iterator rit = lastRow();
+       RowList::iterator rbegin = firstRow();
 
-       if (tmpy <= y) {
-               while (rit != end && tmpy <= y) {
-                       tmpy += rit->height();
-                       ++rit;
-               }
-               if (rit != beg) {
-                       --rit;
-                       tmpy -= rit->height();
-               }
-       } else {
-               while (rit != beg && tmpy > y) {
-                       --rit;
-                       tmpy -= rit->height();
-               }
-       }
-       if (tmpy < 0 || rit == end) {
-               tmpy = 0;
-               rit = beg;
-       }
-
-       // return the rel y
-       y = tmpy;
+       while (rit != rbegin && static_cast<int>(rit->y()) > y)
+               previousRow(pit, rit);
 
        return rit;
 }
@@ -2250,82 +2030,52 @@ int LyXText::getDepth() const
 }
 
 
-#warning Expensive. Remove before 1.4!
-// computes a ParagraphList::iterator from RowList::iterator by
-// counting zeros in the sequence of pos values.
-
-ParagraphList::iterator LyXText::getPar(RowList::iterator row) const
-{
-       if (row == rows().end()) {
-               lyxerr << "getPar() pit at end " << endl;
-               Assert(false);
-       }
-
-       if (row == rows().begin()) {
-               return ownerParagraphs().begin();
-       }
-
-       ParagraphList::iterator pit = ownerParagraphs().begin();
-       RowList::iterator rit = rows().begin();
-       RowList::iterator rend = rows().end();
-       for (++rit ; rit != rend; ++rit) {
-               if (rit->pos() == 0) {
-                       ++pit;
-                       if (pit == ownerParagraphs().end()) {
-                               lyxerr << "unexpected in LyXText::getPar()" << endl;
-                               Assert(false);
-                       }
-               }
-               if (rit == row) {
-                       return pit;
-               }
-       }
-
-       lyxerr << "LyXText::getPar: row not found " << endl;
-       Assert(false);
-       return ownerParagraphs().end(); // shut up compiler
-}
-
-
-RowList::iterator LyXText::beginRow(ParagraphList::iterator pit) const
+RowList::iterator LyXText::firstRow() const
 {
-       int n = std::distance(ownerParagraphs().begin(), pit);
-
-       RowList::iterator rit = rows().begin();
-       RowList::iterator end = rows().end();
-       for ( ; rit != end; ++rit)
-               if (rit->pos() == 0 && n-- == 0)
-                       return rit;
-
-       return rit;
+       return ownerParagraphs().front().rows.begin();
 }
 
 
-RowList::iterator LyXText::endRow(ParagraphList::iterator pit) const
+RowList::iterator LyXText::lastRow() const
 {
-       return beginRow(boost::next(pit));
+       return boost::prior(endRow());
 }
 
 
-RowList::iterator LyXText::firstRow() const
+RowList::iterator LyXText::endRow() const
 {
-       return rowlist_.begin();
+       return ownerParagraphs().back().rows.end();
 }
 
 
-RowList::iterator LyXText::lastRow() const
+void LyXText::nextRow(ParagraphList::iterator & pit,
+       RowList::iterator & rit) const
 {
-       return boost::prior(rowlist_.end());
+       ++rit;
+       if (rit == pit->rows.end()) {
+               ++pit;
+               if (pit == ownerParagraphs().end())
+                       --pit;
+               else
+                       rit = pit->rows.begin();
+       }
 }
 
 
-RowList::iterator LyXText::nextRow(RowList::iterator rit) const
+void LyXText::previousRow(ParagraphList::iterator & pit,
+       RowList::iterator & rit) const
 {
-       return boost::next(rit);
+       if (rit != pit->rows.begin())
+               --rit;
+       else {
+               Assert(pit != ownerParagraphs().begin());
+               --pit;
+               rit = boost::prior(pit->rows.end());
+       }
 }
 
 
-RowList::iterator LyXText::previousRow(RowList::iterator rit) const
+bool LyXText::noRows() const
 {
-       return boost::prior(rit);
+       return ownerParagraphs().begin()->rows.empty();
 }