diff options
author | Nikolai Kosjar <nikolai.kosjar@digia.com> | 2013-08-01 10:14:10 +0200 |
---|---|---|
committer | Nikolai Kosjar <nikolai.kosjar@digia.com> | 2013-08-22 09:42:22 +0200 |
commit | ef018ddd9ecf87338c58c5747904fcd81c06bbc5 (patch) | |
tree | 95af78bdbc2670c87fdca7934aef2577bb04437d | |
parent | 541a717933db3f5f83699f412d9268c0fe590e71 (diff) | |
download | qt-creator-ef018ddd9ecf87338c58c5747904fcd81c06bbc5.tar.gz |
Locator: Case sensitivity of input affects prioritizing
So far candidates were prefix matched case sensitive which led to
an unfavorable results order.
With this patch, if the input is lower case, the prioritizing happens by
a case insensitive prefix match. Otherwise the match happens case
sensitive (just like before).
Example:
Search for e.g. "m cppmodelmanager"
Top result before: AbstractEditorSupport (match at parameter type)
Top result now: CppModelManager
Change-Id: Ic27042cfe717be812a2237a3437399597c98dd74
Reviewed-by: Orgad Shaneh <orgads@gmail.com>
Reviewed-by: David Schulz <david.schulz@digia.com>
-rw-r--r-- | src/plugins/coreplugin/helpmanager.cpp | 5 | ||||
-rw-r--r-- | src/plugins/coreplugin/helpmanager.h | 4 | ||||
-rw-r--r-- | src/plugins/cpptools/cppcurrentdocumentfilter.cpp | 4 | ||||
-rw-r--r-- | src/plugins/cpptools/cpplocatorfilter.cpp | 3 | ||||
-rw-r--r-- | src/plugins/cpptools/cpplocatorfilter_test.cpp | 6 | ||||
-rw-r--r-- | src/plugins/help/helpindexfilter.cpp | 4 | ||||
-rw-r--r-- | src/plugins/locator/basefilefilter.cpp | 3 | ||||
-rw-r--r-- | src/plugins/locator/commandlocator.cpp | 5 | ||||
-rw-r--r-- | src/plugins/locator/executefilter.cpp | 3 | ||||
-rw-r--r-- | src/plugins/locator/filesystemfilter.cpp | 32 | ||||
-rw-r--r-- | src/plugins/locator/ilocatorfilter.cpp | 5 | ||||
-rw-r--r-- | src/plugins/locator/ilocatorfilter.h | 1 | ||||
-rw-r--r-- | src/plugins/locator/opendocumentsfilter.cpp | 25 | ||||
-rw-r--r-- | src/plugins/macros/macrolocatorfilter.cpp | 18 | ||||
-rw-r--r-- | src/plugins/qmljstools/qmljsfunctionfilter.cpp | 3 |
15 files changed, 86 insertions, 35 deletions
diff --git a/src/plugins/coreplugin/helpmanager.cpp b/src/plugins/coreplugin/helpmanager.cpp index 9ac08d4c5b..49ca75161e 100644 --- a/src/plugins/coreplugin/helpmanager.cpp +++ b/src/plugins/coreplugin/helpmanager.cpp @@ -222,7 +222,8 @@ QMap<QString, QUrl> HelpManager::linksForIdentifier(const QString &id) const } // This should go into Qt 4.8 once we start using it for Qt Creator -QStringList HelpManager::findKeywords(const QString &key, int maxHits) const +QStringList HelpManager::findKeywords(const QString &key, Qt::CaseSensitivity caseSensitivity, + int maxHits) const { if (d->m_needsSetup) return QStringList(); @@ -251,7 +252,7 @@ QStringList HelpManager::findKeywords(const QString &key, int maxHits) const while (query.next()) { const QString &keyValue = query.value(0).toString(); if (!keyValue.isEmpty()) { - if (keyValue.startsWith(key, Qt::CaseInsensitive)) + if (keyValue.startsWith(key, caseSensitivity)) keywordsToSort.insert(keyValue); else keywords.insert(keyValue); diff --git a/src/plugins/coreplugin/helpmanager.h b/src/plugins/coreplugin/helpmanager.h index 59c406eb93..5fc41cad29 100644 --- a/src/plugins/coreplugin/helpmanager.h +++ b/src/plugins/coreplugin/helpmanager.h @@ -63,7 +63,9 @@ public: QMap<QString, QUrl> linksForKeyword(const QString &key) const; QMap<QString, QUrl> linksForIdentifier(const QString &id) const; - QStringList findKeywords(const QString &key, int maxHits = INT_MAX) const; + QStringList findKeywords(const QString &key, + Qt::CaseSensitivity caseSensitivity = Qt::CaseInsensitive, + int maxHits = INT_MAX) const; QUrl findFile(const QUrl &url) const; QByteArray fileData(const QUrl &url) const; diff --git a/src/plugins/cpptools/cppcurrentdocumentfilter.cpp b/src/plugins/cpptools/cppcurrentdocumentfilter.cpp index b18fdbf2a4..2e4809971c 100644 --- a/src/plugins/cpptools/cppcurrentdocumentfilter.cpp +++ b/src/plugins/cpptools/cppcurrentdocumentfilter.cpp @@ -81,6 +81,8 @@ QList<Locator::FilterEntry> CppCurrentDocumentFilter::matchesFor(QFutureInterfac m_itemsOfCurrentDoc = search(thisDocument); } + const Qt::CaseSensitivity caseSensitivityForPrefix = caseSensitivity(entry); + foreach (const ModelItemInfo & info, m_itemsOfCurrentDoc) { if (future.isCanceled()) @@ -94,7 +96,7 @@ QList<Locator::FilterEntry> CppCurrentDocumentFilter::matchesFor(QFutureInterfac Locator::FilterEntry filterEntry(this, symbolName, id, info.icon); filterEntry.extraInfo = info.symbolType; - if (info.symbolName.startsWith(entry)) + if (info.symbolName.startsWith(entry, caseSensitivityForPrefix)) betterEntries.append(filterEntry); else goodEntries.append(filterEntry); diff --git a/src/plugins/cpptools/cpplocatorfilter.cpp b/src/plugins/cpptools/cpplocatorfilter.cpp index ac27be1d03..55f729c6a2 100644 --- a/src/plugins/cpptools/cpplocatorfilter.cpp +++ b/src/plugins/cpptools/cpplocatorfilter.cpp @@ -135,6 +135,7 @@ QList<Locator::FilterEntry> CppLocatorFilter::matchesFor(QFutureInterface<Locato if (!regexp.isValid()) return goodEntries; bool hasWildcard = (entry.contains(asterisk) || entry.contains(QLatin1Char('?'))); + const Qt::CaseSensitivity caseSensitivityForPrefix = caseSensitivity(entry); QHashIterator<QString, QList<ModelItemInfo> > it(m_searchList); while (it.hasNext()) { @@ -157,7 +158,7 @@ QList<Locator::FilterEntry> CppLocatorFilter::matchesFor(QFutureInterface<Locato FileName::fromString(info.fileName)); } - if (info.symbolName.startsWith(entry)) + if (info.symbolName.startsWith(entry, caseSensitivityForPrefix)) betterEntries.append(filterEntry); else goodEntries.append(filterEntry); diff --git a/src/plugins/cpptools/cpplocatorfilter_test.cpp b/src/plugins/cpptools/cpplocatorfilter_test.cpp index 5ec39796ac..b8cb9ab475 100644 --- a/src/plugins/cpptools/cpplocatorfilter_test.cpp +++ b/src/plugins/cpptools/cpplocatorfilter_test.cpp @@ -195,12 +195,12 @@ void CppToolsPlugin::test_cpplocatorfilters_CppLocatorFilter_data() << cppLocatorFilter << _("myclass") << (QList<ResultData>() - << ResultData(_("<anonymous namespace>::MyClass"), testFileShort) - << ResultData(_("<anonymous namespace>::MyClass::MyClass"), _("()")) - << ResultData(_("<anonymous namespace>::MyClass::function2"), _("(bool, int)")) << ResultData(_("MyClass"), testFileShort) << ResultData(_("MyClass::MyClass"), _("()")) << ResultData(_("MyClass::function2"), _("(bool, int)")) + << ResultData(_("<anonymous namespace>::MyClass"), testFileShort) + << ResultData(_("<anonymous namespace>::MyClass::MyClass"), _("()")) + << ResultData(_("<anonymous namespace>::MyClass::function2"), _("(bool, int)")) << ResultData(_("MyNamespace::MyClass"), testFileShort) << ResultData(_("MyNamespace::MyClass::MyClass"), _("()")) << ResultData(_("MyNamespace::MyClass::function2"), _("(bool, int)")) diff --git a/src/plugins/help/helpindexfilter.cpp b/src/plugins/help/helpindexfilter.cpp index 1016ed38eb..7ee6737cdc 100644 --- a/src/plugins/help/helpindexfilter.cpp +++ b/src/plugins/help/helpindexfilter.cpp @@ -62,9 +62,9 @@ QList<FilterEntry> HelpIndexFilter::matchesFor(QFutureInterface<Locator::FilterE { QStringList keywords; if (entry.length() < 2) - keywords = Core::HelpManager::instance()->findKeywords(entry, 200); + keywords = Core::HelpManager::instance()->findKeywords(entry, caseSensitivity(entry), 200); else - keywords = Core::HelpManager::instance()->findKeywords(entry); + keywords = Core::HelpManager::instance()->findKeywords(entry, caseSensitivity(entry)); QList<FilterEntry> entries; foreach (const QString &keyword, keywords) { diff --git a/src/plugins/locator/basefilefilter.cpp b/src/plugins/locator/basefilefilter.cpp index 8cd2a96e40..3df7ff8cd5 100644 --- a/src/plugins/locator/basefilefilter.cpp +++ b/src/plugins/locator/basefilefilter.cpp @@ -70,6 +70,7 @@ QList<FilterEntry> BaseFileFilter::matchesFor(QFutureInterface<Locator::FilterEn m_previousResultNames.clear(); m_forceNewSearchList = false; m_previousEntry = needle; + const Qt::CaseSensitivity caseSensitivityForPrefix = caseSensitivity(needle); QStringListIterator paths(searchListPaths); QStringListIterator names(searchListNames); while (paths.hasNext() && names.hasNext()) { @@ -84,7 +85,7 @@ QList<FilterEntry> BaseFileFilter::matchesFor(QFutureInterface<Locator::FilterEn FilterEntry entry(this, fi.fileName(), QString(path + lineNoSuffix)); entry.extraInfo = FileUtils::shortNativePath(FileName(fi)); entry.fileName = path; - if (name.startsWith(needle)) + if (name.startsWith(needle, caseSensitivityForPrefix)) matches.append(entry); else badMatches.append(entry); diff --git a/src/plugins/locator/commandlocator.cpp b/src/plugins/locator/commandlocator.cpp index 883aeb15bf..4fb9ec01c6 100644 --- a/src/plugins/locator/commandlocator.cpp +++ b/src/plugins/locator/commandlocator.cpp @@ -71,6 +71,7 @@ QList<Locator::FilterEntry> CommandLocator::matchesFor(QFutureInterface<Locator: // Get active, enabled actions matching text, store in list. // Reference via index in extraInfo. const QChar ampersand = QLatin1Char('&'); + const Qt::CaseSensitivity caseSensitivity_ = caseSensitivity(entry); const int count = d->commands.size(); for (int i = 0; i < count; i++) { if (future.isCanceled()) @@ -80,9 +81,9 @@ QList<Locator::FilterEntry> CommandLocator::matchesFor(QFutureInterface<Locator: if (action->isEnabled()) { QString text = action->text(); text.remove(ampersand); - if (text.startsWith(entry, Qt::CaseInsensitive)) + if (text.startsWith(entry, caseSensitivity_)) betterEntries.append(FilterEntry(this, text, QVariant(i))); - else if (text.contains(entry, Qt::CaseInsensitive)) + else if (text.contains(entry, caseSensitivity_)) goodEntries.append(FilterEntry(this, text, QVariant(i))); } } diff --git a/src/plugins/locator/executefilter.cpp b/src/plugins/locator/executefilter.cpp index c34f7f5f27..8a1251bd64 100644 --- a/src/plugins/locator/executefilter.cpp +++ b/src/plugins/locator/executefilter.cpp @@ -64,12 +64,13 @@ QList<FilterEntry> ExecuteFilter::matchesFor(QFutureInterface<Locator::FilterEnt if (!entry.isEmpty()) // avoid empty entry value.append(FilterEntry(this, entry, QVariant())); QList<FilterEntry> others; + const Qt::CaseSensitivity caseSensitivityForPrefix = caseSensitivity(entry); foreach (const QString& i, m_commandHistory) { if (future.isCanceled()) break; if (i == entry) // avoid repeated entry continue; - if (i.startsWith(entry)) + if (i.startsWith(entry, caseSensitivityForPrefix)) value.append(FilterEntry(this, i, QVariant())); else others.append(FilterEntry(this, i, QVariant())); diff --git a/src/plugins/locator/filesystemfilter.cpp b/src/plugins/locator/filesystemfilter.cpp index 88cbf36719..d25d45a2a3 100644 --- a/src/plugins/locator/filesystemfilter.cpp +++ b/src/plugins/locator/filesystemfilter.cpp @@ -38,6 +38,21 @@ using namespace Core; using namespace Locator; using namespace Locator::Internal; +namespace { + +QList<FilterEntry> *categorize(const QString &entry, const QString &candidate, + Qt::CaseSensitivity caseSensitivity, + QList<FilterEntry> *betterEntries, QList<FilterEntry> *goodEntries) +{ + if (entry.isEmpty() || candidate.startsWith(entry, caseSensitivity)) + return betterEntries; + else if (candidate.contains(entry, caseSensitivity)) + return goodEntries; + return 0; +} + +} // anynoumous namespace + FileSystemFilter::FileSystemFilter(EditorManager *editorManager, LocatorWidget *locatorWidget) : m_editorManager(editorManager), m_locatorWidget(locatorWidget), m_includeHidden(true) { @@ -49,7 +64,8 @@ FileSystemFilter::FileSystemFilter(EditorManager *editorManager, LocatorWidget * QList<FilterEntry> FileSystemFilter::matchesFor(QFutureInterface<Locator::FilterEntry> &future, const QString &entry) { - QList<FilterEntry> value; + QList<FilterEntry> goodEntries; + QList<FilterEntry> betterEntries; QFileInfo entryInfo(entry); QString name = entryInfo.fileName(); QString directory = entryInfo.path(); @@ -72,6 +88,7 @@ QList<FilterEntry> FileSystemFilter::matchesFor(QFutureInterface<Locator::Filter dirFilter |= QDir::Hidden; fileFilter |= QDir::Hidden; } + const Qt::CaseSensitivity caseSensitivity_ = caseSensitivity(entry); QStringList dirs = dirInfo.entryList(dirFilter, QDir::Name|QDir::IgnoreCase|QDir::LocaleAware); QStringList files = dirInfo.entryList(fileFilter, @@ -79,11 +96,12 @@ QList<FilterEntry> FileSystemFilter::matchesFor(QFutureInterface<Locator::Filter foreach (const QString &dir, dirs) { if (future.isCanceled()) break; - if (name.isEmpty() || dir.startsWith(name, Qt::CaseInsensitive)) { + if (QList<FilterEntry> *category = categorize(name, dir, caseSensitivity_, &betterEntries, + &goodEntries)) { const QString fullPath = dirInfo.filePath(dir); FilterEntry filterEntry(this, dir, QVariant()); filterEntry.fileName = fullPath; - value.append(filterEntry); + category->append(filterEntry); } } // file names can match with +linenumber or :linenumber @@ -93,14 +111,16 @@ QList<FilterEntry> FileSystemFilter::matchesFor(QFutureInterface<Locator::Filter foreach (const QString &file, files) { if (future.isCanceled()) break; - if (name.isEmpty() || file.startsWith(name, Qt::CaseInsensitive)) { + if (QList<FilterEntry> *category = categorize(name, file, caseSensitivity_, &betterEntries, + &goodEntries)) { const QString fullPath = dirInfo.filePath(file); FilterEntry filterEntry(this, file, QString(fullPath + lineNoSuffix)); filterEntry.fileName = fullPath; - value.append(filterEntry); + category->append(filterEntry); } } - return value; + betterEntries.append(goodEntries); + return betterEntries; } void FileSystemFilter::accept(FilterEntry selection) const diff --git a/src/plugins/locator/ilocatorfilter.cpp b/src/plugins/locator/ilocatorfilter.cpp index 16521dc5f1..225f78900a 100644 --- a/src/plugins/locator/ilocatorfilter.cpp +++ b/src/plugins/locator/ilocatorfilter.cpp @@ -132,6 +132,11 @@ QString ILocatorFilter::trimWildcards(const QString &str) return str.mid(first, last-first+1); } +Qt::CaseSensitivity ILocatorFilter::caseSensitivity(const QString &str) +{ + return str == str.toLower() ? Qt::CaseInsensitive : Qt::CaseSensitive; +} + bool ILocatorFilter::isConfigurable() const { return m_isConfigurable; diff --git a/src/plugins/locator/ilocatorfilter.h b/src/plugins/locator/ilocatorfilter.h index 331b17e847..6ea20a64a9 100644 --- a/src/plugins/locator/ilocatorfilter.h +++ b/src/plugins/locator/ilocatorfilter.h @@ -138,6 +138,7 @@ public: bool isEnabled() const; static QString trimWildcards(const QString &str); + static Qt::CaseSensitivity caseSensitivity(const QString &str); public slots: /* Enable or disable the filter. */ diff --git a/src/plugins/locator/opendocumentsfilter.cpp b/src/plugins/locator/opendocumentsfilter.cpp index c7d78b912e..54a873e8f4 100644 --- a/src/plugins/locator/opendocumentsfilter.cpp +++ b/src/plugins/locator/opendocumentsfilter.cpp @@ -56,7 +56,8 @@ OpenDocumentsFilter::OpenDocumentsFilter(EditorManager *editorManager) : QList<FilterEntry> OpenDocumentsFilter::matchesFor(QFutureInterface<Locator::FilterEntry> &future, const QString &entry_) { - QList<FilterEntry> value; + QList<FilterEntry> goodEntries; + QList<FilterEntry> betterEntries; QString entry = entry_; const QString lineNoSuffix = EditorManager::splitLineNumber(&entry); const QChar asterisk = QLatin1Char('*'); @@ -65,23 +66,27 @@ QList<FilterEntry> OpenDocumentsFilter::matchesFor(QFutureInterface<Locator::Fil pattern += asterisk; QRegExp regexp(pattern, Qt::CaseInsensitive, QRegExp::Wildcard); if (!regexp.isValid()) - return value; + return goodEntries; + const Qt::CaseSensitivity caseSensitivityForPrefix = caseSensitivity(entry); foreach (const DocumentModel::Entry &editorEntry, m_editors) { if (future.isCanceled()) break; QString fileName = editorEntry.fileName(); + if (fileName.isEmpty()) + continue; QString displayName = editorEntry.displayName(); if (regexp.exactMatch(displayName)) { - if (!fileName.isEmpty()) { - QFileInfo fi(fileName); - FilterEntry fiEntry(this, fi.fileName(), QString(fileName + lineNoSuffix)); - fiEntry.extraInfo = FileUtils::shortNativePath(FileName(fi)); - fiEntry.fileName = fileName; - value.append(fiEntry); - } + QFileInfo fi(fileName); + FilterEntry fiEntry(this, fi.fileName(), QString(fileName + lineNoSuffix)); + fiEntry.extraInfo = FileUtils::shortNativePath(FileName(fi)); + fiEntry.fileName = fileName; + QList<FilterEntry> &category = displayName.startsWith(entry, caseSensitivityForPrefix) + ? betterEntries : goodEntries; + category.append(fiEntry); } } - return value; + betterEntries.append(goodEntries); + return betterEntries; } void OpenDocumentsFilter::refreshInternally() diff --git a/src/plugins/macros/macrolocatorfilter.cpp b/src/plugins/macros/macrolocatorfilter.cpp index 03df032dc6..2bb81904c5 100644 --- a/src/plugins/macros/macrolocatorfilter.cpp +++ b/src/plugins/macros/macrolocatorfilter.cpp @@ -55,7 +55,10 @@ MacroLocatorFilter::~MacroLocatorFilter() QList<Locator::FilterEntry> MacroLocatorFilter::matchesFor(QFutureInterface<Locator::FilterEntry> &future, const QString &entry) { Q_UNUSED(future) - QList<Locator::FilterEntry> result; + QList<Locator::FilterEntry> goodEntries; + QList<Locator::FilterEntry> betterEntries; + + const Qt::CaseSensitivity caseSensitivity_ = caseSensitivity(entry); const QMap<QString, Macro*> ¯os = MacroManager::macros(); QMapIterator<QString, Macro*> it(macros); @@ -64,14 +67,21 @@ QList<Locator::FilterEntry> MacroLocatorFilter::matchesFor(QFutureInterface<Loca it.next(); QString name = it.key(); - if (name.contains(entry)) { + QList<Locator::FilterEntry> *category = 0; + if (name.startsWith(entry, caseSensitivity_)) + category = &betterEntries; + else if (name.contains(entry, caseSensitivity_)) + category = &goodEntries; + + if (category) { QVariant id; Locator::FilterEntry entry(this, it.key(), id, m_icon); entry.extraInfo = it.value()->description(); - result.append(entry); + category->append(entry); } } - return result; + betterEntries.append(goodEntries); + return betterEntries; } void MacroLocatorFilter::accept(Locator::FilterEntry selection) const diff --git a/src/plugins/qmljstools/qmljsfunctionfilter.cpp b/src/plugins/qmljstools/qmljsfunctionfilter.cpp index 33c1eb9356..89b6c6e903 100644 --- a/src/plugins/qmljstools/qmljsfunctionfilter.cpp +++ b/src/plugins/qmljstools/qmljsfunctionfilter.cpp @@ -72,6 +72,7 @@ QList<Locator::FilterEntry> FunctionFilter::matchesFor(QFutureInterface<Locator: if (!regexp.isValid()) return goodEntries; bool hasWildcard = (entry.contains(asterisk) || entry.contains(QLatin1Char('?'))); + const Qt::CaseSensitivity caseSensitivityForPrefix = caseSensitivity(entry); QHashIterator<QString, QList<LocatorData::Entry> > it(m_data->entries()); while (it.hasNext()) { @@ -91,7 +92,7 @@ QList<Locator::FilterEntry> FunctionFilter::matchesFor(QFutureInterface<Locator: Locator::FilterEntry filterEntry(this, info.displayName, id/*, info.icon*/); filterEntry.extraInfo = info.extraInfo; - if (info.symbolName.startsWith(entry)) + if (info.symbolName.startsWith(entry, caseSensitivityForPrefix)) betterEntries.append(filterEntry); else goodEntries.append(filterEntry); |