Not tested througly, but seems to work normally on standard operations. (note that almost all the + are in the new files...)
Comments please? BufferView_pimpl.C | 2 Makefile.am | 2 PosIterator.C | 151 ++++++++++++++ PosIterator.h | 66 ++++++ buffer.C | 13 + buffer.h | 5 insets/inset.h | 4 insets/insetcollapsable.C | 42 ---- insets/insetcollapsable.h | 10 insets/insettabular.C | 101 +-------- insets/insettabular.h | 10 insets/insettext.C | 76 ------- insets/insettext.h | 12 - insets/updatableinset.C | 16 - insets/updatableinset.h | 9 iterators.C | 32 +++ iterators.h | 10 lyxfind.C | 476 ++++++++++++++++++---------------------------- lyxfind.h | 28 -- paragraph.C | 8 paragraph.h | 2 text.C | 2 22 files changed, 520 insertions(+), 557 deletions(-)
? iterators.C-save ? iterators.h-save ? lyxfind.C-save ? lyxrow_funcs.C-bad1 ? paragraph.C-bad1 ? text.C-bad1 ? text.C-good ? text.C-goood ? text3-save.C Index: BufferView_pimpl.C =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/BufferView_pimpl.C,v retrieving revision 1.450 diff -u -p -u -r1.450 BufferView_pimpl.C --- BufferView_pimpl.C 29 Oct 2003 19:19:21 -0000 1.450 +++ BufferView_pimpl.C 31 Oct 2003 21:26:33 -0000 @@ -418,8 +418,6 @@ void BufferView::Pimpl::resizeCurrentBuf bv_->text->fullRebreak(); update(); } else { - lyxerr << "text not available!" << endl; - lyxerr << "no text in cache!" << endl; bv_->text = new LyXText(bv_, 0, false, bv_->buffer()->paragraphs()); bv_->text->init(bv_); } Index: Makefile.am =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/Makefile.am,v retrieving revision 1.197 diff -u -p -u -r1.197 Makefile.am --- Makefile.am 29 Oct 2003 10:47:12 -0000 1.197 +++ Makefile.am 31 Oct 2003 21:26:33 -0000 @@ -228,6 +228,8 @@ lyx_SOURCES = \ paragraph.h \ paragraph_pimpl.C \ paragraph_pimpl.h \ + PosIterator.h \ + PosIterator.C \ SpellBase.h \ ispell.C \ ispell.h \ Index: PosIterator.C =================================================================== RCS file: PosIterator.C diff -N PosIterator.C --- /dev/null 1 Jan 1970 00:00:00 -0000 +++ PosIterator.C 31 Oct 2003 21:26:33 -0000 @@ -0,0 +1,151 @@ +/* \file PosIterator.C + * This file is part of LyX, the document processor. + * Licence details can be found in the file COPYING. + * + * \author + * + * Full author contact details are available in file CREDITS. + */ + + +#include <config.h> + +#include "PosIterator.h" + +#include "buffer.h" +#include "BufferView.h" +#include "lyxtext.h" + +#include "paragraph.h" +#include "cursor.h" +#include "iterators.h" + +#include "insets/insettext.h" +#include "insets/updatableinset.h" +#include "insets/inset.h" + + +using boost::prior; + +PosIterator & PosIterator::operator++() +{ + while (!stack_.empty()) { + PosIteratorItem & p = stack_.top(); + + if (p.pos < p.pit->size()) { + InsetOld * inset = p.pit->getInset(p.pos); + if (inset) { + ParagraphList * pl = inset->getParagraphs(p.index); + if (pl) { + p.index++; + stack_.push(PosIteratorItem(pl)); + return *this; + } + } + p.index = 0; + ++p.pos; + } else { + ++p.pit; + p.pos = 0; + } + + if (p.pit != p.pl->end() || stack_.size() == 1) + return *this; + + stack_.pop(); + } + return *this; +} + + +PosIterator & PosIterator::operator--() +{ + while (!stack_.empty()) { + { + PosIteratorItem & p = stack_.top(); + if (p.pos > 0) { + --p.pos; + InsetOld * inset = p.pit->getInset(p.pos); + if (inset) + p.index = inset->numParagraphs(); + } else { + if (p.pit == p.pl->begin()) { + if (stack_.size() == 1) + return *this; + stack_.pop(); + --stack_.top().index; + } else { + --p.pit; + p.pos = p.pit->size(); + } + } + } + PosIteratorItem & p = stack_.top(); + if (p.pos < p.pit->size()) { + InsetOld * inset = p.pit->getInset(p.pos); + if (inset && p.index > 0) { + ParagraphList * + pl = inset->getParagraphs(p.index - 1); + BOOST_ASSERT(pl); + stack_.push(PosIteratorItem(pl, prior(pl->end()), pl->back().size())); + } + } + return *this; + } + return *this; +} + + +bool PosIterator::operator!=(PosIterator const & a) const +{ + return !operator==(a); +} + + + +bool PosIterator::operator==(PosIterator const & a) const +{ + + PosIteratorItem const & pa = a.stack_.top(); + PosIteratorItem const & p = stack_.top(); + + return (pa.pl == p.pl && pa.pit == p.pit && + (p.pit == p.pl->end() || pa.pos == p.pos)); +} + + +bool PosIterator::at_end() const +{ + return pos() == pit()->size(); +} + + +PosIterator::PosIterator(ParagraphList * pl, ParagraphList::iterator pit, + lyx::pos_type pos) +{ + stack_.push(PosIteratorItem(pl,pit,pos)); +} + + +PosIterator::PosIterator(ParagraphList * pl) +{ + stack_.push(PosIteratorItem(pl, pl->begin(), 0)); +} + + +PosIterator::PosIterator(BufferView & bv) +{ + LyXText * text = bv.getLyXText(); + lyx::pos_type pos = text->cursor.pos(); + ParagraphList::iterator pit = text->cursorPar(); + + ParIterator par = bv.buffer()->par_iterator_begin(); + ParIterator end = bv.buffer()->par_iterator_end(); + for ( ; par != end; ++par) { + if (par.pit() == pit) + break; + } + + *this = PosIterator(par, pos); +} + Index: PosIterator.h =================================================================== RCS file: PosIterator.h diff -N PosIterator.h --- /dev/null 1 Jan 1970 00:00:00 -0000 +++ PosIterator.h 31 Oct 2003 21:26:33 -0000 @@ -0,0 +1,66 @@ +// -*- C++ -*- +/* \file iterators.h + * This file is part of LyX, the document processor. + * Licence details can be found in the file COPYING. + * + * \author unknown + * \author Lars Gullik Bjønnes + * + * Full author contact details are available in file CREDITS. + */ + +#ifndef POSITERATOR_H +#define POSITERATOR_H + +#include "ParagraphList_fwd.h" + +#include <boost/scoped_ptr.hpp> + +#include "support/types.h" + +#include <stack> + +class ParIterator; + +class BufferView; + +struct PosIteratorItem +{ + PosIteratorItem(ParagraphList * pl): pl(pl), pit(pl->begin()), + pos(0), index(0) {}; + PosIteratorItem(ParagraphList * pl, + ParagraphList::iterator pit, + lyx::pos_type pos, + int index = 0) + : pl(pl), pit(pit), pos(pos), index(index) {}; + ParagraphList * pl; + ParagraphList::iterator pit; + lyx::pos_type pos; + int index; +}; + + +class PosIterator +{ +public: + PosIterator(BufferView & bv); + PosIterator(ParIterator & par, lyx::pos_type pos); + PosIterator(ParagraphList * pl); + PosIterator(ParagraphList * pl, ParagraphList::iterator pit, + lyx::pos_type pos); + PosIterator(ParIterator const & parit, lyx::pos_type p); + PosIterator & operator++(); + PosIterator & operator--(); + bool operator!=(PosIterator const &) const; + bool operator==(PosIterator const &) const; + + ParagraphList::iterator pit() const { return stack_.top().pit; } + lyx::pos_type pos() const { return stack_.top().pos; } + bool at_end() const; +private: + std::stack<PosIteratorItem> stack_; +}; + + +#endif + Index: buffer.C =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/buffer.C,v retrieving revision 1.538 diff -u -p -u -r1.538 buffer.C --- buffer.C 31 Oct 2003 18:45:34 -0000 1.538 +++ buffer.C 31 Oct 2003 21:26:35 -0000 @@ -36,6 +36,7 @@ #include "paragraph.h" #include "paragraph_funcs.h" #include "ParagraphParameters.h" +#include "PosIterator.h" #include "sgml.h" #include "texrow.h" #include "undo.h" @@ -1469,6 +1470,18 @@ bool Buffer::hasParWithID(int id) const return true; return false; +} + + +PosIterator Buffer::pos_iterator_begin() +{ + return PosIterator(¶graphs(), paragraphs().begin(), 0); +} + + +PosIterator Buffer::pos_iterator_end() +{ + return PosIterator(¶graphs(), paragraphs().end(), 0); } Index: buffer.h =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/buffer.h,v retrieving revision 1.170 diff -u -p -u -r1.170 buffer.h --- buffer.h 31 Oct 2003 18:45:34 -0000 1.170 +++ buffer.h 31 Oct 2003 21:26:36 -0000 @@ -40,6 +40,7 @@ class LatexRunParams; class Language; class Messages; class ParIterator; +class PosIterator; class ParConstIterator; class TeXErrors; class TexRow; @@ -345,6 +346,10 @@ public: /// return the const end of all *top-level* insets in the buffer inset_iterator inset_const_iterator_end() const; + /// + PosIterator pos_iterator_begin(); + /// + PosIterator pos_iterator_end(); /// ParIterator par_iterator_begin(); /// Index: iterators.C =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/iterators.C,v retrieving revision 1.23 diff -u -p -u -r1.23 iterators.C --- iterators.C 29 Oct 2003 12:18:06 -0000 1.23 +++ iterators.C 31 Oct 2003 21:26:36 -0000 @@ -13,9 +13,15 @@ #include "iterators.h" #include "paragraph.h" +#include "PosIterator.h" #include "cursor.h" +#include "BufferView.h" +#include "funcrequest.h" +#include "dispatchresult.h" + #include "insets/inset.h" +#include "insets/updatableinset.h" #include <boost/next_prior.hpp> #include <boost/optional.hpp> @@ -355,4 +361,30 @@ bool operator==(ParConstIterator const & bool operator!=(ParConstIterator const & iter1, ParConstIterator const & iter2) { return !(iter1 == iter2); +} + + +PosIterator::PosIterator(ParIterator & parit, lyx::pos_type pos) +{ + int const last = parit.size() - 1; + for (int i = 0; i < last; ++i) { + ParPosition & pp = parit.pimpl_->positions[i]; + stack_.push(PosIteratorItem(const_cast<ParagraphList *>(pp.plist), + pp.pit, (*pp.it)->pos, *pp.index + 1)); + } + ParPosition const & pp = parit.pimpl_->positions[last]; + stack_.push(PosIteratorItem(const_cast<ParagraphList *>(pp.plist), + pp.pit, pos, 0)); +} + + +void ParIterator::lockPath(BufferView * bv) const +{ + bv->insetUnlock(); + int last = size() - 1; + for (int i = 0; i < last; ++i) { + UpdatableInset * inset = dynamic_cast<UpdatableInset *>((*pimpl_->positions[i].it)->inset); + FuncRequest cmd(bv, LFUN_INSET_EDIT); + inset->dispatch(cmd); + } } Index: iterators.h =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/iterators.h,v retrieving revision 1.19 diff -u -p -u -r1.19 iterators.h --- iterators.h 29 Oct 2003 12:18:06 -0000 1.19 +++ iterators.h 31 Oct 2003 21:26:36 -0000 @@ -19,6 +19,7 @@ class LyXText; class InsetOld; class Cursor; +class BufferView; class ParIterator { public: @@ -56,6 +57,11 @@ public: /// friend bool operator==(ParIterator const & iter1, ParIterator const & iter2); + /// + friend class PosIterator; + /// + void lockPath(BufferView *) const; + private: struct Pimpl; boost::scoped_ptr<Pimpl> pimpl_; @@ -93,6 +99,10 @@ public: friend bool operator==(ParConstIterator const & iter1, ParConstIterator const & iter2); + /// + friend class PosIterator; + /// + void lockPath(BufferView *) const; private: struct Pimpl; boost::scoped_ptr<Pimpl> pimpl_; Index: lyxfind.C =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/lyxfind.C,v retrieving revision 1.54 diff -u -p -u -r1.54 lyxfind.C --- lyxfind.C 9 Oct 2003 10:52:07 -0000 1.54 +++ lyxfind.C 31 Oct 2003 21:26:37 -0000 @@ -14,11 +14,16 @@ #include "lyxfind.h" +#include "funcrequest.h" +#include "dispatchresult.h" #include "buffer.h" #include "BufferView.h" +#include "debug.h" +#include "iterators.h" #include "gettext.h" #include "lyxtext.h" #include "paragraph.h" +#include "PosIterator.h" #include "frontends/Alert.h" @@ -37,159 +42,213 @@ namespace find { namespace { -// returns true if the specified string is at the specified position -bool isStringInText(Paragraph const & par, pos_type pos, - string const & str, bool const & cs, - bool const & mw) +class MatchString { - string::size_type size = str.length(); - pos_type i = 0; - pos_type parsize = par.size(); - while ((pos + i < parsize) - && (string::size_type(i) < size) - && (cs ? (str[i] == par.getChar(pos + i)) - : (uppercase(str[i]) == uppercase(par.getChar(pos + i))))) { - ++i; - } - - if (size == string::size_type(i)) { - // if necessary, check whether string matches word - if (!mw) - return true; - if ((pos <= 0 || !IsLetterCharOrDigit(par.getChar(pos - 1))) - && (pos + pos_type(size) >= parsize - || !IsLetterCharOrDigit(par.getChar(pos + size)))) { - return true; +public: + MatchString(string const & str, bool cs, bool mw) + : str(str), cs(cs), mw(mw) {}; +// returns true if the specified string is at the specified position + bool operator()(Paragraph const & par, pos_type pos) const + { + string::size_type size = str.length(); + pos_type i = 0; + pos_type parsize = par.size(); + while ((pos + i < parsize) + && (string::size_type(i) < size) + && (cs ? (str[i] == par.getChar(pos + i)) + : (uppercase(str[i]) == uppercase(par.getChar(pos + i))))) { + ++i; + } + if (size == string::size_type(i)) { + // if necessary, check whether string matches word + if (!mw) + return true; + if ((pos <= 0 || !IsLetterCharOrDigit(par.getChar(pos - 1))) + && (pos + pos_type(size) >= parsize + || !IsLetterCharOrDigit(par.getChar(pos + size)))) { + return true; + } } + return false; } - return false; -} + +private: + string str; + bool cs; + bool mw; +}; + + + +} //namespace anon + + + + + +namespace { + -// forward search: -// if the string can be found: return true and set the cursor to -// the new position, cs = casesensitive, mw = matchword -SearchResult searchForward(BufferView * bv, LyXText * text, string const & str, - bool const & cs, bool const & mw) +void put_selection_at(BufferView * bv, PosIterator & cur, + int length, bool backwards) { - ParagraphList::iterator pit = text->cursorPar(); - ParagraphList::iterator pend = text->ownerParagraphs().end(); - pos_type pos = text->cursor.pos(); - UpdatableInset * inset; - - while (pit != pend && !isStringInText(*pit, pos, str, cs, mw)) { - if (pos < pit->size() - && pit->isInset(pos) - && (inset = (UpdatableInset *)pit->getInset(pos)) - && inset->isTextInset() - && inset->searchForward(bv, str, cs, mw)) - return SR_FOUND_NOUPDATE; - - if (++pos >= pit->size()) { - ++pit; - pos = 0; - } + ParIterator par = bv->buffer()->par_iterator_begin(); + for (; par.pit() != cur.pit(); ++par) + ; + + { + LyXText * text = bv->getLyXText(); + text->clearSelection(); } + + UpdatableInset * outer = dynamic_cast<UpdatableInset *>(par.inset()); + + par.lockPath(bv); + + LyXText * text = par.text() ? par.text() : bv->text; - if (pit != pend) { - text->setCursor(pit, pos); - return SR_FOUND; + InsetText * inner = text->inset_owner; + + if (inner != outer) { + outer->insetUnlock(bv); + outer->lockInsetInInset(bv, inner); } - return SR_NOT_FOUND; + + + text->setCursor(cur.pit(), cur.pos()); + if (length) { + text->setSelectionRange(length); + text->setSelection(); + if (backwards) + text->cursor = text->selection.start; + } + + + bv->fitCursor(); + bv->update(); + } -// backward search: -// if the string can be found: return true and set the cursor to -// the new position, cs = casesensitive, mw = matchword -SearchResult searchBackward(BufferView * bv, LyXText * text, - string const & str, - bool const & cs, bool const & mw) +bool findForward(PosIterator & cur, PosIterator & end, MatchString & match) { - ParagraphList::iterator pit = text->cursorPar(); - ParagraphList::iterator pbegin = text->ownerParagraphs().begin(); - pos_type pos = text->cursor.pos(); - - // skip past a match at the current cursor pos - if (pos > 0) { - --pos; - } else if (pit != pbegin) { - --pit; - pos = pit->size(); - } else { - return SR_NOT_FOUND; - } + for (; cur != end && !match(*cur.pit(), cur.pos()); ++cur) + ; - while (true) { - if (pos < pit->size()) { - if (pit->isInset(pos) && pit->getInset(pos)->isTextInset()) { - UpdatableInset * inset = (UpdatableInset *)pit->getInset(pos); - if (inset->searchBackward(bv, str, cs, mw)) - return SR_FOUND_NOUPDATE; - } + return cur != end; +} - if (isStringInText(*pit, pos, str, cs, mw)) { - text->setCursor(pit, pos); - return SR_FOUND; - } - } - if (pos == 0 && pit == pbegin) +bool findBackwards(PosIterator & cur, PosIterator & beg, MatchString & match) +{ + if (beg == cur) + return false; + do { + --cur; + if (match(*cur.pit(), cur.pos())) break; + } while (cur != beg); - if (pos > 0) { - --pos; - } else if (pit != pbegin) { - --pit; - pos = pit->size(); - } + return match(*cur.pit(), cur.pos()); +} + + +bool findChange(PosIterator & cur, PosIterator & end) +{ + for (; cur != end; ++cur) { + if ((!cur.pit()->size() || !cur.at_end()) + && cur.pit()->lookupChange(cur.pos()) != Change::UNCHANGED) + break; } + + return cur != end; +} + + + +} // namespace anon + + + - return SR_NOT_FOUND; +bool find(BufferView * bv, + string const & searchstr, bool fw, bool cs, bool mw) +{ + if (!bv->available() || searchstr.empty()) + return false; + + PosIterator cur = PosIterator(*bv); + + MatchString match(searchstr, cs, mw); + + if (fw) { + PosIterator end = bv->buffer()->pos_iterator_end(); + findForward(cur, end, match); + } else { + PosIterator beg = bv->buffer()->pos_iterator_begin(); + findBackwards(cur, beg, match); + } + put_selection_at(bv, cur, searchstr.length(), !fw); + return true; } -} // anon namespace +int replace_all(BufferView * bv, + string const & searchstr, string const & replacestr, + bool fw, bool cs, bool mw) +{ + + PosIterator cur = bv->buffer()->pos_iterator_begin(); + PosIterator end = bv->buffer()->pos_iterator_end(); + // override search direction because we search top to bottom + fw = true; + MatchString match(searchstr, cs, mw); + int num = 0; + + int const rsize = replacestr.size(); + int const ssize = searchstr.size(); + while (findForward(cur, end, match)) { + pos_type pos = cur.pos(); + int striked = ssize - cur.pit()->erase(pos, pos + ssize); + cur.pit()->insert(pos, replacestr); + for (int i = 0; i < rsize + striked; ++i) + // what do I need for std::advance? + ++cur; + ++num; + } + PosIterator beg = bv->buffer()->pos_iterator_begin(); + bv->text->fullRebreak(); + put_selection_at(bv, beg, 0, false); + return num; +} int replace(BufferView * bv, - string const & searchstr, string const & replacestr, - bool forward, bool casesens, bool matchwrd, bool replaceall, - bool once) + string const & searchstr, string const & replacestr, + bool fw, bool cs, bool mw, bool replaceall, + bool once) { if (!bv->available() || bv->buffer()->isReadonly()) return 0; - // CutSelection cannot cut a single space, so we have to stop - // in order to avoid endless loop :-( - if (searchstr.length() == 0 - || (searchstr.length() == 1 && searchstr[0] == ' ')) { -#ifdef WITH_WARNINGS -#warning BLECH. If we have an LFUN for replace, we can sort of fix this bogosity -#endif - Alert::error(_("Cannot replace"), - _("You cannot replace a single space or " - "an empty character.")); + if (searchstr.length() == 0) { + Alert::error(_("Search error"), _("Search string is empty")); return 0; } // now we can start searching for the first // start at top if replaceall + + if (replaceall) + return replace_all(bv, searchstr, replacestr, fw, cs, mw); + LyXText * text = bv->getLyXText(); - bool fw = forward; - if (replaceall) { - text->clearSelection(); - bv->unlockInset(bv->theLockingInset()); - text = bv->text; - text->cursorTop(); - // override search direction because we search top to bottom - fw = true; - } // if nothing selected or selection does not equal search string // search and select next occurance and return if no replaceall string str1; string str2; - if (casesens) { + if (cs) { str1 = searchstr; str2 = text->selectionAsString(*bv->buffer(), false); } else { @@ -197,16 +256,14 @@ int replace(BufferView * bv, str2 = lowercase(text->selectionAsString(*bv->buffer(), false)); } if (str1 != str2) { - if (!find(bv, searchstr, fw, casesens, matchwrd) || - !replaceall) { + if (!find(bv, searchstr, fw, cs, mw)) return 0; - } } bool found = false; int replace_count = 0; do { - text = bv->getLyXText(); + LyXText * text = bv->getLyXText(); // We have to do this check only because mathed insets don't // return their own LyXText but the LyXText of it's parent! if (!bv->theLockingInset() || @@ -217,8 +274,8 @@ int replace(BufferView * bv, ++replace_count; } if (!once) - found = find(bv, searchstr, fw, casesens, matchwrd); - } while (!once && replaceall && found); + found = find(bv, searchstr, fw, cs, mw); + } while (!once && found); // FIXME: should be called via an LFUN bv->buffer()->markDirty(); @@ -228,113 +285,22 @@ int replace(BufferView * bv, } -bool find(BufferView * bv, - string const & searchstr, bool forward, - bool casesens, bool matchwrd) +bool findNextChange(BufferView * bv) { - if (!bv->available() || searchstr.empty()) + if (!bv->available()) return false; - if (bv->theLockingInset()) { - bool found = forward ? - bv->theLockingInset()->searchForward(bv, searchstr, casesens, matchwrd) : - bv->theLockingInset()->searchBackward(bv, searchstr, casesens, matchwrd); - // We found the stuff inside the inset so we don't have to - // do anything as the inset did all the update for us! - if (found) - return true; - // We now are in the main text but if we did a forward - // search we have to put the cursor behind the inset. - if (forward) { - bv->text->cursorRight(true); - } - } - // If we arrive here we are in the main text again so we - // just start searching from the root LyXText at the position - // we are! - LyXText * text = bv->text; - - - if (text->selection.set()) - text->cursor = forward ? - text->selection.end : text->selection.start; - - text->clearSelection(); - - SearchResult result = forward ? - searchForward(bv, text, searchstr, casesens, matchwrd) : - searchBackward(bv, text, searchstr, casesens, matchwrd); - - bool found = true; - // If we found the cursor inside an inset we will get back - // SR_FOUND_NOUPDATE and we don't have to do anything as the - // inset did it already. - if (result == SR_FOUND) { - bv->unlockInset(bv->theLockingInset()); - text->setSelectionRange(searchstr.length()); - } else if (result == SR_NOT_FOUND) { - bv->unlockInset(bv->theLockingInset()); - found = false; - } - bv->update(); - - return found; -} - - -SearchResult find(BufferView * bv, LyXText * text, - string const & searchstr, bool forward, - bool casesens, bool matchwrd) -{ - if (text->selection.set()) - text->cursor = forward ? - text->selection.end : text->selection.start; - - text->clearSelection(); - - SearchResult result = forward ? - searchForward(bv, text, searchstr, casesens, matchwrd) : - searchBackward(bv, text, searchstr, casesens, matchwrd); - - return result; -} - - - - -SearchResult nextChange(BufferView * bv, LyXText * text, pos_type & length) -{ - ParagraphList::iterator pit = text->cursorPar(); - ParagraphList::iterator pend = text->ownerParagraphs().end(); - pos_type pos = text->cursor.pos(); - - while (pit != pend) { - pos_type parsize = pit->size(); - - if (pos < parsize) { - if ((!parsize || pos != parsize) - && pit->lookupChange(pos) != Change::UNCHANGED) - break; - - if (pit->isInset(pos) && pit->getInset(pos)->isTextInset()) { - UpdatableInset * inset = (UpdatableInset *)pit->getInset(pos); - if (inset->nextChange(bv, length)) - return SR_FOUND_NOUPDATE; - } - } - - ++pos; - - if (pos >= parsize) { - ++pit; - pos = 0; - } - } - - if (pit == pend) - return SR_NOT_FOUND; + PosIterator cur = PosIterator(*bv); + PosIterator endit(&bv->buffer()->paragraphs(), + bv->buffer()->paragraphs().end(), 0); - text->setCursor(pit, pos); + if (!findChange(cur, endit)) + return false; + + + ParagraphList::iterator pit = cur.pit(); + pos_type pos = cur.pos(); + Change orig_change = pit->lookupChangeFull(pos); pos_type parsize = pit->size(); pos_type end = pos; @@ -349,69 +315,9 @@ SearchResult nextChange(BufferView * bv, break; } } - length = end - pos; - return SR_FOUND; -} - - -SearchResult findNextChange(BufferView * bv, LyXText * text, pos_type & length) -{ - if (text->selection.set()) - text->cursor = text->selection.end; - - text->clearSelection(); - - return nextChange(bv, text, length); -} - - -bool findNextChange(BufferView * bv) -{ - if (!bv->available()) - return false; - - pos_type length; - - if (bv->theLockingInset()) { - bool found = bv->theLockingInset()->nextChange(bv, length); - - // We found the stuff inside the inset so we don't have to - // do anything as the inset did all the update for us! - if (found) - return true; - - // We now are in the main text but if we did a forward - // search we have to put the cursor behind the inset. - bv->text->cursorRight(true); - } - // If we arrive here we are in the main text again so we - // just start searching from the root LyXText at the position - // we are! - LyXText * text = bv->text; - - if (text->selection.set()) - text->cursor = text->selection.end; - - text->clearSelection(); - - SearchResult result = nextChange(bv, text, length); - - bool found = true; - - // If we found the cursor inside an inset we will get back - // SR_FOUND_NOUPDATE and we don't have to do anything as the - // inset did it already. - if (result == SR_FOUND) { - bv->unlockInset(bv->theLockingInset()); - text->setSelectionRange(length); - } else if (result == SR_NOT_FOUND) { - bv->unlockInset(bv->theLockingInset()); - found = false; - } - - bv->update(); - - return found; + pos_type length = end - pos; + put_selection_at(bv, cur, length, true); + return true; } } // find namespace Index: lyxfind.h =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/lyxfind.h,v retrieving revision 1.16 diff -u -p -u -r1.16 lyxfind.h --- lyxfind.h 7 Oct 2003 06:45:24 -0000 1.16 +++ lyxfind.h 31 Oct 2003 21:26:37 -0000 @@ -24,20 +24,10 @@ class LyXText; namespace lyx { namespace find { -enum SearchResult { - // - SR_NOT_FOUND = 0, - // - SR_FOUND, - // - SR_FOUND_NOUPDATE -}; - - int replace(BufferView * bv, - std::string const &, std::string const &, - bool, bool = true, bool = false, - bool = false, bool = false); + std::string const &, std::string const &, + bool, bool = true, bool = false, + bool = false, bool = false); /** * This function is called as a general interface to find some @@ -45,8 +35,8 @@ int replace(BufferView * bv, * we want to go. This does also update the screen. */ bool find(BufferView *, - std::string const & searchstr, bool forward, - bool casesens = true, bool matchwrd = false); + std::string const & searchstr, bool forward, + bool casesens = true, bool matchwrd = false); /** * This function does search from the cursor position inside the @@ -56,16 +46,8 @@ bool find(BufferView *, * returning to the calling function. */ -SearchResult find(BufferView *, LyXText * text, - std::string const & searchstr, bool forward, - bool casesens = true, bool matchwrd = false); - /// find the next change in the buffer bool findNextChange(BufferView * bv); - -SearchResult findNextChange(BufferView * bv, LyXText * text, lyx::pos_type & length); - -SearchResult nextChange(BufferView * bv, LyXText * text, lyx::pos_type & length); } // namespace find } // namespace lyx Index: paragraph.C =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/paragraph.C,v retrieving revision 1.340 diff -u -p -u -r1.340 paragraph.C --- paragraph.C 31 Oct 2003 18:45:34 -0000 1.340 +++ paragraph.C 31 Oct 2003 21:26:39 -0000 @@ -257,6 +257,14 @@ int Paragraph::erase(pos_type start, pos } +void Paragraph::insert(pos_type start, string const & str) +{ + int size = str.size(); + for (int i = 0 ; i < size ; ++i) + insertChar(start + i, str[i]); +} + + bool Paragraph::checkInsertChar(LyXFont & font) { if (pimpl_->inset_owner) Index: paragraph.h =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/paragraph.h,v retrieving revision 1.117 diff -u -p -u -r1.117 paragraph.h --- paragraph.h 31 Oct 2003 18:45:35 -0000 1.117 +++ paragraph.h 31 Oct 2003 21:26:40 -0000 @@ -271,6 +271,8 @@ public: lyx::pos_type endpos, LyXFont_size def_size) const; /// + void insert(lyx::pos_type pos, std::string const & str); + /// void insertChar(lyx::pos_type pos, value_type c); /// void insertChar(lyx::pos_type pos, value_type c, LyXFont const &, Change change = Change(Change::INSERTED)); Index: text.C =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/text.C,v retrieving revision 1.491 diff -u -p -u -r1.491 text.C --- text.C 29 Oct 2003 12:18:07 -0000 1.491 +++ text.C 31 Oct 2003 21:26:43 -0000 @@ -1592,7 +1592,7 @@ void LyXText::backspace() ParagraphList::iterator LyXText::cursorPar() const { - if (cursor.par() != cache_pos_) { + if (cursor.par() != cache_pos_ || cache_pos_ == -1) { cache_pos_ = cursor.par(); cache_par_ = getPar(cache_pos_); } Index: insets/inset.h =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/insets/inset.h,v retrieving revision 1.130 diff -u -p -u -r1.130 inset.h --- insets/inset.h 31 Oct 2003 18:45:38 -0000 1.130 +++ insets/inset.h 31 Oct 2003 21:26:46 -0000 @@ -239,8 +239,8 @@ public: /// virtual LyXText * getText(int /*num*/) const { return 0; } /// - virtual bool haveParagraphs() const { - return false; + virtual int numParagraphs() const { + return 0; } /// return the cursor if we own one otherwise giv'em just the Index: insets/insetcollapsable.C =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/insets/insetcollapsable.C,v retrieving revision 1.188 diff -u -p -u -r1.188 insetcollapsable.C --- insets/insetcollapsable.C 31 Oct 2003 18:45:38 -0000 1.188 +++ insets/insetcollapsable.C 31 Oct 2003 21:26:47 -0000 @@ -472,6 +472,12 @@ ParagraphList * InsetCollapsable::getPar } +int InsetCollapsable::numParagraphs() const +{ + return inset.numParagraphs(); +} + + LyXText * InsetCollapsable::getText(int i) const { return inset.getText(i); @@ -527,42 +533,6 @@ void InsetCollapsable::setCollapsed(bool void InsetCollapsable::markErased() { inset.markErased(); -} - - -bool InsetCollapsable::nextChange(BufferView * bv, lyx::pos_type & length) -{ - bool found = inset.nextChange(bv, length); - - if (first_after_edit && !found) - close(bv); - else if (!found) - first_after_edit = false; - return found; -} - - -bool InsetCollapsable::searchForward(BufferView * bv, string const & str, - bool cs, bool mw) -{ - bool found = inset.searchForward(bv, str, cs, mw); - if (first_after_edit && !found) - close(bv); - else if (!found) - first_after_edit = false; - return found; -} - - -bool InsetCollapsable::searchBackward(BufferView * bv, string const & str, - bool cs, bool mw) -{ - bool found = inset.searchBackward(bv, str, cs, mw); - if (first_after_edit && !found) - close(bv); - else if (!found) - first_after_edit = false; - return found; } Index: insets/insetcollapsable.h =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/insets/insetcollapsable.h,v retrieving revision 1.136 diff -u -p -u -r1.136 insetcollapsable.h --- insets/insetcollapsable.h 31 Oct 2003 18:45:38 -0000 1.136 +++ insets/insetcollapsable.h 31 Oct 2003 21:26:47 -0000 @@ -119,6 +119,8 @@ public: /// ParagraphList * getParagraphs(int) const; /// + int numParagraphs() const; + /// LyXText * getText(int) const; /// LyXCursor const & cursor(BufferView *) const; @@ -139,14 +141,6 @@ public: void selectSelectedWord(BufferView *); void markErased(); - - bool nextChange(BufferView * bv, lyx::pos_type & length); - - /// - bool searchForward(BufferView * bv, std::string const & str, - bool = true, bool = false); - bool searchBackward(BufferView * bv, std::string const & str, - bool = true, bool = false); /// void addPreview(lyx::graphics::PreviewLoader &) const; Index: insets/insettabular.C =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/insets/insettabular.C,v retrieving revision 1.359 diff -u -p -u -r1.359 insettabular.C --- insets/insettabular.C 31 Oct 2003 18:45:39 -0000 1.359 +++ insets/insettabular.C 31 Oct 2003 21:26:51 -0000 @@ -432,6 +432,9 @@ bool InsetTabular::lockInsetInInset(Buff oldcell = -1; + lyxerr[Debug::INSETTEXT] << "HERE1" << std::endl; + + if (inset == &tabular.getCellInset(actcell)) { lyxerr[Debug::INSETTEXT] << "OK" << endl; the_locking_inset = &tabular.getCellInset(actcell); @@ -439,27 +442,37 @@ bool InsetTabular::lockInsetInInset(Buff return true; } + lyxerr[Debug::INSETTEXT] << "HERE2" << std::endl; + if (!the_locking_inset) { int const n = tabular.getNumberOfCells(); int const id = inset->id(); for (int i = 0; i < n; ++i) { InsetText * in = &tabular.getCellInset(i); if (inset == in) { + lyxerr[Debug::INSETTEXT] << + "found!" << std::endl; actcell = i; the_locking_inset = in; locked = true; resetPos(bv); return true; } + /* if (in->getInsetFromID(id)) { actcell = i; in->dispatch(FuncRequest(bv, LFUN_INSET_EDIT)); return the_locking_inset->lockInsetInInset(bv, inset); } + */ } return false; } + lyxerr[Debug::INSETTEXT] << "HERE3" << std::endl; + + + if (the_locking_inset && (the_locking_inset == inset)) { lyxerr[Debug::INSETTEXT] << "OK" << endl; resetPos(bv); @@ -2391,6 +2404,12 @@ ParagraphList * InsetTabular::getParagra } +int InsetTabular::numParagraphs() const +{ + return tabular.getNumberOfCells(); +} + + LyXText * InsetTabular::getText(int i) const { return i < tabular.getNumberOfCells() @@ -2481,88 +2500,6 @@ void InsetTabular::markErased() { for (int cell = 0; cell < tabular.getNumberOfCells(); ++cell) tabular.getCellInset(cell).markErased(); -} - - -bool InsetTabular::nextChange(BufferView * bv, lyx::pos_type & length) -{ - if (the_locking_inset) { - if (the_locking_inset->nextChange(bv, length)) { - updateLocal(bv); - return true; - } - if (tabular.isLastCell(actcell)) - return false; - ++actcell; - } - InsetText & inset = tabular.getCellInset(actcell); - if (inset.nextChange(bv, length)) { - updateLocal(bv); - return true; - } - while (!tabular.isLastCell(actcell)) { - ++actcell; - InsetText & inset = tabular.getCellInset(actcell); - if (inset.nextChange(bv, length)) { - updateLocal(bv); - return true; - } - } - return false; -} - - -bool InsetTabular::searchForward(BufferView * bv, string const & str, - bool cs, bool mw) -{ - int cell = 0; - if (the_locking_inset) { - if (the_locking_inset->searchForward(bv, str, cs, mw)) { - updateLocal(bv); - return true; - } - if (tabular.isLastCell(actcell)) - return false; - cell = actcell + 1; - } - InsetText & inset = tabular.getCellInset(cell); - if (inset.searchForward(bv, str, cs, mw)) { - updateLocal(bv); - return true; - } - while (!tabular.isLastCell(cell)) { - ++cell; - InsetText & inset = tabular.getCellInset(cell); - if (inset.searchForward(bv, str, cs, mw)) { - updateLocal(bv); - return true; - } - } - return false; -} - - -bool InsetTabular::searchBackward(BufferView * bv, string const & str, - bool cs, bool mw) -{ - int cell = tabular.getNumberOfCells(); - if (the_locking_inset) { - if (the_locking_inset->searchBackward(bv, str, cs, mw)) { - updateLocal(bv); - return true; - } - cell = actcell; - } - - while (cell) { - --cell; - InsetText & inset = tabular.getCellInset(cell); - if (inset.searchBackward(bv, str, cs, mw)) { - updateLocal(bv); - return true; - } - } - return false; } Index: insets/insettabular.h =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/insets/insettabular.h,v retrieving revision 1.156 diff -u -p -u -r1.156 insettabular.h --- insets/insettabular.h 31 Oct 2003 18:45:40 -0000 1.156 +++ insets/insettabular.h 31 Oct 2003 21:26:51 -0000 @@ -162,6 +162,8 @@ public: /// ParagraphList * getParagraphs(int) const; /// + int numParagraphs() const; + /// LyXText * getText(int) const; /// LyXCursor const & cursor(BufferView *) const; @@ -174,14 +176,6 @@ public: void selectSelectedWord(BufferView *); void markErased(); - - /// find next change - bool nextChange(BufferView *, lyx::pos_type & length); - /// - bool searchForward(BufferView *, std::string const &, - bool = true, bool = false); - bool searchBackward(BufferView *, std::string const &, - bool = true, bool = false); // this should return true if we have a "normal" cell, otherwise true. // "normal" means without width set! Index: insets/insettext.C =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/insets/insettext.C,v retrieving revision 1.520 diff -u -p -u -r1.520 insettext.C --- insets/insettext.C 31 Oct 2003 18:45:41 -0000 1.520 +++ insets/insettext.C 31 Oct 2003 21:26:53 -0000 @@ -369,6 +369,7 @@ void InsetText::lockInset(BufferView * b font.setLanguage(bv->getParentLanguage(this)); setFont(bv, font, false); } + lyxerr << "HERE" << std::endl; } @@ -1490,81 +1491,6 @@ void InsetText::selectSelectedWord(Buffe getLyXText(bv)->selectSelectedWord(); updateLocal(bv, false); } - - -bool InsetText::nextChange(BufferView * bv, lyx::pos_type & length) -{ - if (the_locking_inset) { - if (the_locking_inset->nextChange(bv, length)) - return true; - text_.cursorRight(true); - } - lyx::find::SearchResult result = - lyx::find::findNextChange(bv, &text_, length); - - if (result == lyx::find::SR_FOUND) { - LyXCursor cur = text_.cursor; - bv->unlockInset(bv->theLockingInset()); - if (bv->lockInset(this)) - locked = true; - text_.cursor = cur; - text_.setSelectionRange(length); - updateLocal(bv, false); - } - return result != lyx::find::SR_NOT_FOUND; -} - - -bool InsetText::searchForward(BufferView * bv, string const & str, - bool cs, bool mw) -{ - if (the_locking_inset) { - if (the_locking_inset->searchForward(bv, str, cs, mw)) - return true; - text_.cursorRight(true); - } - lyx::find::SearchResult result = - lyx::find::find(bv, &text_, str, true, cs, mw); - - if (result == lyx::find::SR_FOUND) { - LyXCursor cur = text_.cursor; - bv->unlockInset(bv->theLockingInset()); - if (bv->lockInset(this)) - locked = true; - text_.cursor = cur; - text_.setSelectionRange(str.length()); - updateLocal(bv, false); - } - return result != lyx::find::SR_NOT_FOUND; -} - - -bool InsetText::searchBackward(BufferView * bv, string const & str, - bool cs, bool mw) -{ - if (the_locking_inset) { - if (the_locking_inset->searchBackward(bv, str, cs, mw)) - return true; - } - if (!locked) { - text_.setCursor(paragraphs.size() - 1, paragraphs.back().size()); - } - lyx::find::SearchResult result = - lyx::find::find(bv, &text_, str, false, cs, mw); - - if (result == lyx::find::SR_FOUND) { - LyXCursor cur = text_.cursor; - bv->unlockInset(bv->theLockingInset()); - if (bv->lockInset(this)) - locked = true; - text_.cursor = cur; - text_.setSelectionRange(str.length()); - updateLocal(bv, false); - } - return result != lyx::find::SR_NOT_FOUND; -} - - bool InsetText::checkInsertChar(LyXFont & font) { return owner() ? owner()->checkInsertChar(font) : true; Index: insets/insettext.h =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/insets/insettext.h,v retrieving revision 1.218 diff -u -p -u -r1.218 insettext.h --- insets/insettext.h 31 Oct 2003 18:45:41 -0000 1.218 +++ insets/insettext.h 31 Oct 2003 21:26:53 -0000 @@ -177,16 +177,8 @@ public: * for the (empty) paragraph contained. */ void markNew(bool track_changes = false); - /// find next change - bool nextChange(BufferView *, lyx::pos_type & length); /// - bool searchForward(BufferView *, std::string const &, - bool = true, bool = false); - /// - bool searchBackward(BufferView *, std::string const &, - bool = true, bool = false); - /// bool checkInsertChar(LyXFont &); /// void getDrawFont(LyXFont &) const; @@ -197,8 +189,8 @@ public: void addPreview(lyx::graphics::PreviewLoader &) const; /// - bool haveParagraphs() const { - return true; + int numParagraphs() const { + return 1; } /// mutable ParagraphList paragraphs; Index: insets/updatableinset.C =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/insets/updatableinset.C,v retrieving revision 1.30 diff -u -p -u -r1.30 updatableinset.C --- insets/updatableinset.C 29 Oct 2003 19:19:26 -0000 1.30 +++ insets/updatableinset.C 31 Oct 2003 21:26:53 -0000 @@ -157,19 +157,3 @@ bool UpdatableInset::nextChange(BufferVi } -bool UpdatableInset::searchForward(BufferView * bv, string const &, - bool, bool) -{ - // we have to unlock ourself in this function by default! - bv->unlockInset(const_cast<UpdatableInset *>(this)); - return false; -} - - -bool UpdatableInset::searchBackward(BufferView * bv, string const &, - bool, bool) -{ - // we have to unlock ourself in this function by default! - bv->unlockInset(const_cast<UpdatableInset *>(this)); - return false; -} Index: insets/updatableinset.h =================================================================== RCS file: /usr/local/lyx/cvsroot/lyx-devel/src/insets/updatableinset.h,v retrieving revision 1.20 diff -u -p -u -r1.20 updatableinset.h --- insets/updatableinset.h 29 Oct 2003 10:47:19 -0000 1.20 +++ insets/updatableinset.h 31 Oct 2003 21:26:54 -0000 @@ -101,15 +101,6 @@ public: /// find the next change in the inset virtual bool nextChange(BufferView * bv, lyx::pos_type & length); - /// - // needed for search/replace functionality - /// - virtual bool searchForward(BufferView *, std::string const &, - bool = true, bool = false); - /// - virtual bool searchBackward(BufferView *, std::string const &, - bool = true, bool = false); - protected: /// An updatable inset could handle lyx editing commands virtual