]> git.lyx.org Git - lyx.git/blobdiff - src/TextMetrics.cpp
make \lyxadded and \lyxdeleted robust (#8435)
[lyx.git] / src / TextMetrics.cpp
index 50f6062275a685b238031c94eb8c02cccc8bf8f5..938223050961fbe55778f9d7719849ae62ba137f 100644 (file)
@@ -375,19 +375,28 @@ bool TextMetrics::redoParagraph(pit_type const pit)
        main_text_ = (text_ == &buffer.text());
        bool changed = false;
 
+       // Check whether there are InsetBibItems that need fixing
        // FIXME: This check ought to be done somewhere else. It is the reason
-       // why text_ is not     const. But then, where else to do it?
+       // why text_ is not const. But then, where else to do it?
        // Well, how can you end up with either (a) a biblio environment that
        // has no InsetBibitem or (b) a biblio environment with more than one
        // InsetBibitem? I think the answer is: when paragraphs are merged;
        // when layout is set; when material is pasted.
-       int const moveCursor = par.checkBiblio(buffer);
-       if (moveCursor > 0)
-               const_cast<Cursor &>(bv_->cursor()).posForward();
-       else if (moveCursor < 0) {
-               Cursor & cursor = const_cast<Cursor &>(bv_->cursor());
-               if (cursor.pos() >= -moveCursor)
-                       cursor.posBackward();
+       if (par.brokenBiblio()) {
+               Cursor & cur = const_cast<Cursor &>(bv_->cursor());
+               // In some cases, we do not know how to record undo
+               if (&cur.inset() == &text_->inset())
+                       cur.recordUndo(ATOMIC_UNDO, pit, pit);
+
+               int const moveCursor = par.fixBiblio(buffer);
+
+               // Is it necessary to update the cursor?
+               if (&cur.inset() == &text_->inset() && cur.pit() == pit) {
+                       if (moveCursor > 0)
+                               cur.posForward();
+                       else if (moveCursor < 0 && cur.pos() >= -moveCursor)
+                               cur.posBackward();
+               }
        }
 
        // Optimisation: this is used in the next two loops
@@ -707,6 +716,8 @@ int TextMetrics::labelFill(pit_type const pit, Row const & row) const
 }
 
 
+#if 0
+// Not used, see TextMetrics::rowBreakPoint. 
 // this needs special handling - only newlines count as a break point
 static pos_type addressBreakPoint(pos_type i, Paragraph const & par)
 {
@@ -718,6 +729,7 @@ static pos_type addressBreakPoint(pos_type i, Paragraph const & par)
 
        return end;
 }
+#endif
 
 
 int TextMetrics::labelEnd(pit_type const pit) const
@@ -798,8 +810,13 @@ pos_type TextMetrics::rowBreakPoint(int width, pit_type const pit,
 
        Layout const & layout = par.layout();
 
+#if 0
+       //FIXME: As long as leftMargin() is not correctly implemented for 
+       // MARGIN_RIGHT_ADDRESS_BOX, we should also not do this here.
+       // Otherwise, long rows will be painted off the screen.
        if (layout.margintype == MARGIN_RIGHT_ADDRESS_BOX)
                return addressBreakPoint(pos, par);
+#endif
 
        pos_type const body_pos = par.beginOfBody();
 
@@ -1231,12 +1248,13 @@ pos_type TextMetrics::getColumnNearX(pit_type const pit,
 
        // If lastrow is false, we don't need to compute
        // the value of rtl.
-       bool const rtl = lastrow ? text_->isRTL(par) : false;
+       bool const rtl_on_lastrow = lastrow ? text_->isRTL(par) : false;
 
        // if the first character is a separator, and we are in RTL
        // text, this character will not be painted on screen
-       // and thus we should not count it and skip to the next.
-       if (rtl && par.isSeparator(bidi.vis2log(vc)))
+       // and thus we should not count it and skip to the next. Only
+       // in freespacing paragraphs, this first character is painted.
+       if (!par.isFreeSpacing() && par.isSeparator(bidi.vis2log(vc)))
                ++vc;
 
        while (vc < end && tmpx <= x) {
@@ -1266,8 +1284,8 @@ pos_type TextMetrics::getColumnNearX(pit_type const pit,
        boundary = false;
 
        if (lastrow &&
-           ((rtl  &&  left_side && vc == row.pos() && x < tmpx - 5) ||
-            (!rtl && !left_side && vc == end  && x > tmpx + 5))) {
+           ((rtl_on_lastrow  &&  left_side && vc == row.pos() && x < tmpx - 5) ||
+            (!rtl_on_lastrow && !left_side && vc == end  && x > tmpx + 5))) {
                if (!par.isNewline(end - 1))
                        c = end;
        } else if (vc == row.pos()) {
@@ -1380,7 +1398,8 @@ pit_type TextMetrics::getPitNearY(int y)
        int yy = -1;
        ParMetricsCache::const_iterator it = par_metrics_.begin();
        ParMetricsCache::const_iterator et = par_metrics_.end();
-       ParMetricsCache::const_iterator last = et; last--;
+       ParMetricsCache::const_iterator last = et;
+       --last;
 
        ParagraphMetrics const & pm = it->second;
 
@@ -1974,16 +1993,18 @@ int TextMetrics::leftMargin(int max_width,
 
        case MARGIN_RIGHT_ADDRESS_BOX: {
 #if 0
-               // ok, a terrible hack. The left margin depends on the widest
-               // row in this paragraph.
-               RowList::iterator rit = par.rows().begin();
-               RowList::iterator end = par.rows().end();
-               // FIXME: This is wrong.
+               // The left margin depends on the widest row in this paragraph.
+               // This code is wrong because it depends on the rows, but at the
+               // same time this function is used in redoParagraph to construct
+               // the rows. 
+               ParagraphMetrics const & pm = par_metrics_[pit];
+               RowList::const_iterator rit = pm.rows().begin();
+               RowList::const_iterator end = pm.rows().end();
                int minfill = max_width;
                for ( ; rit != end; ++rit)
                        if (rit->fill() < minfill)
                                minfill = rit->fill();
-               l_margin += theFontMetrics(params.getFont()).signedWidth(layout.leftmargin);
+               l_margin += theFontMetrics(buffer.params().getFont()).signedWidth(layout.leftmargin);
                l_margin += minfill;
 #endif
                // also wrong, but much shorter.