X-Git-Url: https://git.lyx.org/gitweb/?a=blobdiff_plain;f=src%2FCompare.cpp;h=cd54e43bb4b938274276bd539b933af031e507c3;hb=b64d17e9dcaeb84a94095622c93a051e4d93eab7;hp=a6d925752af44bda5868192bf914c719129a7bad;hpb=ce6aa0d8d3af42bdc7c408a54d22498b2db29872;p=lyx.git diff --git a/src/Compare.cpp b/src/Compare.cpp index a6d925752a..cd54e43bb4 100644 --- a/src/Compare.cpp +++ b/src/Compare.cpp @@ -14,15 +14,15 @@ #include "BufferParams.h" #include "Changes.h" +#include "Font.h" #include "insets/InsetText.h" #include "support/lassert.h" +#include "support/qstring_helpers.h" #include -#include - using namespace std; using namespace lyx::support; @@ -219,7 +219,7 @@ class Compare::Impl { public: /// Impl(Compare const & compare) - : abort_(false), compare_(compare) + : abort_(false), compare_(compare), recursion_level_(0), D_(0) {} /// @@ -234,6 +234,14 @@ public: /// Set to true to cancel the algorithm bool abort_; + /// + QString status() { + QString status; + status += toqstr("recursion level:") + " " + QString::number(recursion_level_) + + " " + toqstr("differences:") + " " + QString::number(D_); + return status; + } + private: /// Finds the middle snake and returns the length of the /// shortest edit script. @@ -264,7 +272,7 @@ private: /// around the middle snake. void diff_i(DocRangePair const & rp); - /// Processes the splitted chunks. It either adds them as deleted, + /// Processes the split chunks. It either adds them as deleted, /// as added, or call diff_i for further processing. void diffPart(DocRangePair const & rp); @@ -322,6 +330,10 @@ private: compl_vector nrp; compl_vector ors; compl_vector nrs; + + /// The number of differences in the path the algorithm + /// is currently processing. + int D_; }; ///////////////////////////////////////////////////////////////////// @@ -335,6 +347,15 @@ Compare::Compare(Buffer const * new_buf, Buffer const * old_buf, : new_buffer(new_buf), old_buffer(old_buf), dest_buffer(dest_buf), options_(options), pimpl_(new Impl(*this)) { + connect(&status_timer_, SIGNAL(timeout()), + this, SLOT(doStatusMessage())); + status_timer_.start(1000); +} + + +void Compare::doStatusMessage() +{ + statusMessage(pimpl_->status()); } @@ -347,6 +368,8 @@ void Compare::run() dest_buffer->params() = options_.settings_from_new ? new_buffer->params() : old_buffer->params(); + doStatusMessage(); + // do the real work if (!doCompare()) return; @@ -422,6 +445,13 @@ static bool equal(Inset const * i_o, Inset const * i_n) static bool equal(DocIterator & o, DocIterator & n) { + // Explicitly check for this, so we won't call + // Paragraph::getChar for the last pos. + bool const o_lastpos = o.pos() == o.lastpos(); + bool const n_lastpos = n.pos() == n.lastpos(); + if (o_lastpos || n_lastpos) + return o_lastpos && n_lastpos; + Paragraph const & old_par = o.text()->getPar(o.pit()); Paragraph const & new_par = n.text()->getPar(n.pit()); @@ -496,6 +526,7 @@ void Compare::Impl::furthestDpathKdiagonal(int D, int k, // Where do we take the step from ? int const kk = vertical_step ? k + 1 : k - 1; DocPair p(op[kk], np[kk]); + DocPair const s(os[kk], ns[kk]); // If D==0 we simulate a vertical step from (0,-1) by doing nothing. if (D != 0) { @@ -517,8 +548,8 @@ void Compare::Impl::furthestDpathKdiagonal(int D, int k, ns[k] = p.n; } else { // Copy last snake from the previous step - os[k] = os[kk]; - ns[k] = ns[kk]; + os[k] = s.o; + ns[k] = s.n; } //Record new position @@ -601,10 +632,13 @@ int Compare::Impl::findMiddleSnake(DocRangePair const & rp, ors.reset(DocIterator()); nrs.reset(DocIterator()); + // In the formula below, the "+ 1" ensures we round like ceil() + int const D_max = (M_ + N_ + 1)/2; // D is the number of horizontal and vertical steps, i.e. // different characters in the old and new chunk. - int const D_max = ceil(((double)M_ + N_)/2); for (int D = 0; D <= D_max; ++D) { + // to be used in the status messages + D_ = D; // Forward and reverse paths for (int f = 0; f < 2; ++f) { @@ -625,6 +659,8 @@ int Compare::Impl::findMiddleSnake(DocRangePair const & rp, return 2 * D - odd_offset_; } } + if (abort_) + return 0; } } } @@ -656,7 +692,9 @@ bool Compare::Impl::diff(Buffer const * new_buf, Buffer const * old_buf, processSnake(snake); // Start the recursive algorithm - diff_i(rp); + DocRangePair rp_new(from, rp.to()); + if (!rp_new.o.empty() || !rp_new.n.empty()) + diff_i(rp_new); for (pit_type p = 0; p < (pit_type)dest_pars_->size(); ++p) { (*dest_pars_)[p].setBuffer(const_cast(*dest_buf)); @@ -669,6 +707,9 @@ bool Compare::Impl::diff(Buffer const * new_buf, Buffer const * old_buf, void Compare::Impl::diff_i(DocRangePair const & rp) { + if (abort_) + return; + // The middle snake DocPair middle_snake;