Commit 65f13fe0 authored by Nikolai Kosjar's avatar Nikolai Kosjar

CppEditor: Clean up cppvirtualfunctionassistprovider.cpp

- Moves the findMatchingClassDeclaration() call from
  FollowSymbolUnderCursor::findLink into VirtualFunctionsAssistProcessor
  since we already have a SymbolFinder there
- Make canLookupVirtualFunctionOverrides a class member because we plan
  to add some methods
- Better parameter names/order for FunctionHelper::overrides()

Change-Id: I0a93ff5445352d47e808adad45485e520f06946e
Reviewed-by: default avatarErik Verbruggen <erik.verbruggen@digia.com>
parent 8f0be66d
......@@ -55,22 +55,60 @@ typedef BaseTextEditorWidget::Link Link;
namespace {
bool lookupVirtualFunctionOverrides(TypeOfExpression &typeOfExpression,
const Document::Ptr &document,
const Function *function,
Scope *scope,
const Snapshot &snapshot)
class VirtualFunctionHelper {
public:
VirtualFunctionHelper(const TypeOfExpression &typeOfExpression,
Scope *scope,
const Document::Ptr &document,
const Snapshot &snapshot);
bool canLookupVirtualFunctionOverrides(const Function *function) const;
private:
VirtualFunctionHelper();
Q_DISABLE_COPY(VirtualFunctionHelper)
ExpressionAST *getBaseExpressionAST() const
{
if (!m_expressionAST)
return 0;
CallAST *callAST = m_expressionAST->asCall();
if (!callAST)
return 0;
if (ExpressionAST *baseExpressionAST = callAST->base_expression)
return baseExpressionAST;
return 0;
}
private:
const QSharedPointer<TypeOfExpression> m_typeOfExpression;
ExpressionAST *m_expressionAST;
const Document::Ptr m_expressionDocument;
Scope *m_scope;
const Document::Ptr &m_document;
const Snapshot &m_snapshot;
};
VirtualFunctionHelper::VirtualFunctionHelper(const TypeOfExpression &typeOfExpression,
Scope *scope,
const Document::Ptr &document,
const Snapshot &snapshot)
: m_expressionAST(typeOfExpression.expressionAST())
, m_expressionDocument(typeOfExpression.context().expressionDocument())
, m_scope(scope)
, m_document(document)
, m_snapshot(snapshot)
{
if (!document || !function || !scope || scope->isClass() || snapshot.isEmpty())
return false;
}
ExpressionAST *expressionAST = typeOfExpression.expressionAST();
if (!expressionAST)
return false;
CallAST *callAST = expressionAST->asCall();
if (!callAST)
bool VirtualFunctionHelper::canLookupVirtualFunctionOverrides(const Function *function) const
{
if (!m_expressionDocument || !m_document || !function || !m_scope || m_scope->isClass()
|| m_snapshot.isEmpty()) {
return false;
ExpressionAST *baseExpressionAST = callAST->base_expression;
}
ExpressionAST *baseExpressionAST = getBaseExpressionAST();
if (!baseExpressionAST)
return false;
......@@ -79,23 +117,23 @@ bool lookupVirtualFunctionOverrides(TypeOfExpression &typeOfExpression,
if (IdExpressionAST *idExpressionAST = baseExpressionAST->asIdExpression()) {
NameAST *name = idExpressionAST->name;
const bool nameIsQualified = name && name->asQualifiedName();
result = !nameIsQualified && FunctionHelper::isVirtualFunction(function, snapshot);
result = !nameIsQualified && FunctionHelper::isVirtualFunction(function, m_snapshot);
} else if (MemberAccessAST *memberAccessAST = baseExpressionAST->asMemberAccess()) {
NameAST *name = memberAccessAST->member_name;
const bool nameIsQualified = name && name->asQualifiedName();
if (!nameIsQualified && FunctionHelper::isVirtualFunction(function, snapshot)) {
const Document::Ptr expressionDocument
= typeOfExpression.context().expressionDocument();
QTC_ASSERT(expressionDocument, return false);
TranslationUnit *unit = expressionDocument->translationUnit();
if (!nameIsQualified && FunctionHelper::isVirtualFunction(function, m_snapshot)) {
TranslationUnit *unit = m_expressionDocument->translationUnit();
QTC_ASSERT(unit, return false);
const int accessTokenKind = unit->tokenKind(memberAccessAST->access_token);
if (accessTokenKind == T_ARROW) {
result = true;
} else if (accessTokenKind == T_DOT) {
TypeOfExpression typeOfExpression;
typeOfExpression.init(m_document, m_snapshot);
typeOfExpression.setExpandTemplates(true);
const QList<LookupItem> items = typeOfExpression.reference(
memberAccessAST->base_expression, document, scope);
memberAccessAST->base_expression, m_document, m_scope);
if (!items.isEmpty()) {
const LookupItem item = items.first();
if (Symbol *declaration = item.declaration())
......@@ -552,13 +590,10 @@ BaseTextEditorWidget::Link FollowSymbolUnderCursor::findLink(const QTextCursor &
// Consider to show a pop-up displaying overrides for the function
Function *function = symbol->type()->asFunctionType();
VirtualFunctionHelper helper(*typeOfExpression, scope, doc, snapshot);
if (lookupVirtualFunctionOverrides(*typeOfExpression, doc, function, scope, snapshot)) {
Class *klass = symbolFinder->findMatchingClassDeclaration(function, snapshot);
QTC_CHECK(klass);
if (helper.canLookupVirtualFunctionOverrides(function)) {
VirtualFunctionAssistProvider::Parameters params;
params.startClass = klass;
params.function = function;
params.typeOfExpression = typeOfExpression;
params.snapshot = snapshot;
......
......@@ -132,12 +132,16 @@ public:
IAssistProposal *perform(const IAssistInterface *)
{
QTC_ASSERT(m_params.startClass, return 0);
QTC_ASSERT(m_params.function, return 0);
QTC_ASSERT(!m_params.snapshot.isEmpty(), return 0);
Class *functionsClass = m_finder.findMatchingClassDeclaration(m_params.function,
m_params.snapshot);
if (!functionsClass)
return 0;
const QList<Symbol *> overrides
= FunctionHelper::overrides(m_params.startClass, m_params.function, m_params.snapshot);
= FunctionHelper::overrides(m_params.function, functionsClass, m_params.snapshot);
if (overrides.isEmpty())
return 0;
......@@ -250,19 +254,19 @@ bool FunctionHelper::isPureVirtualFunction(const Function *function, const Snaps
return isVirtualFunction_helper(function, snapshot, PureVirtual);
}
QList<Symbol *> FunctionHelper::overrides(Class *startClass, Function *function,
QList<Symbol *> FunctionHelper::overrides(Function *function, Class *functionsClass,
const Snapshot &snapshot)
{
QList<Symbol *> result;
QTC_ASSERT(startClass && function, return result);
QTC_ASSERT(function && functionsClass, return result);
FullySpecifiedType referenceType = function->type();
const Name *referenceName = function->name();
QTC_ASSERT(referenceName && referenceType.isValid(), return result);
// Find overrides
CppEditor::Internal::CppClass cppClass = CppClass(startClass);
cppClass.lookupDerived(startClass, snapshot);
CppEditor::Internal::CppClass cppClass = CppClass(functionsClass);
cppClass.lookupDerived(functionsClass, snapshot);
QList<CppClass> l;
l << cppClass;
......
......@@ -48,9 +48,8 @@ public:
VirtualFunctionAssistProvider();
struct Parameters {
Parameters() : startClass(0), function(0), cursorPosition(-1), openInNextSplit(false) {}
Parameters() : function(0), cursorPosition(-1), openInNextSplit(false) {}
CPlusPlus::Class *startClass;
CPlusPlus::Function *function;
QSharedPointer<CPlusPlus::TypeOfExpression> typeOfExpression; // Keeps instantiated symbols.
CPlusPlus::Snapshot snapshot;
......@@ -79,8 +78,8 @@ public:
static bool isPureVirtualFunction(const CPlusPlus::Function *function,
const CPlusPlus::Snapshot &snapshot);
static QList<CPlusPlus::Symbol *> overrides(CPlusPlus::Class *startClass,
CPlusPlus::Function *function,
static QList<CPlusPlus::Symbol *> overrides(CPlusPlus::Function *function,
CPlusPlus::Class *functionsClass,
const CPlusPlus::Snapshot &snapshot);
};
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment