On Thu, Dec 22, 2005 at 06:23:26PM +0100, Jean-Marc Lasgouttes wrote: > >>>>> "David" == David Green <[EMAIL PROTECTED]> writes: > > David> On 12/22/05 7:41 AM, "Jean-Marc Lasgouttes" > David> <[EMAIL PROTECTED]> > David> wrote: > > >>>>>>> "Martin" == Martin Vermeer <[EMAIL PROTECTED]> writes: > >> > Martin> Is crc32 invariant for character transposition? > >> Sure. > > David> Erm, crc32 should produce a different result when characters > David> are transposed. > > Yes, that's what I meant, sorry. > > So my answer was supposed to be "of course not."
That is what I wanted to hear... Attached, finally, the corrected version of the patch using crc32. Turns out y isn't needed here after all. - Martin
Index: RowList_fwd.h =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/RowList_fwd.h,v retrieving revision 1.6 diff -u -p -r1.6 RowList_fwd.h --- RowList_fwd.h 31 Jan 2005 16:29:38 -0000 1.6 +++ RowList_fwd.h 29 Dec 2005 20:58:34 -0000 @@ -15,6 +15,7 @@ #include "lyxrow.h" #include <vector> +#include <map> /** * Each paragraph is broken up into a number of rows on the screen. @@ -22,5 +23,7 @@ * downwards. */ typedef std::vector<Row> RowList; +/// +typedef std::map<lyx::size_type, lyx::size_type> RowSignature; #endif Index: paragraph.C =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/paragraph.C,v retrieving revision 1.417 diff -u -p -r1.417 paragraph.C --- paragraph.C 25 Nov 2005 14:40:34 -0000 1.417 +++ paragraph.C 29 Dec 2005 20:58:35 -0000 @@ -81,7 +81,8 @@ Paragraph::Paragraph() Paragraph::Paragraph(Paragraph const & par) : itemdepth(par.itemdepth), insetlist(par.insetlist), dim_(par.dim_), - rows_(par.rows_), layout_(par.layout_), + rows_(par.rows_), rowSignature_(par.rowSignature_), + layout_(par.layout_), text_(par.text_), begin_of_body_(par.begin_of_body_), pimpl_(new Paragraph::Pimpl(*par.pimpl_, this)) { @@ -107,6 +108,7 @@ Paragraph & Paragraph::operator=(Paragra rows_ = par.rows_; dim_ = par.dim_; + rowSignature_ = par.rowSignature_; layout_ = par.layout(); text_ = par.text_; begin_of_body_ = par.begin_of_body_; Index: paragraph.h =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/paragraph.h,v retrieving revision 1.157 diff -u -p -r1.157 paragraph.h --- paragraph.h 7 Sep 2005 10:36:59 -0000 1.157 +++ paragraph.h 29 Dec 2005 20:58:35 -0000 @@ -391,7 +391,9 @@ public: RowList & rows() { return rows_; } /// The painter and others use this RowList const & rows() const { return rows_; } - + /// + RowSignature & rowSignature() const { return rowSignature_; } + /// LyXText::redoParagraph updates this Dimension & dim() { return dim_; } @@ -408,6 +410,9 @@ private: /// mutable RowList rows_; + /// + mutable RowSignature rowSignature_; + /// LyXLayout_ptr layout_; /** Index: rowpainter.C =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/rowpainter.C,v retrieving revision 1.160 diff -u -p -r1.160 rowpainter.C --- rowpainter.C 17 Dec 2005 15:03:39 -0000 1.160 +++ rowpainter.C 29 Dec 2005 20:58:36 -0000 @@ -40,6 +40,8 @@ #include "support/textutils.h" +#include <boost/crc.hpp> + using lyx::pos_type; using lyx::pit_type; @@ -717,7 +719,8 @@ void RowPainter::paintText() void paintPar - (PainterInfo & pi, LyXText const & text, pit_type pit, int x, int y) + (PainterInfo & pi, LyXText const & text, pit_type pit, int x, int y, + bool repaintAll) { // lyxerr << " paintPar: pit: " << pit << " at y: " << y << endl; static NullPainter nop; @@ -731,22 +734,67 @@ void paintPar theCoords.parPos()[&text][pit] = Point(x, y); y -= rb->ascent(); - for (RowList::const_iterator rit = rb; rit != re; ++rit) { + lyx::size_type rowno(0); + for (RowList::const_iterator rit = rb; rit != re; ++rit, ++rowno) { y += rit->ascent(); bool const inside = (y + rit->descent() >= 0 && y - rit->ascent() < ww); RowPainter rp(inside ? pi : nullpi, text, pit, *rit, x, y); y += rit->descent(); - rp.paintAppendix(); - rp.paintDepthBar(); - rp.paintChangeBar(); - if (rit == rb) - rp.paintFirst(); - if (rit + 1 == re) - rp.paintLast(); - rp.paintText(); + + // Row signature; has row changed since last paint? + boost::crc_32_type crc; + for (lyx::pos_type i = rit->pos(); i < rit->endpos(); ++i) { + const unsigned char b[] = { par.getChar(i) }; + crc.process_bytes(b, 1); + } + lyx::size_type const row_sig = crc.checksum(); + + // The following code figures out if the cursor is inside + // an inset _on this row_. + bool cur_in_inset_in_row(false); + InsetList::const_iterator ii = par.insetlist.begin(); + InsetList::const_iterator iend = par.insetlist.end(); + for ( ; ii != iend; ++ii) { + if (ii->pos >= rit->pos() && ii->pos < rit->endpos() + && ii->inset->isTextInset() + && pi.base.bv->cursor().isInside(ii->inset)) + cur_in_inset_in_row = true; + break; + } + + // If selection is on, the current row signature differs from + // from cache, or cursor is inside an inset _on this row_, + // then paint the row + if (repaintAll || par.rowSignature()[rowno] != row_sig + || cur_in_inset_in_row) { + // Add to row signature cache + par.rowSignature()[rowno] = row_sig; + + // Clear background of this row + // (if paragraph background was not cleared) + if (!repaintAll) { + int ht = rit->ascent() + rit->descent(); + pi.pain.fillRectangle(x, y - ht, + pi.base.bv->workWidth(), ht, + text.backgroundColor()); + } + + // Instrumentation for testing row cache (see also + // 12 lines lower): + //lyxerr << "#"; + rp.paintAppendix(); + rp.paintDepthBar(); + rp.paintChangeBar(); + if (rit == rb) + rp.paintFirst(); + if (rit + 1 == re) + rp.paintLast(); + rp.paintText(); + } } + //lyxerr << "." << endl; } } // namespace anon @@ -756,22 +804,25 @@ void paintText(BufferView const & bv, Vi { Painter & pain = bv.painter(); LyXText * const text = bv.text(); + bool const select = bv.cursor().selection(); - // clear background - pain.fillRectangle(0, vi.y1, bv.workWidth(), vi.y2 - vi.y1, - LColor::background); - - // draw selection PainterInfo pi(const_cast<BufferView *>(&bv), pain); - - text->drawSelection(pi, 0, 0); + if (select || !vi.singlepar) { + // Clear background (Delegated to rows if no selection) + pain.fillRectangle(0, vi.y1, bv.workWidth(), vi.y2 - vi.y1, + text->backgroundColor()); + } + if (select) { + text->drawSelection(pi, 0, 0); + } int yy = vi.y1; // draw contents for (pit_type pit = vi.p1; pit <= vi.p2; ++pit) { - yy += text->getPar(pit).ascent(); - paintPar(pi, *bv.text(), pit, 0, yy); - yy += text->getPar(pit).descent(); + Paragraph const & par = text->getPar(pit); + yy += par.ascent(); + paintPar(pi, *bv.text(), pit, 0, yy, select || !vi.singlepar); + yy += par.descent(); } // Cache one paragraph above and one below @@ -809,7 +860,7 @@ void paintTextInset(LyXText const & text y -= text.getPar(0).ascent(); for (int pit = 0; pit < int(text.paragraphs().size()); ++pit) { y += text.getPar(pit).ascent(); - paintPar(pi, text, pit, x, y); + paintPar(pi, text, pit, x, y, true); y += text.getPar(pit).descent(); } }
pgpmI4Zu3R95q.pgp
Description: PGP signature