summaryrefslogtreecommitdiff
path: root/src/plugins/cpptools/cppcodecompletion.cpp
diff options
context:
space:
mode:
authorThorbjørn Lindeijer <thorbjorn.lindeijer@nokia.com>2009-02-04 16:40:42 +0100
committerThorbjørn Lindeijer <thorbjorn.lindeijer@nokia.com>2009-02-16 15:08:38 +0100
commit9aa86f91356630b3609ffc577c0232992dca3050 (patch)
treeb8befc2edae58ff2982288a8e0132dc28644b579 /src/plugins/cpptools/cppcodecompletion.cpp
parente539a9375b6279b84390ee3be3a1529b5b779b16 (diff)
downloadqt-creator-9aa86f91356630b3609ffc577c0232992dca3050.tar.gz
Completion for constructors used on initialization
Deals with cases like "QString s(", but for the moment doesn't handle yet "QString const s(". Done with Roberto Raggi. (cherry picked from commit fca3ec1f3288ac4bcbfaed7f6c613af5cc762dda)
Diffstat (limited to 'src/plugins/cpptools/cppcodecompletion.cpp')
-rw-r--r--src/plugins/cpptools/cppcodecompletion.cpp85
1 files changed, 62 insertions, 23 deletions
diff --git a/src/plugins/cpptools/cppcodecompletion.cpp b/src/plugins/cpptools/cppcodecompletion.cpp
index 0ff66aaa6e..20faa6e7a3 100644
--- a/src/plugins/cpptools/cppcodecompletion.cpp
+++ b/src/plugins/cpptools/cppcodecompletion.cpp
@@ -432,7 +432,7 @@ int CppCodeCompletion::startCompletion(TextEditor::ITextEditable *editor)
return -1;
m_editor = editor;
- m_startPosition = findStartOfName(editor);
+ m_startPosition = findStartOfName();
m_completionOperator = T_EOF_SYMBOL;
int endOfOperator = m_startPosition;
@@ -520,7 +520,7 @@ int CppCodeCompletion::startCompletion(TextEditor::ITextEditable *editor)
if (m_completionOperator == T_LPAREN && completeFunction(exprTy, resolvedTypes, context)) {
return m_startPosition;
- } if ((m_completionOperator == T_DOT || m_completionOperator == T_ARROW) &&
+ } else if ((m_completionOperator == T_DOT || m_completionOperator == T_ARROW) &&
completeMember(resolvedTypes, context)) {
return m_startPosition;
} else if (m_completionOperator == T_COLON_COLON && completeScope(resolvedTypes, context)) {
@@ -531,6 +531,32 @@ int CppCodeCompletion::startCompletion(TextEditor::ITextEditable *editor)
return m_startPosition;
}
}
+
+ if (m_completionOperator == T_LPAREN) {
+ // Find the expression that precedes the current name
+ int index = endOfExpression;
+ while (m_editor->characterAt(index - 1).isSpace())
+ --index;
+ index = findStartOfName(index);
+
+ QTextCursor tc(edit->document());
+ tc.setPosition(index);
+ QString baseExpression = expressionUnderCursor(tc);
+
+ // Resolve the type of this expression
+ QList<TypeOfExpression::Result> results =
+ typeOfExpression(baseExpression, thisDocument, symbol, TypeOfExpression::Preprocess);
+
+ // If it's a class, add completions for the constructors
+ foreach (const TypeOfExpression::Result &result, results) {
+ if (result.first->isClass()) {
+ FullySpecifiedType exprTy = result.first;
+ if (completeConstructors(exprTy->asClass()))
+ return m_startPosition;
+ break;
+ }
+ }
+ }
}
// nothing to do.
@@ -541,26 +567,14 @@ bool CppCodeCompletion::completeFunction(FullySpecifiedType exprTy,
const QList<TypeOfExpression::Result> &resolvedTypes,
const LookupContext &)
{
- ConvertToCompletionItem toCompletionItem(this);
- Overview o;
- o.setShowReturnTypes(true);
- o.setShowArgumentNames(true);
-
if (Class *klass = exprTy->asClass()) {
- for (unsigned i = 0; i < klass->memberCount(); ++i) {
- Symbol *member = klass->memberAt(i);
- if (! member->type()->isFunction())
- continue;
- else if (! member->identity())
- continue;
- else if (! member->identity()->isEqualTo(klass->identity()))
- continue;
- if (TextEditor::CompletionItem item = toCompletionItem(member)) {
- item.m_text = o(member->type(), member->name());
- m_completions.append(item);
- }
- }
+ completeConstructors(klass);
} else {
+ ConvertToCompletionItem toCompletionItem(this);
+ Overview o;
+ o.setShowReturnTypes(true);
+ o.setShowArgumentNames(true);
+
QSet<QString> signatures;
foreach (TypeOfExpression::Result p, resolvedTypes) {
FullySpecifiedType ty = p.first;
@@ -873,6 +887,30 @@ void CppCodeCompletion::completeClass(const QList<Symbol *> &candidates,
}
}
+bool CppCodeCompletion::completeConstructors(Class *klass)
+{
+ ConvertToCompletionItem toCompletionItem(this);
+ Overview o;
+ o.setShowReturnTypes(true);
+ o.setShowArgumentNames(true);
+
+ for (unsigned i = 0; i < klass->memberCount(); ++i) {
+ Symbol *member = klass->memberAt(i);
+ if (! member->type()->isFunction())
+ continue;
+ else if (! member->identity())
+ continue;
+ else if (! member->identity()->isEqualTo(klass->identity()))
+ continue;
+ if (TextEditor::CompletionItem item = toCompletionItem(member)) {
+ item.m_text = o(member->type(), member->name());
+ m_completions.append(item);
+ }
+ }
+
+ return ! m_completions.isEmpty();
+}
+
bool CppCodeCompletion::completeQtMethod(CPlusPlus::FullySpecifiedType,
const QList<TypeOfExpression::Result> &results,
const LookupContext &context,
@@ -1150,14 +1188,15 @@ void CppCodeCompletion::cleanup()
typeOfExpression.setSnapshot(Snapshot());
}
-int CppCodeCompletion::findStartOfName(const TextEditor::ITextEditor *editor)
+int CppCodeCompletion::findStartOfName(int pos) const
{
- int pos = editor->position();
+ if (pos == -1)
+ pos = m_editor->position();
QChar chr;
// Skip to the start of a name
do {
- chr = editor->characterAt(--pos);
+ chr = m_editor->characterAt(--pos);
} while (chr.isLetterOrNumber() || chr == QLatin1Char('_'));
return pos + 1;