Пример #1
0
        async void CompletionWindowManager_WindowClosed(object sender, EventArgs e)
        {
            var document = DocumentContext.AnalysisDocument;

            if (document == null)
            {
                return;
            }
            var caretPosition = Editor.CaretOffset;
            var token         = await CSharpEditorFormattingService.GetTokenBeforeTheCaretAsync(document, caretPosition, default(CancellationToken)).ConfigureAwait(false);

            if (token.IsMissing || !token.Parent.IsKind(SyntaxKind.ElseDirectiveTrivia))
            {
                return;
            }
            var tokenRange = Microsoft.CodeAnalysis.CSharp.Utilities.FormattingRangeHelper.FindAppropriateRange(token);

            if (tokenRange == null || !tokenRange.HasValue || tokenRange.Value.Item1.Equals(tokenRange.Value.Item2))
            {
                return;
            }

            var value = tokenRange.Value;

            using (var undo = Editor.OpenUndoGroup()) {
                OnTheFlyFormatter.Format(Editor, DocumentContext, value.Item1.SpanStart, value.Item2.Span.End, optionSet: optionSet);
            }
        }
 void RunFormatter(DocumentLocation location)
 {
     if (OnTheFlyFormatting && textEditorData != null && !(textEditorData.CurrentMode is TextLinkEditMode) && !(textEditorData.CurrentMode is InsertionCursorEditMode))
     {
         OnTheFlyFormatter.Format(Document, location);
     }
 }
Пример #3
0
        void RunFormatter(MonoDevelop.Ide.Editor.DocumentLocation location)
        {
            if (!OnTheFlyFormatting || Editor == null || Editor.EditMode != EditMode.Edit)
            {
                return;
            }
            var offset = Editor.LocationToOffset(location);

            OnTheFlyFormatter.Format(Editor, DocumentContext, offset, offset, optionSet: optionSet);
        }
        public override async Task PostFomatPastedText(int insertionOffset, int insertedChars)
        {
            if (indent.Editor.Options.IndentStyle == IndentStyle.None ||
                indent.Editor.Options.IndentStyle == IndentStyle.Auto)
            {
                return;
            }
            if (DefaultSourceEditorOptions.Instance.OnTheFlyFormatting)
            {
                var tree = await indent.DocumentContext.AnalysisDocument.GetSyntaxTreeAsync();

                var startLine        = indent.Editor.GetLineByOffset(insertionOffset);
                var endLine          = indent.Editor.GetLineByOffset(insertionOffset + insertedChars);
                int lineStartOffset  = startLine.Offset != endLine.Offset ? startLine.Offset : insertionOffset;
                int formatCharsCount = insertedChars + (insertionOffset - lineStartOffset);
                var policy           = indent.DocumentContext.GetFormattingPolicy();
                var textPolicy       = indent.DocumentContext.Project.Policies.Get <Ide.Gui.Content.TextStylePolicy> (indent.Editor.MimeType);
                var optionSet        = policy.CreateOptions(textPolicy);
                var span             = new TextSpan(lineStartOffset, formatCharsCount);
                var doc = await Formatter.FormatAsync(indent.DocumentContext.AnalysisDocument, span, optionSet);

                OnTheFlyFormatter.ApplyNewTree(indent.Editor, lineStartOffset, true, span, tree, await doc.GetSyntaxTreeAsync());
                return;
            }
            // Just correct the start line of the paste operation - the text is already indented.
            var curLine       = indent.Editor.GetLineByOffset(insertionOffset);
            var curLineOffset = curLine.Offset;

            indent.SafeUpdateIndentEngine(curLineOffset);
            if (!indent.stateTracker.IsInsideOrdinaryCommentOrString)
            {
                int    pos       = curLineOffset;
                string curIndent = curLine.GetIndentation(indent.Editor);
                int    nlwsp     = curIndent.Length;
                if (!indent.stateTracker.LineBeganInsideMultiLineComment || (nlwsp < curLine.LengthIncludingDelimiter && indent.Editor.GetCharAt(curLineOffset + nlwsp) == '*'))
                {
                    // Possibly replace the indent
                    indent.SafeUpdateIndentEngine(curLineOffset + curLine.Length);
                    string newIndent = indent.stateTracker.ThisLineIndent;
                    if (newIndent != curIndent)
                    {
                        if (CompletionWindowManager.IsVisible)
                        {
                            if (pos < CompletionWindowManager.CodeCompletionContext.TriggerOffset)
                            {
                                CompletionWindowManager.CodeCompletionContext.TriggerOffset -= nlwsp;
                            }
                        }
                        indent.Editor.ReplaceText(pos, nlwsp, newIndent);
                        //						textEditorData.Document.CommitLineUpdate (textEditorData.CaretLine);
                    }
                }
            }
            indent.Editor.FixVirtualIndentation();
        }
