cipri.l
cipri.l

Reputation: 819

How do I format code selection and maintain leading trivia with Roslyn?

I want to format the code that I modified with roslyn. I am modifying code inside a method. I don't want to reformat the entire file. The original formatting looks the following:

MyNamespace
{
    class CodeBasicTests
    {
        int OperationOrder_0()
        {
            int a = 20;
            int b = 10;
            int sum = a + b;
            return (int) sum;
        }
    }
}

After I format the body of the method, it gets aligned to the border, not to the method signature.

MyNamespace
{
    class CodeBasicTests
    {
int OperationOrder_0()
{
    int a = 20;
    int b = 10;
    int c = 30; //new instruction
    int sum = a + b + c;
    return (int) sum;
}
     }
}

I have tried the following inside the method visitor (CSharpSyntaxRewriter):

MethodDeclarationSyntax method = visited method node;
updatedMethod = method.ReplaceNode(method.Body, newBody);
updatedMethod = updatedMethod.NormalizeWhitespace().WithTriviaFrom(method);
return updatedMethod;

or selecting only the method body

newBody = (BlockSyntax) Formatter.Format(oldBody, texts, VisualStudioSolutionHandler.workspace);

I have tried also to work with the text spans of the formatter, but I don't manage to make it work at at all.

I don't want/know to write a visitor to insert a right tab to every element in the newBody because the statements that I insert are much more complex, and I would like to use the autoformatting feature for the updated method only.

I don't know hot to keep the original method indentation.

Upvotes: 2

Views: 2368

Answers (1)

Jeff Mercado
Jeff Mercado

Reputation: 134881

Replace the trivia with the current trivia list with the new trivia inserted in place.

Here's an example of an extension method I created to add newlines to certain annotated nodes.

public static TNode AddNewlineToAnnotated<TNode>(this TNode node, string annotationKind)
    where TNode : CSharpSyntaxNode =>
    node.ReplaceNodes(node.GetAnnotatedNodes(annotationKind), (_, n) =>
        n.WithLeadingTrivia(n.GetLeadingTrivia()
            .Insert(0, SyntaxTree.ElasticEndOfLine(Environment.NewLine))
        )
    );

Getting the leading trivia gives you a SyntaxTriviaList and you can Add(), Insert() or otherwise modify the trivia list to give you a new trivia list.

Upvotes: 1

Related Questions