forked from qt-creator/qt-creator
ClangCodeModel: Forward to the built-in code model
... if the user tries to complete inside a comment or string. Fixes: QTCREATORBUG-20828 Change-Id: I245e1bd16acaf696601cabe33f27210da21cc12a Reviewed-by: David Schulz <david.schulz@qt.io> Reviewed-by: <github-actions-qt-creator@cristianadam.eu>
This commit is contained in:
@@ -12,7 +12,6 @@
|
||||
|
||||
#include <cppeditor/cppcompletionassistprocessor.h>
|
||||
#include <cppeditor/cppcompletionassistprovider.h>
|
||||
#include <cppeditor/cppdoxygen.h>
|
||||
#include <cppeditor/cppeditorconstants.h>
|
||||
#include <cppeditor/cppmodelmanager.h>
|
||||
#include <cppeditor/cppprojectfile.h>
|
||||
@@ -44,7 +43,7 @@ namespace ClangCodeModel::Internal {
|
||||
static Q_LOGGING_CATEGORY(clangdLogCompletion, "qtc.clangcodemodel.clangd.completion",
|
||||
QtWarningMsg);
|
||||
|
||||
enum class CustomAssistMode { Doxygen, Preprocessor, IncludePath };
|
||||
enum class CustomAssistMode { Preprocessor, IncludePath };
|
||||
|
||||
class CustomAssistProcessor : public IAssistProcessor
|
||||
{
|
||||
@@ -126,6 +125,12 @@ IAssistProcessor *ClangdCompletionAssistProvider::createProcessor(
|
||||
<< interface->textAt(interface->position(), -10);
|
||||
qCDebug(clangdLogCompletion) << "text after cursor is"
|
||||
<< interface->textAt(interface->position(), 10);
|
||||
|
||||
if (!interface->isBaseObject()) {
|
||||
qCDebug(clangdLogCompletion) << "encountered assist interface for built-in code model";
|
||||
return CppEditor::getCppCompletionAssistProcessor();
|
||||
}
|
||||
|
||||
ClangCompletionContextAnalyzer contextAnalyzer(interface->textDocument(),
|
||||
interface->position(), false, {});
|
||||
contextAnalyzer.analyze();
|
||||
@@ -133,13 +138,6 @@ IAssistProcessor *ClangdCompletionAssistProvider::createProcessor(
|
||||
case ClangCompletionContextAnalyzer::PassThroughToLibClangAfterLeftParen:
|
||||
qCDebug(clangdLogCompletion) << "creating function hint processor";
|
||||
return new ClangdFunctionHintProcessor(m_client);
|
||||
case ClangCompletionContextAnalyzer::CompleteDoxygenKeyword:
|
||||
qCDebug(clangdLogCompletion) << "creating doxygen processor";
|
||||
return new CustomAssistProcessor(m_client,
|
||||
contextAnalyzer.positionForProposal(),
|
||||
contextAnalyzer.positionEndOfExpression(),
|
||||
contextAnalyzer.completionOperator(),
|
||||
CustomAssistMode::Doxygen);
|
||||
case ClangCompletionContextAnalyzer::CompletePreprocessorDirective:
|
||||
qCDebug(clangdLogCompletion) << "creating macro processor";
|
||||
return new CustomAssistProcessor(m_client,
|
||||
@@ -147,10 +145,6 @@ IAssistProcessor *ClangdCompletionAssistProvider::createProcessor(
|
||||
contextAnalyzer.positionEndOfExpression(),
|
||||
contextAnalyzer.completionOperator(),
|
||||
CustomAssistMode::Preprocessor);
|
||||
case ClangCompletionContextAnalyzer::CompleteSignal:
|
||||
case ClangCompletionContextAnalyzer::CompleteSlot:
|
||||
if (!interface->isBaseObject())
|
||||
return CppEditor::getCppCompletionAssistProcessor();
|
||||
default:
|
||||
break;
|
||||
}
|
||||
@@ -415,12 +409,6 @@ IAssistProposal *CustomAssistProcessor::perform()
|
||||
{
|
||||
QList<AssistProposalItemInterface *> completions;
|
||||
switch (m_mode) {
|
||||
case CustomAssistMode::Doxygen:
|
||||
for (int i = 1; i < T_DOXY_LAST_TAG; ++i) {
|
||||
completions << createItem(QLatin1String(doxygenTagSpell(i)),
|
||||
CPlusPlus::Icons::keywordIcon());
|
||||
}
|
||||
break;
|
||||
case CustomAssistMode::Preprocessor: {
|
||||
static QIcon macroIcon = Utils::CodeModelIcon::iconForType(CodeModelIcon::Macro);
|
||||
for (const QString &completion
|
||||
|
||||
@@ -1500,7 +1500,7 @@ ClangdTestCompletion::ClangdTestCompletion()
|
||||
setProjectFileName("completion.pro");
|
||||
setSourceFileNames({"completionWithProject.cpp", "constructorCompletion.cpp",
|
||||
"classAndConstructorCompletion.cpp", "dotToArrowCorrection.cpp",
|
||||
"doxygenKeywordsCompletion.cpp", "functionAddress.cpp",
|
||||
"functionAddress.cpp",
|
||||
"functionCompletion.cpp", "functionCompletionFiltered2.cpp",
|
||||
"functionCompletionFiltered.cpp", "globalCompletion.cpp",
|
||||
"includeDirectiveCompletion.cpp", "mainwindow.cpp",
|
||||
@@ -1518,18 +1518,6 @@ void ClangdTestCompletion::initTestCase()
|
||||
startCollectingHighlightingInfo();
|
||||
}
|
||||
|
||||
void ClangdTestCompletion::testCompleteDoxygenKeywords()
|
||||
{
|
||||
ProposalModelPtr proposal;
|
||||
getProposal("doxygenKeywordsCompletion.cpp", proposal);
|
||||
|
||||
QVERIFY(proposal);
|
||||
QVERIFY(hasItem(proposal, "brief"));
|
||||
QVERIFY(hasItem(proposal, "param"));
|
||||
QVERIFY(hasItem(proposal, "return"));
|
||||
QVERIFY(!hasSnippet(proposal, "class "));
|
||||
}
|
||||
|
||||
void ClangdTestCompletion::testCompletePreprocessorKeywords()
|
||||
{
|
||||
ProposalModelPtr proposal;
|
||||
|
||||
@@ -137,7 +137,6 @@ public:
|
||||
private slots:
|
||||
void initTestCase() override;
|
||||
|
||||
void testCompleteDoxygenKeywords();
|
||||
void testCompletePreprocessorKeywords();
|
||||
void testCompleteIncludeDirective();
|
||||
|
||||
|
||||
@@ -29,7 +29,6 @@
|
||||
<file>completion/classAndConstructorCompletion.cpp</file>
|
||||
<file>completion/completionWithProject.cpp</file>
|
||||
<file>completion/constructorCompletion.cpp</file>
|
||||
<file>completion/doxygenKeywordsCompletion.cpp</file>
|
||||
<file>completion/functionCompletion.cpp</file>
|
||||
<file>completion/functionCompletionFiltered.cpp</file>
|
||||
<file>completion/functionCompletionFiltered2.cpp</file>
|
||||
|
||||
@@ -1 +0,0 @@
|
||||
//! \ /* COMPLETE HERE */
|
||||
@@ -1268,7 +1268,8 @@ std::unique_ptr<AssistInterface> CppEditorWidget::createAssistInterface(AssistKi
|
||||
if (cap)
|
||||
return cap->createAssistInterface(textDocument()->filePath(), this, getFeatures(), reason);
|
||||
|
||||
if (isOldStyleSignalOrSlot()) {
|
||||
if (isOldStyleSignalOrSlot()
|
||||
|| isInCommentOrString(textCursor(), LanguageFeatures::defaultFeatures())) {
|
||||
return CppModelManager::completionAssistProvider()
|
||||
->createAssistInterface(textDocument()->filePath(), this, getFeatures(), reason);
|
||||
}
|
||||
|
||||
@@ -293,29 +293,33 @@ bool isInCommentOrString(const TextEditor::AssistInterface *interface,
|
||||
{
|
||||
QTextCursor tc(interface->textDocument());
|
||||
tc.setPosition(interface->position());
|
||||
return isInCommentOrString(tc, features);
|
||||
}
|
||||
|
||||
bool isInCommentOrString(const QTextCursor &cursor, CPlusPlus::LanguageFeatures features)
|
||||
{
|
||||
SimpleLexer tokenize;
|
||||
features.qtMocRunEnabled = true;
|
||||
tokenize.setLanguageFeatures(features);
|
||||
tokenize.setSkipComments(false);
|
||||
const Tokens &tokens = tokenize(tc.block().text(),
|
||||
BackwardsScanner::previousBlockState(tc.block()));
|
||||
const int tokenIdx = SimpleLexer::tokenBefore(tokens, qMax(0, tc.positionInBlock() - 1));
|
||||
const Tokens &tokens = tokenize(cursor.block().text(),
|
||||
BackwardsScanner::previousBlockState(cursor.block()));
|
||||
const int tokenIdx = SimpleLexer::tokenBefore(tokens, qMax(0, cursor.positionInBlock() - 1));
|
||||
const Token tk = (tokenIdx == -1) ? Token() : tokens.at(tokenIdx);
|
||||
|
||||
if (tk.isComment())
|
||||
return true;
|
||||
if (!tk.isLiteral())
|
||||
if (!tk.isStringLiteral())
|
||||
return false;
|
||||
if (tokens.size() == 3 && tokens.at(0).kind() == T_POUND
|
||||
&& tokens.at(1).kind() == T_IDENTIFIER) {
|
||||
const QString &line = tc.block().text();
|
||||
&& tokens.at(1).kind() == T_IDENTIFIER) {
|
||||
const QString &line = cursor.block().text();
|
||||
const Token &idToken = tokens.at(1);
|
||||
QStringView identifier = QStringView(line).mid(idToken.utf16charsBegin(),
|
||||
idToken.utf16chars());
|
||||
if (identifier == QLatin1String("include")
|
||||
|| identifier == QLatin1String("include_next")
|
||||
|| (features.objCEnabled && identifier == QLatin1String("import"))) {
|
||||
|| identifier == QLatin1String("include_next")
|
||||
|| (features.objCEnabled && identifier == QLatin1String("import"))) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -54,6 +54,8 @@ const CPlusPlus::Macro CPPEDITOR_EXPORT *findCanonicalMacro(const QTextCursor &c
|
||||
|
||||
bool CPPEDITOR_EXPORT isInCommentOrString(const TextEditor::AssistInterface *interface,
|
||||
CPlusPlus::LanguageFeatures features);
|
||||
bool CPPEDITOR_EXPORT isInCommentOrString(const QTextCursor &cursor,
|
||||
CPlusPlus::LanguageFeatures features);
|
||||
TextEditor::QuickFixOperations CPPEDITOR_EXPORT
|
||||
quickFixOperations(const TextEditor::AssistInterface *interface);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user