Пример #5
0
        void HandleOnTheFlyFormatting(KeyDescriptor descriptor)
        {
            if (descriptor.KeyChar == '{')
            {
                return;
            }
            SafeUpdateIndentEngine(Editor.CaretOffset);
            bool skipFormatting = stateTracker.IsInsideOrdinaryCommentOrString;

            if (!skipFormatting && !(stateTracker.IsInsideComment || stateTracker.IsInsideString))
            {
                if (DocumentContext.ParsedDocument == null || DocumentContext.ParsedDocument.GetAst <SemanticModel> () == null)
                {
                    return;
                }
                var document = DocumentContext.AnalysisDocument;
                if (document == null)
                {
                    return;
                }
                if (!skipFormatting && service.SupportsFormattingOnTypedCharacter(document, descriptor.KeyChar))
                {
                    var caretPosition = Editor.CaretOffset;
                    var token         = CSharpEditorFormattingService.GetTokenBeforeTheCaretAsync(document, caretPosition, default(CancellationToken)).Result;
                    if (token.IsMissing || !service.ValidSingleOrMultiCharactersTokenKind(descriptor.KeyChar, token.Kind()) || token.IsKind(SyntaxKind.EndOfFileToken) || token.IsKind(SyntaxKind.None))
                    {
                        return;
                    }
                    if (CSharpEditorFormattingService.TokenShouldNotFormatOnTypeChar(token))
                    {
                        return;
                    }
                    using (var undo = Editor.OpenUndoGroup()) {
                        if (OnTheFlyFormatting && Editor != null && Editor.EditMode == EditMode.Edit)
                        {
                            var oldVersion = Editor.Version;
                            OnTheFlyFormatter.FormatStatmentAt(Editor, DocumentContext, Editor.CaretLocation, optionSet: optionSet);
                            if (oldVersion.CompareAge(Editor.Version) != 0)
                            {
                                CompletionWindowManager.HideWindow();
                            }
                        }
                    }
                }
            }
            if (OnTheFlyFormatting && descriptor.SpecialKey == SpecialKey.Return)
            {
                try {
                    FormatOnReturn();
                } catch (Exception e) {
                    LoggingService.LogError("Exception while formatting", e);
                }
            }
        }
Пример #6
0
        /*		void TextCut (object sender, ReplaceEventArgs e)
         * {
         *      if (!string.IsNullOrEmpty (e.Value) || e.Count == 0)
         *              return;
         *      RunFormatterAt (e.Offset);
         * }*/

        void RunFormatterAt(int offset)
        {
            if (PropertyService.Get("OnTheFlyFormatting", false) && textEditorData != null && Document != null)
            {
                //	textEditorData.Document.TextReplaced -= TextCut;
                ProjectDom       dom      = Document.Dom;
                DocumentLocation loc      = textEditorData.Document.OffsetToLocation(offset);
                DomLocation      location = new DomLocation(loc.Line, loc.Column);
                //	CSharpFormatter.Format (textEditorData, dom, Document.CompilationUnit, location);
                OnTheFlyFormatter.Format(Document, dom, location);
                //	textEditorData.Document.TextReplaced += TextCut;
            }
        }
        void RunFormatter()
        {
            if (PropertyService.Get("OnTheFlyFormatting", false) && textEditorData != null && !(textEditorData.CurrentMode is TextLinkEditMode))
            {
                //		textEditorData.Document.TextReplaced -= TextCut;
                ProjectDom dom = ProjectDomService.GetProjectDom(Document.Project);
                if (dom == null)
                {
                    dom = ProjectDomService.GetFileDom(Document.FileName);
                }

                DomLocation location = new DomLocation(textEditorData.Caret.Location.Line + (lastCharInserted == '\n' ? -1 : 0), textEditorData.Caret.Location.Column);
                //				CSharpFormatter.Format (textEditorData, dom, Document.CompilationUnit, location);
                OnTheFlyFormatter.Format(Document, dom, location, lastCharInserted == '\n');

                //		textEditorData.Document.TextReplaced += TextCut;
            }
        }
