diff --git a/src/Razor/src/Microsoft.CodeAnalysis.Razor.Workspaces/Formatting/Passes/CSharpFormattingPass.CSharpDocumentGenerator.cs b/src/Razor/src/Microsoft.CodeAnalysis.Razor.Workspaces/Formatting/Passes/CSharpFormattingPass.CSharpDocumentGenerator.cs index bd587cc945e..d5044ab16cc 100644 --- a/src/Razor/src/Microsoft.CodeAnalysis.Razor.Workspaces/Formatting/Passes/CSharpFormattingPass.CSharpDocumentGenerator.cs +++ b/src/Razor/src/Microsoft.CodeAnalysis.Razor.Workspaces/Formatting/Passes/CSharpFormattingPass.CSharpDocumentGenerator.cs @@ -548,10 +548,13 @@ public override LineInfo VisitMarkupStartTag(MarkupStartTagSyntax node) { var element = (MarkupElementSyntax)node.Parent; - if (node.Name.Content == "textarea") + if (ElementContentsShouldNotBeIndented(node)) { - // The contents of textareas is significant, so we never want any formatting to happen inside them - _ignoreUntilLine = GetLineNumber(element.EndTag?.CloseAngle ?? element.StartTag.CloseAngle); + // The contents of textareas is significant, so we never want any formatting to happen in their contents + if (GetLineNumber(node) == GetLineNumber(node.CloseAngle)) + { + _ignoreUntilLine = GetLineNumber(element.EndTag?.CloseAngle ?? element.StartTag.CloseAngle); + } return EmitCurrentLineAsComment(); } @@ -645,6 +648,11 @@ private bool ElementCausesIndentation(BaseMarkupStartTagSyntax node) return true; } + private static bool ElementContentsShouldNotBeIndented(BaseMarkupStartTagSyntax node) + { + return node.Name.Content.Equals("textarea", StringComparison.OrdinalIgnoreCase); + } + public override LineInfo VisitRazorMetaCode(RazorMetaCodeSyntax node) { // This could be a directive attribute, like @bind-Value="asdf" @@ -736,10 +744,16 @@ public override LineInfo VisitMarkupCommentBlock(MarkupCommentBlockSyntax node) htmlIndentLevel = FormattingUtilities.GetIndentationLevel(nameSpan.Start - lineStart, _tabSize, out additionalIndentation); } - // If the element has caused indentation, then we'll want to take one level off our attribute indentation to - // compensate. Need to be careful here because things like ` 0) + if (ElementContentsShouldNotBeIndented(startTag) && + GetLineNumber(node) == GetLineNumber(startTag.CloseAngle)) + { + // If this is the last line of a tag that shouldn't be indented, honour that + _ignoreUntilLine = GetLineNumber(startTag.GetEndTag()?.CloseAngle ?? startTag.CloseAngle); + } + else if (ElementCausesIndentation(startTag) && htmlIndentLevel > 0) { + // If the element has caused indentation, then we'll want to take one level off our attribute indentation to + // compensate. Need to be careful here because things like ` RunFormattingTestAsync( + input: """ + + """, + expected: """ + + """); + + [FormattingTestFact] + internal Task TextArea_WithAttributes_IndentByOne() + => RunFormattingTestAsync( + input: """ + + """, + expected: """ + + """, + attributeIndentStyle: AttributeIndentStyle.IndentByOne); + [FormattingTestFact] [WorkItem("https://github.com/dotnet/razor/issues/11777")] public Task RangeFormat_AfterProperty() diff --git a/src/Razor/test/Microsoft.VisualStudio.Razor.IntegrationTests/Formatting/TestFiles/Expected/FormatDocument.cshtml b/src/Razor/test/Microsoft.VisualStudio.Razor.IntegrationTests/Formatting/TestFiles/Expected/FormatDocument.cshtml index 29a95b3bf6d..44e3f9d6bdc 100644 --- a/src/Razor/test/Microsoft.VisualStudio.Razor.IntegrationTests/Formatting/TestFiles/Expected/FormatDocument.cshtml +++ b/src/Razor/test/Microsoft.VisualStudio.Razor.IntegrationTests/Formatting/TestFiles/Expected/FormatDocument.cshtml @@ -16,6 +16,6 @@ test
@(Html.DropDownList("list") - .ToString() - ) + .ToString() + )
diff --git a/src/Razor/test/Microsoft.VisualStudio.Razor.IntegrationTests/Formatting/TestFiles/Expected/FormatOnPaste.cshtml b/src/Razor/test/Microsoft.VisualStudio.Razor.IntegrationTests/Formatting/TestFiles/Expected/FormatOnPaste.cshtml index f273d2aef49..3157af86440 100644 --- a/src/Razor/test/Microsoft.VisualStudio.Razor.IntegrationTests/Formatting/TestFiles/Expected/FormatOnPaste.cshtml +++ b/src/Razor/test/Microsoft.VisualStudio.Razor.IntegrationTests/Formatting/TestFiles/Expected/FormatOnPaste.cshtml @@ -47,14 +47,14 @@ @foreach (var item in ViewBag.RequestOrder) - - - + + -
+
+
@if (true) { - + - } + }
diff --git a/src/Razor/test/Microsoft.VisualStudio.Razor.IntegrationTests/Formatting/TestFiles/Expected/FormatSelection.cshtml b/src/Razor/test/Microsoft.VisualStudio.Razor.IntegrationTests/Formatting/TestFiles/Expected/FormatSelection.cshtml index 2e40c8ba43f..0038e564992 100644 --- a/src/Razor/test/Microsoft.VisualStudio.Razor.IntegrationTests/Formatting/TestFiles/Expected/FormatSelection.cshtml +++ b/src/Razor/test/Microsoft.VisualStudio.Razor.IntegrationTests/Formatting/TestFiles/Expected/FormatSelection.cshtml @@ -25,29 +25,29 @@ }
- @functions { +@functions { - int userAge = 0; + int userAge = 0; - string HelloMessage(string user) - { - var msg = "Hi " + user + "how are you?"; - return msg; - } + string HelloMessage(string user) + { + var msg = "Hi " + user + "how are you?"; + return msg; + } - int Age - { - get - { - return userAge; - } - set - { - userAge = value; - } - } + int Age + { + get + { + return userAge; } -
+ set + { + userAge = value; + } + } +} +