diff --git a/src/dfmt.d b/src/dfmt.d index 6e243a0..86d314e 100644 --- a/src/dfmt.d +++ b/src/dfmt.d @@ -321,6 +321,8 @@ private: } else if (!currentIs(tok!"{") && !currentIs(tok!"comment")) { + if (ifIndents.length) + ifIndents.pop(); pushIndent(); newline(); } @@ -434,31 +436,38 @@ private: else if (!assumeSorted(astInformation.caseEndLocations) .equalRange(current.index).empty) { - if (!(peekIs(tok!"case", false) || peekIs(tok!"default", false) - || peekIs(tok!"}") || peekIsLabel())) - { - indentLevel++; - } + indentLevel++; writeToken(); newline(); } - else if (peekBackIs(tok!"identifier") && (peekBack2Is(tok!";", true) - || peekBack2Is(tok!"}", true) || peekBack2Is(tok!"{", true))) + else if (peekBackIs(tok!"identifier") && (index <= 1 + || peekBack2Is(tok!"{", true) || peekBack2Is(tok!"}", true) + || peekBack2Is(tok!";", true) || peekBack2Is(tok!":", true)) + && !peekIs(tok!"{") && !(isBlockHeader(1) && !peekIs(tok!"if"))) { - if (tempIndent < 0) - tempIndent = 0; - else - popIndent(); + indentLevel++; writeToken(); - if (isBlockHeader() && !currentIs(tok!"if")) - write(" "); - else if (!currentIs(tok!"{")) - newline(); + newline(); } else { - write(" : "); - index++; + if (peekIs(tok!"..")) + writeToken(); + else if (peekIs(tok!"{")) + { + writeToken(); + pushIndent(); + } + else if (isBlockHeader(1) && !peekIs(tok!"if")) + { + writeToken(); + write(" "); + } + else + { + write(" : "); + index++; + } } break; case tok!"]": @@ -467,18 +476,17 @@ private: write(" "); break; case tok!";": - if (peekIs(tok!"else")) - { + if (peekIs(tok!"else") && ifIndents.length) tempIndent = ifIndents.top(); - if (ifIndents.length) - ifIndents.pop(); - } - else if (braceIndents.top() < tempIndent) + else if (!peekIs(tok!"}")) { - if (!peekIs(tok!"}")) - tempIndent = 0; + if (ifIndents.length) + { + tempIndent = ifIndents.top(); + ifIndents.pop(); + } else - popIndent(); + tempIndent = 0; } writeToken(); linebreakHints = []; @@ -681,7 +689,8 @@ private: { if (currentIs(tok!"{")) { - braceIndents.push(tempIndent); + braceIndents.push(indentLevel); + braceTempIndents.push(tempIndent); depth++; if (assumeSorted(astInformation.structInitStartLocations) .equalRange(tokens[index].index).length) @@ -708,7 +717,6 @@ private: } else if (currentIs(tok!"}")) { - braceIndents.pop(); depth--; if (assumeSorted(astInformation.structInitEndLocations) .equalRange(tokens[index].index).length) @@ -731,8 +739,6 @@ private: if (config.braceStyle == BraceStyle.otbs && currentIs(tok!"else")) write(" "); index++; - if (peekIs(tok!"case") || peekIs(tok!"default")) - indentLevel--; if (ifIndents.length >= 2 && ifIndents.top == tempIndent && !currentIs(tok!"else")) { ifIndents.pop(); @@ -813,7 +819,6 @@ private: formatStep(); } while (index < tokens.length && depth > 0); -// popIndent(); tempIndent = t; linebreakHints = []; } @@ -835,93 +840,16 @@ private: void formatSwitch() { - immutable l = indentLevel; + switchIndents.push(indentLevel); writeToken(); // switch write(" "); writeParens(true); - if (currentIs(tok!"with")) + while (currentIs(tok!"with")) { writeToken(); write(" "); writeParens(true); } - if (!currentIs(tok!"{")) - return; - if (config.braceStyle == BraceStyle.otbs) - write(" "); - else - newline(); - writeToken(); - if (!currentIs(tok!"case") && !currentIs(tok!"default") && !currentIs(tok!"}")) - indentLevel++; - newline(); - while (index < tokens.length) - { - if (currentIs(tok!"}")) - { - indentLevel = l; - indent(); - writeToken(); - newline(); - return; - } - else if (currentIs(tok!";") && peekIs(tok!"}", false)) - { - writeToken(); - newline(); - indentLevel = l; - writeToken(); - newline(); - return; - } - else if (currentIs(tok!"case")) - { - writeToken(); - write(" "); - } - else if (currentIs(tok!":")) - { - if (peekIs(tok!"..")) - { - writeToken(); - write(" "); - writeToken(); - write(" "); - } - else if (peekIsLabel()) - { - writeToken(); - pushIndent(); - newline(); - writeToken(); - writeToken(); - pushIndent(); - newline(); - } - else - goto peek; - } - else if (currentIs(tok!"}", false)) - break; - else - { - peek: - if (peekIs(tok!"case", false) || peekIs(tok!"default", false) - || peekIs(tok!"}", false)) - { - indentLevel = l; - if (peekIsLabel()) - pushIndent(); - } - formatStep(); - } - } - indentLevel = l; - if (currentIs(tok!"}")) - { - writeToken(); - newline(); - } } int currentTokenLength() pure @safe @nogc @@ -1089,14 +1017,30 @@ private: currentLineLength = 0; if (hasCurrent) { + bool switchLabel = false; + if (switchIndents.length && (currentIs(tok!"case") || currentIs(tok!"default") + || (currentIs(tok!"identifier") && peekIs(tok!":")))) + { + indentLevel = switchIndents.top(); + switchLabel = true; + } if (currentIs(tok!"}")) { - tempIndent = braceIndents.top(); - indentLevel--; + if (braceIndents.length) + { + assert (braceTempIndents.length); + indentLevel = braceIndents.top(); + tempIndent = braceTempIndents.top(); + braceIndents.pop(); + braceTempIndents.pop(); + } + if (switchIndents.length && indentLevel == switchIndents.top) + switchIndents.pop(); } else if ((!assumeSorted(astInformation.attributeDeclarationLines) - .equalRange(current.line).empty) || (currentIs(tok!"identifier") - && peekIs(tok!":") && (!isBlockHeader(2) || peek2Is(tok!"if")))) + .equalRange(current.line).empty) || (!switchLabel + && currentIs(tok!"identifier") && peekIs(tok!":") + && (!isBlockHeader(2) || peek2Is(tok!"if")))) { tempIndent--; } @@ -1162,7 +1106,9 @@ private: size_t[] linebreakHints; FixedStack ifIndents; + FixedStack braceTempIndents; FixedStack braceIndents; + FixedStack switchIndents; /// Configuration FormatterConfig* config; diff --git a/tests/issue0043.d b/tests/issue0043.d index a954df7..0f70fed 100644 --- a/tests/issue0043.d +++ b/tests/issue0043.d @@ -3,7 +3,7 @@ unittest switch (something) with (stuff){ case 1: case 2: label:doStuff(); - case 3: + case 3: .. case 4: doOtherStuff(); goto label; default: diff --git a/tests/issue0043.d.ref b/tests/issue0043.d.ref index 12ab96e..a372d79 100644 --- a/tests/issue0043.d.ref +++ b/tests/issue0043.d.ref @@ -6,7 +6,7 @@ unittest case 2: label: doStuff(); - case 3: + case 3: .. case 4: doOtherStuff(); goto label; default: diff --git a/tests/issue0080.d b/tests/issue0080.d new file mode 100644 index 0000000..4740565 --- /dev/null +++ b/tests/issue0080.d @@ -0,0 +1,13 @@ +unittest +{ + switch (x) + { + case a: + return; + version (A) + { + case b: + return; + } + } +} diff --git a/tests/issue0080.d.ref b/tests/issue0080.d.ref new file mode 100644 index 0000000..d6f65b8 --- /dev/null +++ b/tests/issue0080.d.ref @@ -0,0 +1,13 @@ +unittest +{ + switch (x) + { + case a: + return; + version (A) + { + case b: + return; + } + } +} diff --git a/tests/issue0081.d.ref b/tests/issue0081.d.ref index 9666268..18fe78e 100644 --- a/tests/issue0081.d.ref +++ b/tests/issue0081.d.ref @@ -1,3 +1,18 @@ +unittest +{ + if (0) + if (0) + { + } + else if (0) + { + } + else + { + } + doSomething(); +} + unittest { if (0)