Пример #8
0
        public override void PostFomatPastedText(int insertionOffset, int insertedChars)
        {
            if (indent.Editor.Options.IndentStyle == IndentStyle.None ||
                indent.Editor.Options.IndentStyle == IndentStyle.Auto)
            {
                return;
            }
            if (DefaultSourceEditorOptions.Instance.OnTheFlyFormatting)
            {
                OnTheFlyFormatter.Format(indent.Editor, indent.DocumentContext, insertionOffset, insertionOffset + insertedChars);
                return;
            }
            // Just correct the start line of the paste operation - the text is already indented.
            var curLine       = indent.Editor.GetLineByOffset(insertionOffset);
            var curLineOffset = curLine.Offset;

            indent.SafeUpdateIndentEngine(curLineOffset);
            if (!indent.stateTracker.IsInsideOrdinaryCommentOrString)
            {
                int    pos       = curLineOffset;
                string curIndent = curLine.GetIndentation(indent.Editor);
                int    nlwsp     = curIndent.Length;

                if (!indent.stateTracker.LineBeganInsideMultiLineComment || (nlwsp < curLine.LengthIncludingDelimiter && indent.Editor.GetCharAt(curLineOffset + nlwsp) == '*'))
                {
                    // Possibly replace the indent
                    indent.SafeUpdateIndentEngine(curLineOffset + curLine.Length);
                    string newIndent = indent.stateTracker.ThisLineIndent;
                    if (newIndent != curIndent)
                    {
                        if (CompletionWindowManager.IsVisible)
                        {
                            if (pos < CompletionWindowManager.CodeCompletionContext.TriggerOffset)
                            {
                                CompletionWindowManager.CodeCompletionContext.TriggerOffset -= nlwsp;
                            }
                        }
                        indent.Editor.ReplaceText(pos, nlwsp, newIndent);
                        //						textEditorData.Document.CommitLineUpdate (textEditorData.CaretLine);
                    }
                }
            }
            indent.Editor.FixVirtualIndentation();
        }
