public override CommandResult Invoke(Guid group, int id, object inputArg, ref object outputArg) { string originalText = TargetBuffer.CurrentSnapshot.GetText(); string formattedText = string.Empty; var formatter = new RFormatter(Shell.GetService <IREditorSettings>().FormatOptions); try { formattedText = formatter.Format(originalText); } catch (Exception ex) { Debug.Assert(false, "Formatter exception: ", ex.Message); } if (!string.IsNullOrEmpty(formattedText) && !string.Equals(formattedText, originalText, StringComparison.Ordinal)) { var selectionTracker = new RSelectionTracker(TextView, TargetBuffer, new TextRange(0, TargetBuffer.CurrentSnapshot.Length)); selectionTracker.StartTracking(automaticTracking: false); try { using (var massiveChange = new MassiveChange(TextView, TargetBuffer, Shell, Resources.FormatDocument)) { IREditorDocument document = REditorDocument.TryFromTextBuffer(TargetBuffer); if (document != null) { document.EditorTree.Invalidate(); } var caretPosition = TextView.Caret.Position.BufferPosition; var viewPortLeft = TextView.ViewportLeft; RTokenizer tokenizer = new RTokenizer(); string oldText = TargetBuffer.CurrentSnapshot.GetText(); IReadOnlyTextRangeCollection <RToken> oldTokens = tokenizer.Tokenize(oldText); IReadOnlyTextRangeCollection <RToken> newTokens = tokenizer.Tokenize(formattedText); #if DEBUG //if (oldTokens.Count != newTokens.Count) { // for (int i = 0; i < Math.Min(oldTokens.Count, newTokens.Count); i++) { // if (oldTokens[i].TokenType != newTokens[i].TokenType) { // Debug.Assert(false, Invariant($"Token type difference at {i}")); // break; // } else if (oldTokens[i].Length != newTokens[i].Length) { // Debug.Assert(false, Invariant($"token length difference at {i}")); // break; // } // } //} #endif IncrementalTextChangeApplication.ApplyChangeByTokens( TargetBuffer, new TextStream(oldText), new TextStream(formattedText), oldTokens, newTokens, TextRange.FromBounds(0, oldText.Length), Resources.FormatDocument, selectionTracker, Shell); } } finally { selectionTracker.EndTracking(); } return(new CommandResult(CommandStatus.Supported, 0)); } return(CommandResult.NotSupported); }
public override CommandResult Invoke(Guid group, int id, object inputArg, ref object outputArg) { var originalText = TargetBuffer.CurrentSnapshot.GetText(); var formattedText = string.Empty; var formatter = new RFormatter(Services.GetService <IREditorSettings>().FormatOptions); try { formattedText = formatter.Format(originalText); } catch (Exception ex) { Debug.Assert(false, "Formatter exception: ", ex.Message); } if (!string.IsNullOrEmpty(formattedText) && !string.Equals(formattedText, originalText, StringComparison.Ordinal)) { var selectionTracker = new RSelectionTracker(TextView, TargetBuffer, new TextRange(0, TargetBuffer.CurrentSnapshot.Length)); selectionTracker.StartTracking(automaticTracking: false); try { using (var massiveChange = new MassiveChange(TextView, TargetBuffer, Services, Windows_Resources.FormatDocument)) { var document = TargetBuffer.GetEditorDocument <IREditorDocument>(); document?.EditorTree?.Invalidate(); var tokenizer = new RTokenizer(); var oldText = TargetBuffer.CurrentSnapshot.GetText(); var oldTokens = tokenizer.Tokenize(oldText); var newTokens = tokenizer.Tokenize(formattedText); #if DEBUG //if (oldTokens.Count != newTokens.Count) { // for (int i = 0; i < Math.Min(oldTokens.Count, newTokens.Count); i++) { // if (oldTokens[i].TokenType != newTokens[i].TokenType) { // Debug.Assert(false, Invariant($"Token type difference at {i}")); // break; // } else if (oldTokens[i].Length != newTokens[i].Length) { // Debug.Assert(false, Invariant($"token length difference at {i}")); // break; // } // } //} #endif var wsChangeHandler = Services.GetService <IIncrementalWhitespaceChangeHandler>(); wsChangeHandler.ApplyChange( TargetBuffer.ToEditorBuffer(), new TextStream(oldText), new TextStream(formattedText), oldTokens, newTokens, TextRange.FromBounds(0, oldText.Length), Windows_Resources.FormatDocument, selectionTracker); } } finally { selectionTracker.EndTracking(); } return(new CommandResult(CommandStatus.Supported, 0)); } return(CommandResult.NotSupported); }
public static bool FormatRangeExact(ITextView textView, ITextBuffer textBuffer, ITextRange formatRange, RFormatOptions options) { ITextSnapshot snapshot = textBuffer.CurrentSnapshot; Span spanToFormat = new Span(formatRange.Start, formatRange.Length); string spanText = snapshot.GetText(spanToFormat.Start, spanToFormat.Length); string trimmedSpanText = spanText.Trim(); RFormatter formatter = new RFormatter(options); string formattedText = formatter.Format(trimmedSpanText); formattedText = formattedText.Trim(); // There may be inserted line breaks after { // Apply formatted text without indentation. We then will update the parse tree // so we can calculate proper line indents from the AST via the smart indenter. if (!spanText.Equals(formattedText, StringComparison.Ordinal)) { // Extract existing indent before applying changes. Existing indent // may be used by the smart indenter for function argument lists. var startLine = snapshot.GetLineFromPosition(spanToFormat.Start); var originalIndentSizeInSpaces = IndentBuilder.TextIndentInSpaces(startLine.GetText(), options.IndentSize); var selectionTracker = new RSelectionTracker(textView, textBuffer, formatRange); RTokenizer tokenizer = new RTokenizer(); IReadOnlyTextRangeCollection <RToken> oldTokens = tokenizer.Tokenize(spanText); IReadOnlyTextRangeCollection <RToken> newTokens = tokenizer.Tokenize(formattedText); IncrementalTextChangeApplication.ApplyChangeByTokens( textBuffer, new TextStream(spanText), new TextStream(formattedText), oldTokens, newTokens, formatRange, Resources.AutoFormat, selectionTracker, () => { var ast = UpdateAst(textBuffer); // Apply indentation IndentLines(textView, textBuffer, new TextRange(formatRange.Start, formattedText.Length), ast, options, originalIndentSizeInSpaces); }); return(true); } return(false); }
public static bool FormatRangeExact(ITextView textView, ITextBuffer textBuffer, ITextRange formatRange, AstRoot ast, RFormatOptions options, int scopeStatementPosition, bool respectUserIndent = true) { ITextSnapshot snapshot = textBuffer.CurrentSnapshot; Span spanToFormat = new Span(formatRange.Start, formatRange.Length); string spanText = snapshot.GetText(spanToFormat.Start, spanToFormat.Length); string trimmedSpanText = spanText.Trim(); if (trimmedSpanText == "}") { // Locate opening { and its statement var scopeNode = ast.GetNodeOfTypeFromPosition <IAstNodeWithScope>(spanToFormat.Start); if (scopeNode != null) { scopeStatementPosition = scopeNode.Start; } } RFormatter formatter = new RFormatter(options); string formattedText = formatter.Format(trimmedSpanText); formattedText = formattedText.Trim(); // there may be inserted line breaks after { formattedText = IndentLines(textBuffer, spanToFormat.Start, ast, formattedText, options, scopeStatementPosition, respectUserIndent); if (!spanText.Equals(formattedText, StringComparison.Ordinal)) { var selectionTracker = new RSelectionTracker(textView, textBuffer); RTokenizer tokenizer = new RTokenizer(); IReadOnlyTextRangeCollection <RToken> oldTokens = tokenizer.Tokenize(spanText); IReadOnlyTextRangeCollection <RToken> newTokens = tokenizer.Tokenize(formattedText); IncrementalTextChangeApplication.ApplyChangeByTokens( textBuffer, new TextStream(spanText), new TextStream(formattedText), oldTokens, newTokens, formatRange, Resources.AutoFormat, selectionTracker); return(true); } return(false); }