3 * This file is part of LyX, the document processor.
4 * Licence details can be found in the file COPYING.
6 * \author Lars Gullik Bjønnes
9 * Full author contact details are available in file CREDITS
11 * This file contains some utility functions for actually mutating
12 * the text contents of a document
18 #include "lyxcursor.h"
19 #include "ParagraphList.h"
21 #include "support/types.h"
23 #include <boost/next_prior.hpp>
26 using lyx::word_location;
29 bool transposeChars(LyXCursor const & cursor)
31 ParagraphList::iterator tmppit = cursor.par();
32 pos_type tmppos = cursor.pos();
34 // First decide if it is possible to transpose at all
36 if (tmppos == 0 || tmppos == tmppit->size())
39 if (isDeletedText(*tmppit, tmppos - 1)
40 || isDeletedText(*tmppit, tmppos))
43 unsigned char c1 = tmppit->getChar(tmppos);
44 unsigned char c2 = tmppit->getChar(tmppos - 1);
46 // We should have an implementation that handles insets
47 // as well, but that will have to come later. (Lgb)
48 if (c1 == Paragraph::META_INSET || c2 == Paragraph::META_INSET)
51 bool const erased = tmppit->erase(tmppos - 1, tmppos + 1);
52 size_t const ipos = erased ? tmppos - 1 : tmppos + 1;
54 tmppit->insertChar(ipos, c1);
55 tmppit->insertChar(ipos + 1, c2);
60 void cursorLeftOneWord(LyXCursor & cursor, ParagraphList const & pars)
62 // treat HFills, floats and Insets as words
64 ParagraphList::iterator pit = cursor.par();
65 size_t pos = cursor.pos();
68 (pit->isSeparator(pos - 1) ||
69 pit->isKomma(pos - 1) ||
70 pit->isNewline(pos - 1)) &&
71 !(pit->isHfill(pos - 1) ||
72 pit->isInset(pos - 1)))
76 (pit->isInset(pos - 1) ||
77 pit->isHfill(pos - 1))) {
80 // cast only for BSD's g++ 2.95
81 if (pit != const_cast<ParagraphList &>(pars).begin()) {
85 } else { // Here, cur != 0
86 while (pos > 0 && pit->isWord(pos - 1))
95 void cursorRightOneWord(LyXCursor & cursor, ParagraphList const & pars)
97 // treat floats, HFills and Insets as words
98 ParagraphList::iterator pit = cursor.par();
99 pos_type pos = cursor.pos();
101 // CHECK See comment on top of text.C
103 // cast only for BSD's g++ 2.95
104 if (pos == pit->size() &&
105 boost::next(pit) != const_cast<ParagraphList &>(pars).end()) {
109 // Skip through initial nonword stuff.
110 while (pos < pit->size() && !pit->isWord(pos)) {
113 // Advance through word.
114 while (pos < pit->size() && pit->isWord(pos)) {
124 // Select current word. This depends on behaviour of
125 // CursorLeftOneWord(), so it is patched as well.
126 void getWord(LyXCursor & from, LyXCursor & to, word_location const loc,
127 ParagraphList const & pars)
130 case lyx::WHOLE_WORD_STRICT:
131 if (from.pos() == 0 || from.pos() == from.par()->size()
132 || from.par()->isSeparator(from.pos())
133 || from.par()->isKomma(from.pos())
134 || from.par()->isNewline(from.pos())
135 || from.par()->isSeparator(from.pos() - 1)
136 || from.par()->isKomma(from.pos() - 1)
137 || from.par()->isNewline(from.pos() - 1)) {
141 // no break here, we go to the next
143 case lyx::WHOLE_WORD:
144 // Move cursor to the beginning, when not already there.
145 if (from.pos() && !from.par()->isSeparator(from.pos() - 1)
146 && !(from.par()->isKomma(from.pos() - 1)
147 || from.par()->isNewline(from.pos() - 1)))
148 cursorLeftOneWord(from, pars);
150 case lyx::PREVIOUS_WORD:
151 // always move the cursor to the beginning of previous word
152 cursorLeftOneWord(from, pars);
155 lyxerr << "LyXText::getWord: NEXT_WORD not implemented yet\n";
157 case lyx::PARTIAL_WORD:
161 while (to.pos() < to.par()->size()
162 && !to.par()->isSeparator(to.pos())
163 && !to.par()->isKomma(to.pos())
164 && !to.par()->isNewline(to.pos())
165 && !to.par()->isHfill(to.pos())
166 && !to.par()->isInset(to.pos()))
168 to.pos(to.pos() + 1);