Hi,
Based on provided sample here on multi line string I've tried to adapt this code to use multi line commenting using /* and ending with */ literal combination. My written code seems to work correct when string is pre-loaded. However, typing manually in the SyntaxEditor view first character '/' is accepted but a star '*' is failing with exception:
System.IndexOutOfRangeException: Index was outside the bounds of the array. at System.Text.StringBuilder.get_Chars(Int32 index) at Infragistics.Documents.Lexing.StringTable.GetHashCode(StringBuilder contentBuffer, Int32 startIndex, Int32 length) at Infragistics.Documents.Lexing.StringTable.GetString(StringBuilder contentBuffer, Int32 startIndex, Int32 length) at Infragistics.Documents.Lexing.LexingContext.AddMatchToNextLine(StringBuilder contentBufferResolved, LexingMatchComplete match, Int32 startIndex, Boolean shouldClearTouchedLineInformation) at Infragistics.Documents.Lexing.LexingContext.GetNextMatch(Int32& startPosition) at Infragistics.Documents.Lexing.LexingContext.Tokenize() at Infragistics.Documents.Parsing.TokenLineBufferInternal.ReplaceTextCore(Int32& offset, Int32& length, String& newText, Boolean shouldAutoCase) at Infragistics.Documents.Parsing.TokenLineBufferInternal.ReplaceText(Int32& offset, Int32& length, String& newText, Boolean shouldAutoCase) at Infragistics.Documents.TextDocument.ReplaceHelper(Int32 offset, Int32 length, String newText, TextChangeSource source) at Infragistics.Documents.TextDocument.Insert(Int32 offset, String text, TextChangeSource source, Boolean isAutoIndent) at Infragistics.Controls.Editors.SyntaxEditorUtilities.InsertTextHelper(EditorDocumentView documentView, TextDocument document, SnapshotPoint caretSnapshotPoint, String text, Int32 offset) at Infragistics.Controls.Editors.ViewKeyboardHandler.ProcessText(String text) at Infragistics.Controls.Editors.ViewKeyboardHandler.OnTextInput(String text) at Infragistics.Controls.Editors.ViewKeyboardHandler.OnTextInput(TextCompositionEventArgs& e) at Infragistics.Controls.Editors.Primitives.EditorDocumentViewPresenter.OnTextInput(TextCompositionEventArgs e) at System.Windows.UIElement.OnTextInputThunk(Object sender, TextCompositionEventArgs e)
The code handling this:
private static void AddCommentMultiLine(LexerState state) { var lexerStates = state.Grammar.LexerStates; var comment = state.Symbols.Add("COMMENT_START", "/*"); comment.LanguageElement = LanguageElement.Comment; var commentLexerState = lexerStates.Add("Comment"); commentLexerState.Symbols.Add("COMMENT_TEXT", @"([^\/\*])+", TerminalSymbolComparison.RegularExpression).LanguageElement = LanguageElement.Comment; commentLexerState.Symbols.Add("COMMENT_END", "*/", TerminalSymbolComparison.Literal, true) .LanguageElement = LanguageElement.Comment; comment.LexerStateToEnter = commentLexerState; comment.LanguageElement = LanguageElement.Comment; }
Placing same characters in reverse order is working but this is not acceptable.
Update,
Fixed the exception but now I face manor problem to determine the end of the comment when multiple comments in same text.
Code:
private static void AddCommentMultiLine(LexerState state) { var defaultLexerState = state.Grammar.LexerStates.DefaultLexerState; var verbatimStringStart = defaultLexerState.Symbols.Add("VerbatimStringStart", "/*"); var verbatimStringLexerState = state.Grammar.LexerStates.Add("VerbatimString"); verbatimStringStart.LexerStateToEnter = verbatimStringLexerState; var verbatimStringContent = verbatimStringLexerState.Symbols.Add( "VerbatimStringContent", @"([^\*/]|\*|/)+", TerminalSymbolComparison.RegularExpression); var verbatimStringEnd = verbatimStringLexerState.Symbols.Add( "VerbatimStringEnd", "*/", isExitSymbol: true); verbatimStringStart.LanguageElement = LanguageElement.Comment; verbatimStringContent.LanguageElement = LanguageElement.Comment; verbatimStringContent.LookaheadPattern = @"\*/"; //verbatimStringContent.IsLookaheadNegative = true; verbatimStringEnd.LanguageElement = LanguageElement.Comment; }
But this code does not highlighting incorrectly the code and picks middle text too.
Test /* Correct */ Incorrectly picked /* Correct */ Correcty working again
Hello Tomas,
Thank you for your post. I am glad you were able to prevent the IndexOutOfRangeException that you were seeing.
My teammates and I have been investigating the behavior you are reporting, and I am not entirely sure why the highlighting is not working correctly, but I believe it may be due to the Regex statement in your “verbatimStringContent” variable. This may need to be modified to be more specific to what the content of your multi-line comments allow.
It is also interesting that you are trying to change the Grammar in code, as I feel this really should be something that is done within the EBNF file. We also recently had another forum thread together, here, where you were creating a custom language in this case. This is not something that we can generally provide support for, as it can tend to be more complex and out of the scope of what developer support provides, but perhaps the custom language that you are creating is conflicting with your programmatic Grammar modification in this case?
Please let me know if you have any other questions or concerns on this matter.
Hi Andrew,
I was able to fix the problem with highlighting after correctly the Regex and adding new line and space symbols as part of content. The problem solved.
Final code:
var defaultLexerState = state.Grammar.LexerStates.DefaultLexerState; var verbatimStringStart = defaultLexerState.Symbols.Add("VerbatimStringStart", "/*"); var verbatimStringLexerState = state.Grammar.LexerStates.Add("VerbatimString"); verbatimStringStart.LexerStateToEnter = verbatimStringLexerState; var verbatimStringContent = verbatimStringLexerState.Symbols.Add( "VerbatimStringContent", @"([^\*]|\*[^|/])+", TerminalSymbolComparison.RegularExpression); verbatimStringLexerState.Symbols.Add(state.Grammar.NewLineSymbol); verbatimStringLexerState.Symbols.Add(state.Grammar.WhitespaceSymbol); var verbatimStringEnd = verbatimStringLexerState.Symbols.Add( "VerbatimStringEnd", "*/", isExitSymbol: true); verbatimStringStart.LanguageElement = LanguageElement.Comment; verbatimStringContent.LanguageElement = LanguageElement.Comment; verbatimStringContent.LookaheadPattern = @"\*/"; verbatimStringEnd.LanguageElement = LanguageElement.Comment;