forked from qt-creator/qt-creator
Fix find scope expanding
We now use two cursors, with the first one being positioned at the character before the find scope starts. This makes it possible to extend the scope when typing at the beginning or the end of it. This is more what the user expects. The effect is noticable with find&replace of words at the beginning or end of the scope.
This commit is contained in:
@@ -205,8 +205,8 @@ int BaseTextFind::replaceAll(const QString &before, const QString &after,
|
|||||||
IFindSupport::FindFlags findFlags)
|
IFindSupport::FindFlags findFlags)
|
||||||
{
|
{
|
||||||
QTextCursor editCursor = textCursor();
|
QTextCursor editCursor = textCursor();
|
||||||
if (!m_findScope.isNull())
|
if (!m_findScopeStart.isNull())
|
||||||
editCursor.setPosition(m_findScope.selectionStart());
|
editCursor.setPosition(m_findScopeStart.position());
|
||||||
else
|
else
|
||||||
editCursor.movePosition(QTextCursor::Start);
|
editCursor.movePosition(QTextCursor::Start);
|
||||||
editCursor.beginEditBlock();
|
editCursor.beginEditBlock();
|
||||||
@@ -243,14 +243,14 @@ bool BaseTextFind::find(const QString &txt,
|
|||||||
regexp.setCaseSensitivity((findFlags&IFindSupport::FindCaseSensitively) ? Qt::CaseSensitive : Qt::CaseInsensitive);
|
regexp.setCaseSensitivity((findFlags&IFindSupport::FindCaseSensitively) ? Qt::CaseSensitive : Qt::CaseInsensitive);
|
||||||
QTextCursor found = findOne(regexp, start, IFindSupport::textDocumentFlagsForFindFlags(findFlags));
|
QTextCursor found = findOne(regexp, start, IFindSupport::textDocumentFlagsForFindFlags(findFlags));
|
||||||
|
|
||||||
if (!m_findScope.isNull()) {
|
if (!m_findScopeStart.isNull()) {
|
||||||
|
|
||||||
// scoped
|
// scoped
|
||||||
if (found.isNull() || !inScope(found.selectionStart(), found.selectionEnd())) {
|
if (found.isNull() || !inScope(found.selectionStart(), found.selectionEnd())) {
|
||||||
if ((findFlags&IFindSupport::FindBackward) == 0)
|
if ((findFlags&IFindSupport::FindBackward) == 0)
|
||||||
start.setPosition(m_findScope.selectionStart());
|
start.setPosition(m_findScopeStart.position());
|
||||||
else
|
else
|
||||||
start.setPosition(m_findScope.selectionEnd());
|
start.setPosition(m_findScopeEnd.position());
|
||||||
found = findOne(regexp, start, IFindSupport::textDocumentFlagsForFindFlags(findFlags));
|
found = findOne(regexp, start, IFindSupport::textDocumentFlagsForFindFlags(findFlags));
|
||||||
if (found.isNull() || !inScope(found.selectionStart(), found.selectionEnd()))
|
if (found.isNull() || !inScope(found.selectionStart(), found.selectionEnd()))
|
||||||
return false;
|
return false;
|
||||||
@@ -289,8 +289,8 @@ QTextCursor BaseTextFind::findOne(const QRegExp &expr, const QTextCursor &from,
|
|||||||
b.setPosition(candidate.selectionStart());
|
b.setPosition(candidate.selectionStart());
|
||||||
QTextCursor e = candidate;
|
QTextCursor e = candidate;
|
||||||
e.setPosition(candidate.selectionEnd());
|
e.setPosition(candidate.selectionEnd());
|
||||||
if (b.positionInBlock() >= m_findScopeFromColumn
|
if (b.positionInBlock() >= m_findScopeStart.positionInBlock() + 1
|
||||||
&& e.positionInBlock() <= m_findScopeToColumn)
|
&& e.positionInBlock() <= m_findScopeStart.positionInBlock() + 1 + m_findScopeVerticalBlockSelection)
|
||||||
return candidate;
|
return candidate;
|
||||||
candidate = document()->find(expr, candidate, options);
|
candidate = document()->find(expr, candidate, options);
|
||||||
}
|
}
|
||||||
@@ -299,17 +299,18 @@ QTextCursor BaseTextFind::findOne(const QRegExp &expr, const QTextCursor &from,
|
|||||||
|
|
||||||
bool BaseTextFind::inScope(int startPosition, int endPosition) const
|
bool BaseTextFind::inScope(int startPosition, int endPosition) const
|
||||||
{
|
{
|
||||||
if (m_findScope.isNull())
|
if (m_findScopeStart.isNull())
|
||||||
return true;
|
return true;
|
||||||
return (m_findScope.selectionStart() <= startPosition
|
return (m_findScopeStart.position() <= startPosition
|
||||||
&& m_findScope.selectionEnd() >= endPosition);
|
&& m_findScopeEnd.position() >= endPosition);
|
||||||
}
|
}
|
||||||
|
|
||||||
void BaseTextFind::defineFindScope()
|
void BaseTextFind::defineFindScope()
|
||||||
{
|
{
|
||||||
QTextCursor cursor = textCursor();
|
QTextCursor cursor = textCursor();
|
||||||
if (cursor.hasSelection() && cursor.block() != cursor.document()->findBlock(cursor.anchor())) {
|
if (cursor.hasSelection() && cursor.block() != cursor.document()->findBlock(cursor.anchor())) {
|
||||||
m_findScope = cursor;
|
m_findScopeStart = QTextCursor(document()->docHandle(), qMax(0, cursor.selectionStart()-1));
|
||||||
|
m_findScopeEnd = QTextCursor(document()->docHandle(), cursor.selectionEnd());
|
||||||
m_findScopeVerticalBlockSelection = false;
|
m_findScopeVerticalBlockSelection = false;
|
||||||
|
|
||||||
int verticalBlockSelection = 0;
|
int verticalBlockSelection = 0;
|
||||||
@@ -317,18 +318,16 @@ void BaseTextFind::defineFindScope()
|
|||||||
verticalBlockSelection = m_plaineditor->property("verticalBlockSelection").toInt();
|
verticalBlockSelection = m_plaineditor->property("verticalBlockSelection").toInt();
|
||||||
|
|
||||||
if (verticalBlockSelection) {
|
if (verticalBlockSelection) {
|
||||||
QTextDocument *doc = document();
|
int findScopeFromColumn = qMin(m_findScopeStart.positionInBlock()+1,
|
||||||
QTextCursor b(doc->docHandle(), cursor.selectionStart());
|
m_findScopeEnd.positionInBlock());
|
||||||
QTextCursor e(doc->docHandle(), cursor.selectionEnd());
|
int findScopeToColumn = findScopeFromColumn + verticalBlockSelection;
|
||||||
m_findScopeFromColumn = qMin(b.positionInBlock(), e.positionInBlock());
|
m_findScopeStart.setPosition(m_findScopeStart.block().position() + findScopeFromColumn - 1);
|
||||||
m_findScopeToColumn = m_findScopeFromColumn + verticalBlockSelection;
|
m_findScopeEnd.setPosition(m_findScopeEnd.block().position()
|
||||||
m_findScope.setPosition(b.block().position() + m_findScopeFromColumn);
|
+ qMin(m_findScopeEnd.block().length()-1, findScopeToColumn));
|
||||||
m_findScope.setPosition(e.block().position() + qMin(e.block().length()-1, m_findScopeToColumn),
|
|
||||||
QTextCursor::KeepAnchor);
|
|
||||||
m_findScopeVerticalBlockSelection = verticalBlockSelection;
|
m_findScopeVerticalBlockSelection = verticalBlockSelection;
|
||||||
}
|
}
|
||||||
emit findScopeChanged(m_findScope, m_findScopeVerticalBlockSelection);
|
emit findScopeChanged(m_findScopeStart, m_findScopeEnd, m_findScopeVerticalBlockSelection);
|
||||||
cursor.setPosition(m_findScope.selectionStart());
|
cursor.setPosition(m_findScopeStart.position()+1);
|
||||||
setTextCursor(cursor);
|
setTextCursor(cursor);
|
||||||
} else {
|
} else {
|
||||||
clearFindScope();
|
clearFindScope();
|
||||||
@@ -337,7 +336,8 @@ void BaseTextFind::defineFindScope()
|
|||||||
|
|
||||||
void BaseTextFind::clearFindScope()
|
void BaseTextFind::clearFindScope()
|
||||||
{
|
{
|
||||||
m_findScope = QTextCursor();
|
m_findScopeStart = QTextCursor();
|
||||||
|
m_findScopeEnd = QTextCursor();
|
||||||
m_findScopeVerticalBlockSelection = 0;
|
m_findScopeVerticalBlockSelection = 0;
|
||||||
emit findScopeChanged(m_findScope, m_findScopeVerticalBlockSelection);
|
emit findScopeChanged(m_findScopeStart, m_findScopeEnd, m_findScopeVerticalBlockSelection);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -70,7 +70,7 @@ public:
|
|||||||
|
|
||||||
signals:
|
signals:
|
||||||
void highlightAll(const QString &txt, Find::IFindSupport::FindFlags findFlags);
|
void highlightAll(const QString &txt, Find::IFindSupport::FindFlags findFlags);
|
||||||
void findScopeChanged(const QTextCursor &, int = 0);
|
void findScopeChanged(const QTextCursor &start, const QTextCursor &end, int verticalBlockSelection);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
bool find(const QString &txt,
|
bool find(const QString &txt,
|
||||||
@@ -83,10 +83,9 @@ private:
|
|||||||
bool isReadOnly() const;
|
bool isReadOnly() const;
|
||||||
QPointer<QTextEdit> m_editor;
|
QPointer<QTextEdit> m_editor;
|
||||||
QPointer<QPlainTextEdit> m_plaineditor;
|
QPointer<QPlainTextEdit> m_plaineditor;
|
||||||
QTextCursor m_findScope;
|
QTextCursor m_findScopeStart;
|
||||||
|
QTextCursor m_findScopeEnd;
|
||||||
int m_findScopeVerticalBlockSelection;
|
int m_findScopeVerticalBlockSelection;
|
||||||
int m_findScopeFromColumn;
|
|
||||||
int m_findScopeToColumn;
|
|
||||||
bool inScope(int startPosition, int endPosition) const;
|
bool inScope(int startPosition, int endPosition) const;
|
||||||
QTextCursor findOne(const QRegExp &expr, const QTextCursor &from, QTextDocument::FindFlags options) const;
|
QTextCursor findOne(const QRegExp &expr, const QTextCursor &from, QTextDocument::FindFlags options) const;
|
||||||
int m_incrementalStartPos;
|
int m_incrementalStartPos;
|
||||||
|
|||||||
@@ -2197,10 +2197,8 @@ void BaseTextEditorPrivate::highlightSearchResults(const QTextBlock &block,
|
|||||||
int l = 1;
|
int l = 1;
|
||||||
|
|
||||||
int m_findScopeFirstColumn = 0;
|
int m_findScopeFirstColumn = 0;
|
||||||
if (!m_findScope.isNull() && m_findScopeVerticalBlockSelection) {
|
if (!m_findScopeStart.isNull() && m_findScopeVerticalBlockSelection) {
|
||||||
QTextCursor b = cursor;
|
m_findScopeFirstColumn = m_findScopeStart.positionInBlock() + 1;
|
||||||
cursor.setPosition(m_findScope.selectionStart());
|
|
||||||
m_findScopeFirstColumn = cursor.positionInBlock();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -2214,9 +2212,9 @@ void BaseTextEditorPrivate::highlightSearchResults(const QTextBlock &block,
|
|||||||
|| (idx + l < text.length() && text.at(idx + l).isLetterOrNumber())))
|
|| (idx + l < text.length() && text.at(idx + l).isLetterOrNumber())))
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
if (!m_findScope.isNull()) {
|
if (!m_findScopeStart.isNull()) {
|
||||||
if (blockPosition + idx < m_findScope.selectionStart()
|
if (blockPosition + idx < m_findScopeStart.position()
|
||||||
|| blockPosition + idx + l > m_findScope.selectionEnd())
|
|| blockPosition + idx + l > m_findScopeEnd.position())
|
||||||
continue;
|
continue;
|
||||||
if (m_findScopeVerticalBlockSelection) {
|
if (m_findScopeVerticalBlockSelection) {
|
||||||
if (idx < m_findScopeFirstColumn
|
if (idx < m_findScopeFirstColumn
|
||||||
@@ -2487,12 +2485,18 @@ void BaseTextEditor::paintEvent(QPaintEvent *e)
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
if (!d->m_findScope.isNull()) {
|
if (!d->m_findScopeStart.isNull()) {
|
||||||
|
|
||||||
TextEditorOverlay *overlay = new TextEditorOverlay(this);
|
TextEditorOverlay *overlay = new TextEditorOverlay(this);
|
||||||
overlay->addOverlaySelection(d->m_findScope, d->m_searchScopeFormat.background().color().darker(120),
|
overlay->addOverlaySelection(d->m_findScopeStart.position(),
|
||||||
|
d->m_findScopeVerticalBlockSelection ?
|
||||||
|
d->m_findScopeEnd.block().position()
|
||||||
|
+ d->m_findScopeVerticalBlockSelection
|
||||||
|
+ d->m_findScopeStart.positionInBlock() + 1
|
||||||
|
: d->m_findScopeEnd.position(),
|
||||||
|
d->m_searchScopeFormat.background().color().darker(120),
|
||||||
d->m_searchScopeFormat.background().color(),
|
d->m_searchScopeFormat.background().color(),
|
||||||
0,
|
TextEditorOverlay::ExpandBegin,
|
||||||
d->m_findScopeVerticalBlockSelection);
|
d->m_findScopeVerticalBlockSelection);
|
||||||
overlay->setAlpha(false);
|
overlay->setAlpha(false);
|
||||||
overlay->paint(&painter, e->rect());
|
overlay->paint(&painter, e->rect());
|
||||||
@@ -3367,14 +3371,14 @@ void BaseTextEditor::slotUpdateBlockNotify(const QTextBlock &block)
|
|||||||
box which now is invalid.*/
|
box which now is invalid.*/
|
||||||
emit requestBlockUpdate(block.previous());
|
emit requestBlockUpdate(block.previous());
|
||||||
}
|
}
|
||||||
if (!d->m_findScope.isNull()) {
|
if (!d->m_findScopeStart.isNull()) {
|
||||||
if (block.position() < d->m_findScope.selectionEnd()
|
if (block.position() < d->m_findScopeEnd.position()
|
||||||
&& block.position()+block.length() >= d->m_findScope.selectionStart() ) {
|
&& block.position()+block.length() >= d->m_findScopeStart.position()) {
|
||||||
QTextBlock b = block.document()->findBlock(d->m_findScope.selectionStart());
|
QTextBlock b = block.document()->findBlock(d->m_findScopeStart.position());
|
||||||
do {
|
do {
|
||||||
emit requestBlockUpdate(b);
|
emit requestBlockUpdate(b);
|
||||||
b = b.next();
|
b = b.next();
|
||||||
} while (b.isValid() && b.position() < d->m_findScope.selectionEnd());
|
} while (b.isValid() && b.position() < d->m_findScopeEnd.position());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -4704,10 +4708,11 @@ int BaseTextEditor::verticalBlockSelection() const
|
|||||||
return qAbs(b.positionInBlock() - e.positionInBlock()) + d->m_blockSelectionExtraX;
|
return qAbs(b.positionInBlock() - e.positionInBlock()) + d->m_blockSelectionExtraX;
|
||||||
}
|
}
|
||||||
|
|
||||||
void BaseTextEditor::setFindScope(const QTextCursor &scope, int verticalBlockSelection)
|
void BaseTextEditor::setFindScope(const QTextCursor &start, const QTextCursor &end, int verticalBlockSelection)
|
||||||
{
|
{
|
||||||
if (scope.isNull() != d->m_findScope.isNull()) {
|
if (start != d->m_findScopeStart || end != d->m_findScopeEnd) {
|
||||||
d->m_findScope = scope;
|
d->m_findScopeStart = start;
|
||||||
|
d->m_findScopeEnd = end;
|
||||||
d->m_findScopeVerticalBlockSelection = verticalBlockSelection;
|
d->m_findScopeVerticalBlockSelection = verticalBlockSelection;
|
||||||
viewport()->update();
|
viewport()->update();
|
||||||
}
|
}
|
||||||
@@ -5659,7 +5664,8 @@ BaseTextEditorEditable::BaseTextEditorEditable(BaseTextEditor *editor)
|
|||||||
BaseTextFind *baseTextFind = new BaseTextFind(editor);
|
BaseTextFind *baseTextFind = new BaseTextFind(editor);
|
||||||
connect(baseTextFind, SIGNAL(highlightAll(QString, Find::IFindSupport::FindFlags)),
|
connect(baseTextFind, SIGNAL(highlightAll(QString, Find::IFindSupport::FindFlags)),
|
||||||
editor, SLOT(highlightSearchResults(QString, Find::IFindSupport::FindFlags)));
|
editor, SLOT(highlightSearchResults(QString, Find::IFindSupport::FindFlags)));
|
||||||
connect(baseTextFind, SIGNAL(findScopeChanged(QTextCursor, int)), editor, SLOT(setFindScope(QTextCursor, int)));
|
connect(baseTextFind, SIGNAL(findScopeChanged(QTextCursor, QTextCursor, int)),
|
||||||
|
editor, SLOT(setFindScope(QTextCursor, QTextCursor, int)));
|
||||||
aggregate->add(baseTextFind);
|
aggregate->add(baseTextFind);
|
||||||
aggregate->add(editor);
|
aggregate->add(editor);
|
||||||
|
|
||||||
|
|||||||
@@ -461,7 +461,7 @@ private slots:
|
|||||||
void memorizeCursorPosition();
|
void memorizeCursorPosition();
|
||||||
void restoreCursorPosition();
|
void restoreCursorPosition();
|
||||||
void highlightSearchResults(const QString &txt, Find::IFindSupport::FindFlags findFlags);
|
void highlightSearchResults(const QString &txt, Find::IFindSupport::FindFlags findFlags);
|
||||||
void setFindScope(const QTextCursor &, int);
|
void setFindScope(const QTextCursor &start, const QTextCursor &end, int);
|
||||||
void currentEditorChanged(Core::IEditor *editor);
|
void currentEditorChanged(Core::IEditor *editor);
|
||||||
void maybeEmitContentsChangedBecauseOfUndo();
|
void maybeEmitContentsChangedBecauseOfUndo();
|
||||||
|
|
||||||
|
|||||||
@@ -249,7 +249,8 @@ public:
|
|||||||
void removeBlockSelection(const QString &text = QString());
|
void removeBlockSelection(const QString &text = QString());
|
||||||
bool m_moveLineUndoHack;
|
bool m_moveLineUndoHack;
|
||||||
|
|
||||||
QTextCursor m_findScope;
|
QTextCursor m_findScopeStart;
|
||||||
|
QTextCursor m_findScopeEnd;
|
||||||
int m_findScopeVerticalBlockSelection;
|
int m_findScopeVerticalBlockSelection;
|
||||||
QTextCursor m_selectBlockAnchor;
|
QTextCursor m_selectBlockAnchor;
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user