Пример #9
0
        async void FormatOnReturn(CancellationToken cancellationToken = default(CancellationToken))
        {
            var document = DocumentContext.AnalysisDocument;

            if (document == null)
            {
                return;
            }
            var caretPosition = Editor.CaretOffset;
            var token         = await CSharpEditorFormattingService.GetTokenBeforeTheCaretAsync(document, caretPosition, cancellationToken).ConfigureAwait(false);

            if (token.IsMissing)
            {
                return;
            }

            string text = null;

            if (service.IsInvalidToken(token, ref text))
            {
                return;
            }
            // Check to see if the token is ')' and also the parent is a using statement. If not, bail
            if (CSharpEditorFormattingService.TokenShouldNotFormatOnReturn(token))
            {
                return;
            }
            var tokenRange = Microsoft.CodeAnalysis.CSharp.Utilities.FormattingRangeHelper.FindAppropriateRange(token);

            if (tokenRange == null || !tokenRange.HasValue || tokenRange.Value.Item1.Equals(tokenRange.Value.Item2))
            {
                return;
            }
            var value = tokenRange.Value;

            using (var undo = Editor.OpenUndoGroup()) {
                OnTheFlyFormatter.Format(Editor, DocumentContext, value.Item1.SpanStart, value.Item2.Span.End, optionSet: optionSet);
            }
        }
		public override bool KeyPress (Gdk.Key key, char keyChar, Gdk.ModifierType modifier)
		{
			bool skipFormatting = StateTracker.IsInsideOrdinaryCommentOrString ||
			                      StateTracker.IsInsidePreprocessorDirective;

			cursorPositionBeforeKeyPress = textEditorData.Caret.Offset;
			bool isSomethingSelected = textEditorData.IsSomethingSelected;
			if (key == Gdk.Key.BackSpace && textEditorData.Caret.Offset == lastInsertedSemicolon) {
				textEditorData.Document.Undo ();
				lastInsertedSemicolon = -1;
				return false;
			}
			lastInsertedSemicolon = -1;
			if (keyChar == ';' && !(textEditorData.CurrentMode is TextLinkEditMode) && !DoInsertTemplate () && !isSomethingSelected && PropertyService.Get (
				    "SmartSemicolonPlacement",
				    false
			    )) {
				bool retval = base.KeyPress (key, keyChar, modifier);
				DocumentLine curLine = textEditorData.Document.GetLine (textEditorData.Caret.Line);
				string text = textEditorData.Document.GetTextAt (curLine);
				if (!(text.EndsWith (";", StringComparison.Ordinal) || text.Trim ().StartsWith ("for", StringComparison.Ordinal))) {
					int guessedOffset;

					if (GuessSemicolonInsertionOffset (textEditorData, curLine, textEditorData.Caret.Offset, out guessedOffset)) {
						using (var undo = textEditorData.OpenUndoGroup ()) {
							textEditorData.Remove (textEditorData.Caret.Offset - 1, 1);
							textEditorData.Caret.Offset = guessedOffset;
							lastInsertedSemicolon = textEditorData.Caret.Offset + 1;
							retval = base.KeyPress (key, keyChar, modifier);
						}
					}
				}
				using (var undo = textEditorData.OpenUndoGroup ()) {
					if (OnTheFlyFormatting && textEditorData != null && !(textEditorData.CurrentMode is TextLinkEditMode) && !(textEditorData.CurrentMode is InsertionCursorEditMode)) {
						OnTheFlyFormatter.FormatStatmentAt (Document, textEditorData.Caret.Location);
					}
				}
				return retval;
			}
			
			if (key == Gdk.Key.Tab) {
				SafeUpdateIndentEngine (textEditorData.Caret.Offset);
				if (stateTracker.IsInsideStringLiteral && !textEditorData.IsSomethingSelected) {
					var lexer = new CSharpCompletionEngineBase.MiniLexer (textEditorData.Document.GetTextAt (0, textEditorData.Caret.Offset));
					lexer.Parse ();
					if (lexer.IsInString) {
						textEditorData.InsertAtCaret ("\\t");
						return false;
					}
				}
			}


			if (key == Gdk.Key.Tab && DefaultSourceEditorOptions.Instance.TabIsReindent && !CompletionWindowManager.IsVisible && !(textEditorData.CurrentMode is TextLinkEditMode) && !DoInsertTemplate () && !isSomethingSelected) {
				ReindentOnTab ();

				return false;
			}

			SafeUpdateIndentEngine (textEditorData.Caret.Offset);
			if (!stateTracker.IsInsideOrdinaryCommentOrString) {
				if (keyChar == '@') {
					var retval = base.KeyPress (key, keyChar, modifier);
					int cursor = textEditorData.Caret.Offset;
					if (cursor < textEditorData.Length && textEditorData.GetCharAt (cursor) == '"')
						ConvertNormalToVerbatimString (textEditorData, cursor + 1);
					return retval;
				}
			}


			//do the smart indent
			if (textEditorData.Options.IndentStyle == IndentStyle.Smart || textEditorData.Options.IndentStyle == IndentStyle.Virtual) {
				bool retval;
				//capture some of the current state
				int oldBufLen = textEditorData.Length;
				int oldLine = textEditorData.Caret.Line + 1;
				bool reIndent = false;

				//pass through to the base class, which actually inserts the character
				//and calls HandleCodeCompletion etc to handles completion
				using (var undo = textEditorData.OpenUndoGroup ()) {
					DoPreInsertionSmartIndent (key);
				}
				wasInStringLiteral = stateTracker.IsInsideStringLiteral;
				bool automaticReindent;
				// need to be outside of an undo group - otherwise it interferes with other text editor extension
				// esp. the documentation insertion undo steps.
				retval = base.KeyPress (key, keyChar, modifier);
				//handle inserted characters
				if (textEditorData.Caret.Offset <= 0 || textEditorData.IsSomethingSelected)
					return retval;
				
				lastCharInserted = TranslateKeyCharForIndenter (key, keyChar, textEditorData.GetCharAt (textEditorData.Caret.Offset - 1));
				if (lastCharInserted == '\0')
					return retval;
				using (var undo = textEditorData.OpenUndoGroup ()) {
					SafeUpdateIndentEngine (textEditorData.Caret.Offset);

					if (key == Gdk.Key.Return && modifier == Gdk.ModifierType.ControlMask) {
						FixLineStart (textEditorData, stateTracker, textEditorData.Caret.Line + 1);
					} else {
						if (!(oldLine == textEditorData.Caret.Line + 1 && lastCharInserted == '\n') && (oldBufLen != textEditorData.Length || lastCharInserted != '\0')) {
							DoPostInsertionSmartIndent (lastCharInserted, out reIndent);
						} else {
							reIndent = lastCharInserted == '\n';
						}
					}
					//reindent the line after the insertion, if needed
					//N.B. if the engine says we need to reindent, make sure that it's because a char was 
					//inserted rather than just updating the stack due to moving around

					SafeUpdateIndentEngine (textEditorData.Caret.Offset);
					automaticReindent = (stateTracker.NeedsReindent && lastCharInserted != '\0');
					if (key == Gdk.Key.Return && (reIndent || automaticReindent)) {
						if (textEditorData.Options.IndentStyle == IndentStyle.Virtual) {
							if (textEditorData.GetLine (textEditorData.Caret.Line).Length == 0)
								textEditorData.Caret.Column = textEditorData.IndentationTracker.GetVirtualIndentationColumn (textEditorData.Caret.Location);
						} else {
							DoReSmartIndent ();
						}
					}
				}

				if (reIndent || key != Gdk.Key.Return && automaticReindent) {
					using (var undo = textEditorData.OpenUndoGroup ()) {
						DoReSmartIndent ();
					}
				}
				if (!skipFormatting) {
					if (keyChar == ';' || keyChar == '}') {
						using (var undo = textEditorData.OpenUndoGroup ()) {
							if (OnTheFlyFormatting && textEditorData != null && !(textEditorData.CurrentMode is TextLinkEditMode) && !(textEditorData.CurrentMode is InsertionCursorEditMode)) {
								OnTheFlyFormatter.FormatStatmentAt (Document, textEditorData.Caret.Location);
							}
						}
					}
				}

				SafeUpdateIndentEngine (textEditorData.Caret.Offset);
				lastCharInserted = '\0';
				CheckXmlCommentCloseTag (keyChar);
				return retval;
			}

			if (textEditorData.Options.IndentStyle == IndentStyle.Auto && DefaultSourceEditorOptions.Instance.TabIsReindent && key == Gdk.Key.Tab) {
				bool retval = base.KeyPress (key, keyChar, modifier);
				DoReSmartIndent ();
				CheckXmlCommentCloseTag (keyChar);
				return retval;
			}

			//pass through to the base class, which actually inserts the character
			//and calls HandleCodeCompletion etc to handles completion
			var result = base.KeyPress (key, keyChar, modifier);

			if (key == Gdk.Key.Return || key == Gdk.Key.KP_Enter) {
				DoReSmartIndent ();
			}

			CheckXmlCommentCloseTag (keyChar);

			if (!skipFormatting && keyChar == '}')
				RunFormatter (new DocumentLocation (textEditorData.Caret.Location.Line, textEditorData.Caret.Location.Column));
			return result;
		}
