summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorFrancois Ferrand <thetypz@gmail.com>2018-03-01 10:09:13 +0000
committerFrancois Ferrand <thetypz@gmail.com>2018-03-01 10:09:13 +0000
commit2818cfe4cbfcbceed9ed0aca79c91a958636691e (patch)
treec00e8cb9067b3d10d6725b842c5756940fdfeb98
parente845f691846783e8e30d3131c8f8a08311c406e8 (diff)
downloadclang-2818cfe4cbfcbceed9ed0aca79c91a958636691e.tar.gz
[clang-format] Add SpaceBeforeColon option
Summary: When disabled, this option allows removing the space before colon, making it act more like the semi-colon. When enabled (default), the current behavior is not affected. This mostly affects C++11 loop, initializer list, inheritance list and container literals: class Foo: Bar {} Foo::Foo(): a(a) {} for (auto i: myList) {} f({a: 1, b: 2, c: 3}); Reviewers: krasimir, djasper Reviewed By: djasper Subscribers: xvallspl, teemperor, karies, cfe-commits, klimek Differential Revision: https://reviews.llvm.org/D32525 git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@326426 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r--docs/ClangFormatStyleOptions.rst26
-rw-r--r--include/clang/Format/Format.h28
-rw-r--r--lib/Format/Format.cpp9
-rw-r--r--lib/Format/TokenAnnotator.cpp9
-rw-r--r--unittests/Format/FormatTest.cpp111
5 files changed, 182 insertions, 1 deletions
diff --git a/docs/ClangFormatStyleOptions.rst b/docs/ClangFormatStyleOptions.rst
index ea43f19a3c..1ddcce8b7a 100644
--- a/docs/ClangFormatStyleOptions.rst
+++ b/docs/ClangFormatStyleOptions.rst
@@ -1681,6 +1681,23 @@ the configuration (without a prefix: ``Auto``).
int a = 5; vs. int a=5;
a += 42 a+=42;
+**SpaceBeforeCtorInitializerColon** (``bool``)
+ If ``false``, spaces will be removed before constructor initializer
+ colon.
+
+ .. code-block:: c++
+
+ true: false:
+ Foo::Foo() : a(a) {} Foo::Foo(): a(a) {}
+
+**SpaceBeforeInheritanceColon** (``bool``)
+ If ``false``, spaces will be removed before inheritance colon.
+
+ .. code-block:: c++
+
+ true: false:
+ class Foo : Bar {} vs. class Foo: Bar {}
+
**SpaceBeforeParens** (``SpaceBeforeParensOptions``)
Defines in which cases to put a space before opening parentheses.
@@ -1725,6 +1742,15 @@ the configuration (without a prefix: ``Auto``).
+**SpaceBeforeRangeBasedForLoopColon** (``bool``)
+ If ``false``, spaces will be removed before range-based for loop
+ colon.
+
+ .. code-block:: c++
+
+ true: false:
+ for (auto v : values) {} vs. for(auto v: values) {}
+
**SpaceInEmptyParentheses** (``bool``)
If ``true``, spaces may be inserted into ``()``.
diff --git a/include/clang/Format/Format.h b/include/clang/Format/Format.h
index 3060d9b944..6a508b0f71 100644
--- a/include/clang/Format/Format.h
+++ b/include/clang/Format/Format.h
@@ -1525,6 +1525,21 @@ struct FormatStyle {
/// \endcode
bool SpaceBeforeAssignmentOperators;
+ /// \brief If ``false``, spaces will be removed before constructor initializer
+ /// colon.
+ /// \code
+ /// true: false:
+ /// Foo::Foo() : a(a) {} Foo::Foo(): a(a) {}
+ /// \endcode
+ bool SpaceBeforeCtorInitializerColon;
+
+ /// \brief If ``false``, spaces will be removed before inheritance colon.
+ /// \code
+ /// true: false:
+ /// class Foo : Bar {} vs. class Foo: Bar {}
+ /// \endcode
+ bool SpaceBeforeInheritanceColon;
+
/// \brief Different ways to put a space before opening parentheses.
enum SpaceBeforeParensOptions {
/// Never put a space before opening parentheses.
@@ -1563,6 +1578,14 @@ struct FormatStyle {
/// \brief Defines in which cases to put a space before opening parentheses.
SpaceBeforeParensOptions SpaceBeforeParens;
+ /// \brief If ``false``, spaces will be removed before range-based for loop
+ /// colon.
+ /// \code
+ /// true: false:
+ /// for (auto v : values) {} vs. for(auto v: values) {}
+ /// \endcode
+ bool SpaceBeforeRangeBasedForLoopColon;
+
/// \brief If ``true``, spaces may be inserted into ``()``.
/// \code
/// true: false:
@@ -1744,7 +1767,12 @@ struct FormatStyle {
SpaceAfterCStyleCast == R.SpaceAfterCStyleCast &&
SpaceAfterTemplateKeyword == R.SpaceAfterTemplateKeyword &&
SpaceBeforeAssignmentOperators == R.SpaceBeforeAssignmentOperators &&
+ SpaceBeforeCtorInitializerColon ==
+ R.SpaceBeforeCtorInitializerColon &&
+ SpaceBeforeInheritanceColon == R.SpaceBeforeInheritanceColon &&
SpaceBeforeParens == R.SpaceBeforeParens &&
+ SpaceBeforeRangeBasedForLoopColon ==
+ R.SpaceBeforeRangeBasedForLoopColon &&
SpaceInEmptyParentheses == R.SpaceInEmptyParentheses &&
SpacesBeforeTrailingComments == R.SpacesBeforeTrailingComments &&
SpacesInAngles == R.SpacesInAngles &&
diff --git a/lib/Format/Format.cpp b/lib/Format/Format.cpp
index 9229e224ea..5807db9407 100644
--- a/lib/Format/Format.cpp
+++ b/lib/Format/Format.cpp
@@ -411,7 +411,13 @@ template <> struct MappingTraits<FormatStyle> {
Style.SpaceAfterTemplateKeyword);
IO.mapOptional("SpaceBeforeAssignmentOperators",
Style.SpaceBeforeAssignmentOperators);
+ IO.mapOptional("SpaceBeforeCtorInitializerColon",
+ Style.SpaceBeforeCtorInitializerColon);
+ IO.mapOptional("SpaceBeforeInheritanceColon",
+ Style.SpaceBeforeInheritanceColon);
IO.mapOptional("SpaceBeforeParens", Style.SpaceBeforeParens);
+ IO.mapOptional("SpaceBeforeRangeBasedForLoopColon",
+ Style.SpaceBeforeRangeBasedForLoopColon);
IO.mapOptional("SpaceInEmptyParentheses", Style.SpaceInEmptyParentheses);
IO.mapOptional("SpacesBeforeTrailingComments",
Style.SpacesBeforeTrailingComments);
@@ -662,7 +668,10 @@ FormatStyle getLLVMStyle() {
LLVMStyle.SpacesInCStyleCastParentheses = false;
LLVMStyle.SpaceAfterCStyleCast = false;
LLVMStyle.SpaceAfterTemplateKeyword = true;
+ LLVMStyle.SpaceBeforeCtorInitializerColon = true;
+ LLVMStyle.SpaceBeforeInheritanceColon = true;
LLVMStyle.SpaceBeforeParens = FormatStyle::SBPO_ControlStatements;
+ LLVMStyle.SpaceBeforeRangeBasedForLoopColon = true;
LLVMStyle.SpaceBeforeAssignmentOperators = true;
LLVMStyle.SpacesInAngles = false;
diff --git a/lib/Format/TokenAnnotator.cpp b/lib/Format/TokenAnnotator.cpp
index 494b98cd73..4302ad4f6e 100644
--- a/lib/Format/TokenAnnotator.cpp
+++ b/lib/Format/TokenAnnotator.cpp
@@ -2575,8 +2575,15 @@ bool TokenAnnotator::spaceRequiredBefore(const AnnotatedLine &Line,
return true;
if (Right.is(tok::comma))
return false;
- if (Right.isOneOf(TT_CtorInitializerColon, TT_ObjCBlockLParen))
+ if (Right.is(TT_ObjCBlockLParen))
return true;
+ if (Right.is(TT_CtorInitializerColon))
+ return Style.SpaceBeforeCtorInitializerColon;
+ if (Right.is(TT_InheritanceColon) && !Style.SpaceBeforeInheritanceColon)
+ return false;
+ if (Right.is(TT_RangeBasedForLoopColon) &&
+ !Style.SpaceBeforeRangeBasedForLoopColon)
+ return false;
if (Right.is(tok::colon)) {
if (Line.First->isOneOf(tok::kw_case, tok::kw_default) ||
!Right.getNextNonComment() || Right.getNextNonComment()->is(tok::semi))
diff --git a/unittests/Format/FormatTest.cpp b/unittests/Format/FormatTest.cpp
index 1cda9827e1..eead11f55f 100644
--- a/unittests/Format/FormatTest.cpp
+++ b/unittests/Format/FormatTest.cpp
@@ -8933,6 +8933,114 @@ TEST_F(FormatTest, ConfigurableSpaceBeforeAssignmentOperators) {
verifyFormat("a or_eq 8;", Spaces);
}
+TEST_F(FormatTest, ConfigurableSpaceBeforeColon) {
+ verifyFormat("class Foo : public Bar {};");
+ verifyFormat("Foo::Foo() : foo(1) {}");
+ verifyFormat("for (auto a : b) {\n}");
+ verifyFormat("int x = a ? b : c;");
+ verifyFormat("{\n"
+ "label0:\n"
+ " int x = 0;\n"
+ "}");
+ verifyFormat("switch (x) {\n"
+ "case 1:\n"
+ "default:\n"
+ "}");
+
+ FormatStyle CtorInitializerStyle = getLLVMStyleWithColumns(30);
+ CtorInitializerStyle.SpaceBeforeCtorInitializerColon = false;
+ verifyFormat("class Foo : public Bar {};", CtorInitializerStyle);
+ verifyFormat("Foo::Foo(): foo(1) {}", CtorInitializerStyle);
+ verifyFormat("for (auto a : b) {\n}", CtorInitializerStyle);
+ verifyFormat("int x = a ? b : c;", CtorInitializerStyle);
+ verifyFormat("{\n"
+ "label1:\n"
+ " int x = 0;\n"
+ "}",
+ CtorInitializerStyle);
+ verifyFormat("switch (x) {\n"
+ "case 1:\n"
+ "default:\n"
+ "}",
+ CtorInitializerStyle);
+ CtorInitializerStyle.BreakConstructorInitializers =
+ FormatStyle::BCIS_AfterColon;
+ verifyFormat("Fooooooooooo::Fooooooooooo():\n"
+ " aaaaaaaaaaaaaaaa(1),\n"
+ " bbbbbbbbbbbbbbbb(2) {}",
+ CtorInitializerStyle);
+ CtorInitializerStyle.BreakConstructorInitializers =
+ FormatStyle::BCIS_BeforeComma;
+ verifyFormat("Fooooooooooo::Fooooooooooo()\n"
+ " : aaaaaaaaaaaaaaaa(1)\n"
+ " , bbbbbbbbbbbbbbbb(2) {}",
+ CtorInitializerStyle);
+ CtorInitializerStyle.BreakConstructorInitializers =
+ FormatStyle::BCIS_BeforeColon;
+ verifyFormat("Fooooooooooo::Fooooooooooo()\n"
+ " : aaaaaaaaaaaaaaaa(1),\n"
+ " bbbbbbbbbbbbbbbb(2) {}",
+ CtorInitializerStyle);
+ CtorInitializerStyle.ConstructorInitializerIndentWidth = 0;
+ verifyFormat("Fooooooooooo::Fooooooooooo()\n"
+ ": aaaaaaaaaaaaaaaa(1),\n"
+ " bbbbbbbbbbbbbbbb(2) {}",
+ CtorInitializerStyle);
+
+ FormatStyle InheritanceStyle = getLLVMStyle();
+ InheritanceStyle.SpaceBeforeInheritanceColon = false;
+ verifyFormat("class Foo: public Bar {};", InheritanceStyle);
+ verifyFormat("Foo::Foo() : foo(1) {}", InheritanceStyle);
+ verifyFormat("for (auto a : b) {\n}", InheritanceStyle);
+ verifyFormat("int x = a ? b : c;", InheritanceStyle);
+ verifyFormat("{\n"
+ "label2:\n"
+ " int x = 0;\n"
+ "}",
+ InheritanceStyle);
+ verifyFormat("switch (x) {\n"
+ "case 1:\n"
+ "default:\n"
+ "}",
+ InheritanceStyle);
+
+ FormatStyle ForLoopStyle = getLLVMStyle();
+ ForLoopStyle.SpaceBeforeRangeBasedForLoopColon = false;
+ verifyFormat("class Foo : public Bar {};", ForLoopStyle);
+ verifyFormat("Foo::Foo() : foo(1) {}", ForLoopStyle);
+ verifyFormat("for (auto a: b) {\n}", ForLoopStyle);
+ verifyFormat("int x = a ? b : c;", ForLoopStyle);
+ verifyFormat("{\n"
+ "label2:\n"
+ " int x = 0;\n"
+ "}",
+ ForLoopStyle);
+ verifyFormat("switch (x) {\n"
+ "case 1:\n"
+ "default:\n"
+ "}",
+ ForLoopStyle);
+
+ FormatStyle NoSpaceStyle = getLLVMStyle();
+ NoSpaceStyle.SpaceBeforeCtorInitializerColon = false;
+ NoSpaceStyle.SpaceBeforeInheritanceColon = false;
+ NoSpaceStyle.SpaceBeforeRangeBasedForLoopColon = false;
+ verifyFormat("class Foo: public Bar {};", NoSpaceStyle);
+ verifyFormat("Foo::Foo(): foo(1) {}", NoSpaceStyle);
+ verifyFormat("for (auto a: b) {\n}", NoSpaceStyle);
+ verifyFormat("int x = a ? b : c;", NoSpaceStyle);
+ verifyFormat("{\n"
+ "label3:\n"
+ " int x = 0;\n"
+ "}",
+ NoSpaceStyle);
+ verifyFormat("switch (x) {\n"
+ "case 1:\n"
+ "default:\n"
+ "}",
+ NoSpaceStyle);
+}
+
TEST_F(FormatTest, AlignConsecutiveAssignments) {
FormatStyle Alignment = getLLVMStyle();
Alignment.AlignConsecutiveAssignments = false;
@@ -10274,6 +10382,9 @@ TEST_F(FormatTest, ParsesConfigurationBools) {
CHECK_PARSE_BOOL(SpaceAfterCStyleCast);
CHECK_PARSE_BOOL(SpaceAfterTemplateKeyword);
CHECK_PARSE_BOOL(SpaceBeforeAssignmentOperators);
+ CHECK_PARSE_BOOL(SpaceBeforeCtorInitializerColon);
+ CHECK_PARSE_BOOL(SpaceBeforeInheritanceColon);
+ CHECK_PARSE_BOOL(SpaceBeforeRangeBasedForLoopColon);
CHECK_PARSE_NESTED_BOOL(BraceWrapping, AfterClass);
CHECK_PARSE_NESTED_BOOL(BraceWrapping, AfterControlStatement);