forked from OSchip/llvm-project
[clang-format] New format param ObjCBinPackProtocolList
Summary: This is an alternative approach to D42014 after some investigation by stephanemoore@ and myself. Previously, the format parameter `BinPackParameters` controlled both C function parameter list bin-packing and Objective-C protocol conformance list bin-packing. We found in the Google style, some teams were changing `BinPackParameters` from its default (`true`) to `false` so they could lay out Objective-C protocol conformance list items one-per-line instead of bin-packing them into as few lines as possible. To allow teams to use one-per-line Objective-C protocol lists without changing bin-packing for other areas like C function parameter lists, this diff introduces a new LibFormat parameter `ObjCBinPackProtocolList` to control the behavior just for ObjC protocol conformance lists. The new parameter is an enum which defaults to `Auto` to keep the previous behavior (delegating to `BinPackParameters`). Depends On D42649 Test Plan: New tests added. make -j12 FormatTests && ./tools/clang/unittests/Format/FormatTests Reviewers: jolesiak, stephanemoore, djasper Reviewed By: stephanemoore Subscribers: Wizard, hokein, cfe-commits, klimek Differential Revision: https://reviews.llvm.org/D42650 llvm-svn: 324131
This commit is contained in:
parent
e7e147f52c
commit
4dc658ca52
|
@ -390,6 +390,17 @@ struct FormatStyle {
|
|||
/// \endcode
|
||||
bool BinPackParameters;
|
||||
|
||||
/// \brief The style of wrapping parameters on the same line (bin-packed) or
|
||||
/// on one line each.
|
||||
enum BinPackStyle {
|
||||
/// Automatically determine parameter bin-packing behavior.
|
||||
BPS_Auto,
|
||||
/// Always bin-pack parameters.
|
||||
BPS_Always,
|
||||
/// Never bin-pack parameters.
|
||||
BPS_Never,
|
||||
};
|
||||
|
||||
/// \brief The style of breaking before or after binary operators.
|
||||
enum BinaryOperatorStyle {
|
||||
/// Break after operators.
|
||||
|
@ -1299,6 +1310,38 @@ struct FormatStyle {
|
|||
/// \brief The indentation used for namespaces.
|
||||
NamespaceIndentationKind NamespaceIndentation;
|
||||
|
||||
/// \brief Controls bin-packing Objective-C protocol conformance list
|
||||
/// items into as few lines as possible when they go over ``ColumnLimit``.
|
||||
///
|
||||
/// If ``Auto`` (the default), delegates to the value in
|
||||
/// ``BinPackParameters``. If that is ``true``, bin-packs Objective-C
|
||||
/// protocol conformance list items into as few lines as possible
|
||||
/// whenever they go over ``ColumnLimit``.
|
||||
///
|
||||
/// If ``Always``, always bin-packs Objective-C protocol conformance
|
||||
/// list items into as few lines as possible whenever they go over
|
||||
/// ``ColumnLimit``.
|
||||
///
|
||||
/// If ``Never``, lays out Objective-C protocol conformance list items
|
||||
/// onto individual lines whenever they go over ``ColumnLimit``.
|
||||
///
|
||||
/// \code
|
||||
/// Always (or Auto, if BinPackParameters=true):
|
||||
/// @interface ccccccccccccc () <
|
||||
/// ccccccccccccc, ccccccccccccc,
|
||||
/// ccccccccccccc, ccccccccccccc> {
|
||||
/// }
|
||||
///
|
||||
/// Never (or Auto, if BinPackParameters=false):
|
||||
/// @interface ddddddddddddd () <
|
||||
/// ddddddddddddd,
|
||||
/// ddddddddddddd,
|
||||
/// ddddddddddddd,
|
||||
/// ddddddddddddd> {
|
||||
/// }
|
||||
/// \endcode
|
||||
BinPackStyle ObjCBinPackProtocolList;
|
||||
|
||||
/// \brief The number of characters to use for indentation of ObjC blocks.
|
||||
/// \code{.objc}
|
||||
/// ObjCBlockIndentWidth: 4
|
||||
|
@ -1681,6 +1724,7 @@ struct FormatStyle {
|
|||
MacroBlockEnd == R.MacroBlockEnd &&
|
||||
MaxEmptyLinesToKeep == R.MaxEmptyLinesToKeep &&
|
||||
NamespaceIndentation == R.NamespaceIndentation &&
|
||||
ObjCBinPackProtocolList == R.ObjCBinPackProtocolList &&
|
||||
ObjCBlockIndentWidth == R.ObjCBlockIndentWidth &&
|
||||
ObjCSpaceAfterProperty == R.ObjCSpaceAfterProperty &&
|
||||
ObjCSpaceBeforeProtocolList == R.ObjCSpaceBeforeProtocolList &&
|
||||
|
|
|
@ -1222,9 +1222,20 @@ void ContinuationIndenter::moveStatePastScopeOpener(LineState &State,
|
|||
Current.MatchingParen->getPreviousNonComment() &&
|
||||
Current.MatchingParen->getPreviousNonComment()->is(tok::comma);
|
||||
|
||||
// If ObjCBinPackProtocolList is unspecified, fall back to BinPackParameters
|
||||
// for backwards compatibility.
|
||||
bool ObjCBinPackProtocolList =
|
||||
(Style.ObjCBinPackProtocolList == FormatStyle::BPS_Auto &&
|
||||
Style.BinPackParameters) ||
|
||||
Style.ObjCBinPackProtocolList == FormatStyle::BPS_Always;
|
||||
|
||||
bool BinPackDeclaration =
|
||||
(State.Line->Type != LT_ObjCDecl && Style.BinPackParameters) ||
|
||||
(State.Line->Type == LT_ObjCDecl && ObjCBinPackProtocolList);
|
||||
|
||||
AvoidBinPacking =
|
||||
(Style.Language == FormatStyle::LK_JavaScript && EndsInComma) ||
|
||||
(State.Line->MustBeDeclaration && !Style.BinPackParameters) ||
|
||||
(State.Line->MustBeDeclaration && !BinPackDeclaration) ||
|
||||
(!State.Line->MustBeDeclaration && !Style.BinPackArguments) ||
|
||||
(Style.ExperimentalAutoDetectBinPacking &&
|
||||
(Current.PackingKind == PPK_OnePerLine ||
|
||||
|
|
|
@ -105,6 +105,14 @@ template <> struct ScalarEnumerationTraits<FormatStyle::ShortFunctionStyle> {
|
|||
}
|
||||
};
|
||||
|
||||
template <> struct ScalarEnumerationTraits<FormatStyle::BinPackStyle> {
|
||||
static void enumeration(IO &IO, FormatStyle::BinPackStyle &Value) {
|
||||
IO.enumCase(Value, "Auto", FormatStyle::BPS_Auto);
|
||||
IO.enumCase(Value, "Always", FormatStyle::BPS_Always);
|
||||
IO.enumCase(Value, "Never", FormatStyle::BPS_Never);
|
||||
}
|
||||
};
|
||||
|
||||
template <> struct ScalarEnumerationTraits<FormatStyle::BinaryOperatorStyle> {
|
||||
static void enumeration(IO &IO, FormatStyle::BinaryOperatorStyle &Value) {
|
||||
IO.enumCase(Value, "All", FormatStyle::BOS_All);
|
||||
|
@ -378,6 +386,7 @@ template <> struct MappingTraits<FormatStyle> {
|
|||
IO.mapOptional("MacroBlockEnd", Style.MacroBlockEnd);
|
||||
IO.mapOptional("MaxEmptyLinesToKeep", Style.MaxEmptyLinesToKeep);
|
||||
IO.mapOptional("NamespaceIndentation", Style.NamespaceIndentation);
|
||||
IO.mapOptional("ObjCBinPackProtocolList", Style.ObjCBinPackProtocolList);
|
||||
IO.mapOptional("ObjCBlockIndentWidth", Style.ObjCBlockIndentWidth);
|
||||
IO.mapOptional("ObjCSpaceAfterProperty", Style.ObjCSpaceAfterProperty);
|
||||
IO.mapOptional("ObjCSpaceBeforeProtocolList",
|
||||
|
@ -637,6 +646,7 @@ FormatStyle getLLVMStyle() {
|
|||
LLVMStyle.MaxEmptyLinesToKeep = 1;
|
||||
LLVMStyle.KeepEmptyLinesAtTheStartOfBlocks = true;
|
||||
LLVMStyle.NamespaceIndentation = FormatStyle::NI_None;
|
||||
LLVMStyle.ObjCBinPackProtocolList = FormatStyle::BPS_Auto;
|
||||
LLVMStyle.ObjCBlockIndentWidth = 2;
|
||||
LLVMStyle.ObjCSpaceAfterProperty = false;
|
||||
LLVMStyle.ObjCSpaceBeforeProtocolList = true;
|
||||
|
|
|
@ -281,8 +281,7 @@ TEST_F(FormatTestObjC, FormatObjCInterface) {
|
|||
" ccccccccccccc, ccccccccccccc,\n"
|
||||
" ccccccccccccc, ccccccccccccc> {\n"
|
||||
"}");
|
||||
|
||||
Style.BinPackParameters = false;
|
||||
Style.ObjCBinPackProtocolList = FormatStyle::BPS_Never;
|
||||
verifyFormat("@interface ddddddddddddd () <\n"
|
||||
" ddddddddddddd,\n"
|
||||
" ddddddddddddd,\n"
|
||||
|
@ -290,6 +289,20 @@ TEST_F(FormatTestObjC, FormatObjCInterface) {
|
|||
" ddddddddddddd> {\n"
|
||||
"}");
|
||||
|
||||
Style.BinPackParameters = false;
|
||||
Style.ObjCBinPackProtocolList = FormatStyle::BPS_Auto;
|
||||
verifyFormat("@interface eeeeeeeeeeeee () <\n"
|
||||
" eeeeeeeeeeeee,\n"
|
||||
" eeeeeeeeeeeee,\n"
|
||||
" eeeeeeeeeeeee,\n"
|
||||
" eeeeeeeeeeeee> {\n"
|
||||
"}");
|
||||
Style.ObjCBinPackProtocolList = FormatStyle::BPS_Always;
|
||||
verifyFormat("@interface fffffffffffff () <\n"
|
||||
" fffffffffffff, fffffffffffff,\n"
|
||||
" fffffffffffff, fffffffffffff> {\n"
|
||||
"}");
|
||||
|
||||
Style = getGoogleStyle(FormatStyle::LK_ObjC);
|
||||
verifyFormat("@interface Foo : NSObject <NSSomeDelegate> {\n"
|
||||
" @public\n"
|
||||
|
|
Loading…
Reference in New Issue