Пример #11
0
        public override bool KeyPress(KeyDescriptor descriptor)
        {
            completionWindowWasVisible   = CompletionWindowManager.IsVisible;
            cursorPositionBeforeKeyPress = Editor.CaretOffset;
            bool isSomethingSelected = Editor.IsSomethingSelected;

            if (descriptor.SpecialKey == SpecialKey.BackSpace && Editor.CaretOffset == lastInsertedSemicolon)
            {
                EditActions.Undo(Editor);
                lastInsertedSemicolon = -1;
                return(false);
            }

            lastInsertedSemicolon = -1;
            if (descriptor.KeyChar == ';' && Editor.EditMode == EditMode.Edit && !DoInsertTemplate() && !isSomethingSelected && PropertyService.Get(
                    "SmartSemicolonPlacement",
                    false
                    ) && !(stateTracker.IsInsideComment || stateTracker.IsInsideString))
            {
                bool   retval  = base.KeyPress(descriptor);
                var    curLine = Editor.GetLine(Editor.CaretLine);
                string text    = Editor.GetTextAt(curLine);
                if (!(text.EndsWith(";", StringComparison.Ordinal) || text.Trim().StartsWith("for", StringComparison.Ordinal)))
                {
                    int guessedOffset;

                    if (GuessSemicolonInsertionOffset(Editor, curLine, Editor.CaretOffset, out guessedOffset))
                    {
                        using (var undo = Editor.OpenUndoGroup()) {
                            Editor.RemoveText(Editor.CaretOffset - 1, 1);
                            Editor.CaretOffset    = guessedOffset;
                            lastInsertedSemicolon = Editor.CaretOffset + 1;
                            retval = base.KeyPress(descriptor);
                        }
                    }
                }
                using (var undo = Editor.OpenUndoGroup()) {
                    if (OnTheFlyFormatting && Editor != null && Editor.EditMode == EditMode.Edit)
                    {
                        OnTheFlyFormatter.FormatStatmentAt(Editor, DocumentContext, Editor.CaretLocation, optionSet: optionSet);
                    }
                }
                return(retval);
            }

            if (descriptor.SpecialKey == SpecialKey.Tab && descriptor.ModifierKeys == ModifierKeys.None && !CompletionWindowManager.IsVisible)
            {
                SafeUpdateIndentEngine(Editor.CaretOffset);
                if (stateTracker.IsInsideStringLiteral && !Editor.IsSomethingSelected)
                {
                    var lexer = new ICSharpCode.NRefactory.CSharp.Completion.CSharpCompletionEngineBase.MiniLexer(Editor.GetTextAt(0, Editor.CaretOffset));
                    lexer.Parse();
                    if (lexer.IsInString)
                    {
                        Editor.InsertAtCaret("\\t");
                        return(false);
                    }
                }
            }


            if (descriptor.SpecialKey == SpecialKey.Tab && DefaultSourceEditorOptions.Instance.TabIsReindent && !CompletionWindowManager.IsVisible && Editor.EditMode == EditMode.Edit && !DoInsertTemplate() && !isSomethingSelected)
            {
                ReindentOnTab();

                return(false);
            }

            SafeUpdateIndentEngine(Editor.CaretOffset);
            if (!stateTracker.IsInsideOrdinaryCommentOrString)
            {
                if (descriptor.KeyChar == '@')
                {
                    var retval = base.KeyPress(descriptor);
                    int cursor = Editor.CaretOffset;
                    if (cursor < Editor.Length && Editor.GetCharAt(cursor) == '"')
                    {
                        ConvertNormalToVerbatimString(Editor, cursor + 1);
                    }
                    return(retval);
                }
            }


            //do the smart indent
            if (!indentationDisabled)
            {
                bool retval;
                //capture some of the current state
                int  oldBufLen = Editor.Length;
                int  oldLine   = Editor.CaretLine + 1;
                bool reIndent  = false;

                //pass through to the base class, which actually inserts the character
                //and calls HandleCodeCompletion etc to handles completion
                using (var undo = Editor.OpenUndoGroup()) {
                    DoPreInsertionSmartIndent(descriptor.SpecialKey);
                }
                wasInStringLiteral = stateTracker.IsInsideStringLiteral;


                bool returnBetweenBraces =
                    descriptor.SpecialKey == SpecialKey.Return &&
                    descriptor.ModifierKeys == ModifierKeys.None &&
                    Editor.CaretOffset > 0 && Editor.CaretOffset < Editor.Length &&
                    Editor.GetCharAt(Editor.CaretOffset - 1) == '{' && Editor.GetCharAt(Editor.CaretOffset) == '}' && !stateTracker.IsInsideOrdinaryCommentOrString;

                bool automaticReindent;
                // need to be outside of an undo group - otherwise it interferes with other text editor extension
                // esp. the documentation insertion undo steps.
                retval = base.KeyPress(descriptor);


                if (descriptor.KeyChar == '/' && stateTracker.IsInsideMultiLineComment)
                {
                    if (Editor.CaretOffset - 3 >= 0 && Editor.GetCharAt(Editor.CaretOffset - 3) == '*' && Editor.GetCharAt(Editor.CaretOffset - 2) == ' ')
                    {
                        using (var undo = Editor.OpenUndoGroup()) {
                            Editor.RemoveText(Editor.CaretOffset - 2, 1);
                        }
                    }
                }

                //handle inserted characters
                if (Editor.CaretOffset <= 0 || Editor.IsSomethingSelected)
                {
                    return(retval);
                }

                lastCharInserted = TranslateKeyCharForIndenter(descriptor.SpecialKey, descriptor.KeyChar, Editor.GetCharAt(Editor.CaretOffset - 1));
                if (lastCharInserted == '\0')
                {
                    return(retval);
                }
                using (var undo = Editor.OpenUndoGroup()) {
                    if (returnBetweenBraces)
                    {
                        var oldOffset = Editor.CaretOffset;
                        Editor.InsertAtCaret(Editor.EolMarker);
                        DoReSmartIndent();
                        Editor.CaretOffset = oldOffset;
                    }

                    SafeUpdateIndentEngine(Editor.CaretOffset);

                    if (descriptor.SpecialKey == SpecialKey.Return && descriptor.ModifierKeys == ModifierKeys.Control)
                    {
                        FixLineStart(Editor, stateTracker, Editor.CaretLine + 1);
                    }
                    else
                    {
                        if (!(oldLine == Editor.CaretLine + 1 && lastCharInserted == '\n') && (oldBufLen != Editor.Length || lastCharInserted != '\0'))
                        {
                            DoPostInsertionSmartIndent(lastCharInserted, out reIndent);
                        }
                        else
                        {
                            reIndent = lastCharInserted == '\n';
                        }
                    }
                    //reindent the line after the insertion, if needed
                    //N.B. if the engine says we need to reindent, make sure that it's because a char was
                    //inserted rather than just updating the stack due to moving around

                    SafeUpdateIndentEngine(Editor.CaretOffset);
                    // Automatically reindent in text link mode will cause the mode exiting, therefore we need to prevent that.
                    automaticReindent = (stateTracker.NeedsReindent && lastCharInserted != '\0') && Editor.EditMode == EditMode.Edit;
                    if (descriptor.SpecialKey == SpecialKey.Return && (reIndent || automaticReindent))
                    {
                        if (Editor.Options.IndentStyle == IndentStyle.Virtual)
                        {
                            if (Editor.GetLine(Editor.CaretLine).Length == 0)
                            {
                                Editor.CaretColumn = Editor.GetVirtualIndentationColumn(Editor.CaretLine);
                            }
                        }
                        else
                        {
                            DoReSmartIndent();
                        }
                    }
                }

                const string reindentChars = ";){}";
                if (reIndent || descriptor.SpecialKey != SpecialKey.Return && descriptor.SpecialKey != SpecialKey.Tab && automaticReindent && reindentChars.Contains(descriptor.KeyChar))
                {
                    using (var undo = Editor.OpenUndoGroup()) {
                        DoReSmartIndent();
                    }
                }

                HandleOnTheFlyFormatting(descriptor);
                SafeUpdateIndentEngine(Editor.CaretOffset);
                lastCharInserted = '\0';
                CheckXmlCommentCloseTag(descriptor.KeyChar);
                return(retval);
            }

            if (Editor.Options.IndentStyle == IndentStyle.Auto && DefaultSourceEditorOptions.Instance.TabIsReindent && descriptor.SpecialKey == SpecialKey.Tab)
            {
                bool retval = base.KeyPress(descriptor);
                DoReSmartIndent();
                CheckXmlCommentCloseTag(descriptor.KeyChar);
                return(retval);
            }

            //pass through to the base class, which actually inserts the character
            //and calls HandleCodeCompletion etc to handles completion
            var result = base.KeyPress(descriptor);

            if (!indentationDisabled && (descriptor.SpecialKey == SpecialKey.Return))
            {
                DoReSmartIndent();
            }

            CheckXmlCommentCloseTag(descriptor.KeyChar);

            HandleOnTheFlyFormatting(descriptor);

            return(result);
        }
Пример #12
0
 protected override void OnTheFlyFormatImplementation(TextEditor editor, DocumentContext context, int startOffset, int length)
 {
     OnTheFlyFormatter.Format(editor, context, startOffset, startOffset + length);
 }
Пример #13
0
 public override void OnTheFlyFormat(MonoDevelop.Ide.Gui.Document doc, int startOffset, int endOffset)
 {
     OnTheFlyFormatter.Format(doc, startOffset, endOffset);
 }