Commit 546d2978 authored by Nikolai Kosjar's avatar Nikolai Kosjar

CppTools: Handle operator functions when reformatting */& declarations

Respect also whitespace within the operator names (e.g. "operator=" vs
"operator =").

Change-Id: Ibdfc77e9eebf7e3db31ccce7d8959b226dcda765
Reviewed-by: default avatarChristian Kandeler <christian.kandeler@digia.com>
Reviewed-by: default avatarErik Verbruggen <erik.verbruggen@digia.com>
parent 50a900e5
......@@ -216,7 +216,7 @@ bool PointerDeclarationFormatter::visit(SimpleDeclarationAST *ast)
range.end = lastActivationToken;
checkAndRewrite(symbol, range, charactersToRemove);
checkAndRewrite(declarator, symbol, range, charactersToRemove);
}
return true;
}
......@@ -250,7 +250,7 @@ bool PointerDeclarationFormatter::visit(FunctionDefinitionAST *ast)
CHECK_RV(foundBegin, "Declaration without attributes not supported", true);
TokenRange range(firstActivationToken, lastActivationToken);
checkAndRewrite(symbol, range);
checkAndRewrite(declarator, symbol, range);
return true;
}
......@@ -271,7 +271,7 @@ bool PointerDeclarationFormatter::visit(ParameterDeclarationAST *ast)
: ast->lastToken() - 1;
TokenRange range(ast->firstToken(), lastActivationToken);
checkAndRewrite(symbol, range);
checkAndRewrite(declarator, symbol, range);
return true;
}
......@@ -296,7 +296,7 @@ bool PointerDeclarationFormatter::visit(ForeachStatementAST *ast)
: declarator->lastToken() - 1;
TokenRange range(firstSpecifier->firstToken(), lastActivationToken);
checkAndRewrite(symbol, range);
checkAndRewrite(declarator, symbol, range);
return true;
}
......@@ -359,7 +359,7 @@ void PointerDeclarationFormatter::processIfWhileForStatement(ExpressionAST *expr
// Specify activation range
TokenRange range(condition->firstToken(), declarator->equal_token - 1);
checkAndRewrite(symbol, range);
checkAndRewrite(declarator, symbol, range);
}
/*!
......@@ -369,7 +369,9 @@ void PointerDeclarationFormatter::processIfWhileForStatement(ExpressionAST *expr
\param symbol the symbol to be rewritten
\param range the substitution range in the file
*/
void PointerDeclarationFormatter::checkAndRewrite(Symbol *symbol, TokenRange tokenRange,
void PointerDeclarationFormatter::checkAndRewrite(DeclaratorAST *declarator,
Symbol *symbol,
TokenRange tokenRange,
unsigned charactersToRemove)
{
CHECK_R(tokenRange.end > 0, "TokenRange invalid1");
......@@ -408,7 +410,24 @@ void PointerDeclarationFormatter::checkAndRewrite(Symbol *symbol, TokenRange tok
|| originalDeclaration.contains(QLatin1Char('*')), "No pointer or references");
// Does the rewritten declaration (part) differs from the original source (part)?
QString rewrittenDeclaration = rewriteDeclaration(type, symbol->name());
QString rewrittenDeclaration;
const Name *name = symbol->name();
if (name) {
if (name->isOperatorNameId()) {
// Take the operator name from the file instead from the AST, so the white
// spaces within the operator names can be respected, e.g. in "operator =".
const QByteArray operatorText
= m_cppRefactoringFile->textOf(declarator->core_declarator).toLatin1();
Identifier operatorName(operatorText.constData(), operatorText.size());
rewrittenDeclaration = rewriteDeclaration(type, &operatorName);
} else {
rewrittenDeclaration = rewriteDeclaration(type, name);
}
} else {
// The declaration will be correctly rewritten for name == 0 (e.g. "int *").
rewrittenDeclaration = rewriteDeclaration(type, name);
}
rewrittenDeclaration.remove(0, charactersToRemove);
CHECK_R(originalDeclaration != rewrittenDeclaration, "Rewritten is same as original");
......
......@@ -110,7 +110,8 @@ private:
};
void processIfWhileForStatement(ExpressionAST *expression, Symbol *symbol);
void checkAndRewrite(Symbol *symbol, TokenRange range, unsigned charactersToRemove = 0);
void checkAndRewrite(DeclaratorAST *declarator, Symbol *symbol, TokenRange range,
unsigned charactersToRemove = 0);
QString rewriteDeclaration(FullySpecifiedType type, const Name *name) const;
void printCandidate(AST *ast);
......
......@@ -347,6 +347,11 @@ void CppToolsPlugin::test_format_pointerdeclaration_in_simpledeclarations_data()
source = QLatin1String("@char bla;"); // Two spaces to get sure nothing is reformatted.
QTest::newRow("precondition-fail-no-pointer")
<< source << stripCursor(source);
// Respect white space within operator names
QTest::newRow("operators")
<< "class C { C@&operator = (const C &); };"
<< "class C { C & operator = (const C &); };";
}
void CppToolsPlugin::test_format_pointerdeclaration_in_controlflowstatements()
......
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