/// <summary> /// Get the first keyword in Line. The keyword is in UPPERCASE The modifiers (Private, Protected, ... ) are ignored /// If the first Keyword is a Comment, "//" is returned /// </summary> /// <param name="line">The line to analyze</param> /// <param name="doSkipped">Bool value indicating if a "DO" keyword has been skipped</param> /// <param name="minIndent"></param> /// <returns></returns> private String getFirstKeywordInLine(ITextSnapshotLine line, out bool doSkipped, out int minIndent) { minIndent = -1; doSkipped = false; string startOfLine = line.GetText(); string keyword = ""; int index = 0; var tokens = getTokens(startOfLine); if (tokens.Count > 0) { if (tokens[0].Type == XSharpLexer.WS) { index = 1; minIndent = getIndentTokenLength(tokens[0]); } else { minIndent = 0; } while (tokens.Count > index) { var token = tokens[index]; if (token.Type == XSharpLexer.WS) { index++; continue; } if (XSharpLexer.IsKeyword(token.Type)) { keyword = token.Text.ToUpper(); // it could be modifier... if (keywordIsModifier(token.Type)) { index++; keyword = ""; continue; } if (token.Type == XSharpLexer.DO) { index++; keyword = ""; doSkipped = true; continue; } } else if (XSharpLexer.IsComment(token.Type)) { keyword = token.Text.Substring(0, 2); } break; } } return(keyword); }
private ClassificationSpan ClassifyToken(IToken token, IList <ClassificationSpan> regionTags, ITextSnapshot snapshot) { var tokenType = token.Type; ClassificationSpan result = null; switch (token.Channel) { case XSharpLexer.PRAGMACHANNEL: // #pragma case XSharpLexer.PREPROCESSORCHANNEL: // #define, #ifdef etc result = Token2ClassificationSpan(token, snapshot, xsharpPPType); switch (token.Type) { case XSharpLexer.PP_REGION: case XSharpLexer.PP_IFDEF: case XSharpLexer.PP_IFNDEF: regionTags.Add(Token2ClassificationSpan(token, snapshot, xsharpRegionStart)); break; case XSharpLexer.PP_ENDREGION: case XSharpLexer.PP_ENDIF: regionTags.Add(Token2ClassificationSpan(token, snapshot, xsharpRegionStop)); break; default: break; } break; case XSharpLexer.DEFOUTCHANNEL: // code in an inactive #ifdef result = Token2ClassificationSpan(token, snapshot, xsharpInactiveType); break; case XSharpLexer.XMLDOCCHANNEL: case XSharpLexer.Hidden: if (XSharpLexer.IsComment(token.Type)) { result = Token2ClassificationSpan(token, snapshot, xsharpCommentType); if (token.Type == XSharpLexer.ML_COMMENT && token.Text.IndexOf("\r") >= 0) { regionTags.Add(Token2ClassificationSpan(token, snapshot, xsharpRegionStart)); regionTags.Add(Token2ClassificationSpan(token, snapshot, xsharpRegionStop)); } } break; default: // Normal channel IClassificationType type = null; if (XSharpLexer.IsIdentifier(tokenType)) { type = xsharpIdentifierType; } else if (XSharpLexer.IsConstant(tokenType)) { switch (tokenType) { case XSharpLexer.STRING_CONST: case XSharpLexer.CHAR_CONST: case XSharpLexer.ESCAPED_STRING_CONST: case XSharpLexer.INTERPOLATED_STRING_CONST: type = xsharpStringType; break; case XSharpLexer.FALSE_CONST: case XSharpLexer.TRUE_CONST: type = xsharpKeywordType; break; case XSharpLexer.VO_AND: case XSharpLexer.VO_NOT: case XSharpLexer.VO_OR: case XSharpLexer.VO_XOR: case XSharpLexer.SYMBOL_CONST: case XSharpLexer.NIL: type = xsharpLiteralType; break; default: if ((tokenType >= XSharpLexer.FIRST_NULL) && (tokenType <= XSharpLexer.LAST_NULL)) { type = xsharpKeywordType; break; } else { type = xsharpNumberType; } break; } } else if (XSharpLexer.IsKeyword(tokenType)) { type = xsharpKeywordType; } else if (XSharpLexer.IsOperator(tokenType)) { switch (tokenType) { case XSharpLexer.LPAREN: case XSharpLexer.LCURLY: case XSharpLexer.LBRKT: type = xsharpBraceOpenType; break; case XSharpLexer.RPAREN: case XSharpLexer.RCURLY: case XSharpLexer.RBRKT: type = xsharpBraceCloseType; break; default: type = xsharpOperatorType; break; } } if (type != null) { result = Token2ClassificationSpan(token, snapshot, type); } break; } return(result); }
private String getFirstKeywordInLine(ITextSnapshotLine line, int start, int length) { String keyword = ""; var tokens = getTokensInLine(line.Snapshot, start, length); bool inAttribute = false; // if (tokens.Count > 0) { int index = 0; while (index < tokens.Count) { var token = tokens[index]; // skip whitespace tokens if (token.Type == XSharpLexer.WS) { index++; continue; } keyword = ""; if (XSharpLexer.IsKeyword(token.Type) || (token.Type >= XSharpLexer.PP_FIRST && token.Type <= XSharpLexer.PP_LAST)) { keyword = token.Text.ToUpper(); // it could be modifier... if (keywordIsModifier(token.Type)) { index++; continue; } else { // keyword found break; } } else if (XSharpLexer.IsComment(token.Type)) { keyword = token.Text; if (keyword.Length >= 2) { keyword = keyword.Substring(0, 2); } break; } else if (XSharpLexer.IsOperator(token.Type)) { keyword = token.Text; if (token.Type == XSharpLexer.LBRKT) { inAttribute = true; index++; continue; } else if (token.Type == XSharpLexer.RBRKT) { inAttribute = false; index++; continue; } } else { if (inAttribute) { // Skip All Content in index++; continue; } } break; } } return(keyword); }
/// <summary> /// Parse the current Snapshot, and build the Tag List /// </summary> private void Colorize() { var snapshot = this.Buffer.CurrentSnapshot; Snapshot = snapshot; ITokenStream TokenStream = null; // parse for positional keywords that change the colors // and get a reference to the tokenstream string path = String.Empty; if (txtdocfactory != null) { ITextDocument doc = null; if (txtdocfactory.TryGetTextDocument(this.Buffer, out doc)) { path = doc.FilePath; } } // Parse the source and get the (Lexer) Tokenstream to locate comments, keywords and other tokens. // The parser will identify (positional) keywords that are used as identifier xsTagger.Parse(snapshot, out TokenStream, path); if (TokenStream != null) { tags.Clear(); for (var iToken = 0; iToken < TokenStream.Size; iToken++) { var token = TokenStream.Get(iToken); var tokenType = token.Type; TextSpan tokenSpan = new TextSpan(token.StartIndex, token.StopIndex - token.StartIndex + 1); if (XSharpLexer.IsKeyword(tokenType)) { tags.Add(tokenSpan.ToTagSpan(snapshot, xsharpKeywordType)); } else if (XSharpLexer.IsConstant(tokenType)) { tags.Add(tokenSpan.ToTagSpan(snapshot, xsharpConstantType)); } else if (XSharpLexer.IsOperator(tokenType)) { switch (tokenType) { case LanguageService.CodeAnalysis.XSharp.SyntaxParser.XSharpLexer.LPAREN: case LanguageService.CodeAnalysis.XSharp.SyntaxParser.XSharpLexer.LCURLY: case LanguageService.CodeAnalysis.XSharp.SyntaxParser.XSharpLexer.LBRKT: tags.Add(tokenSpan.ToTagSpan(snapshot, xsharpBraceOpenType)); break; case LanguageService.CodeAnalysis.XSharp.SyntaxParser.XSharpLexer.RPAREN: case LanguageService.CodeAnalysis.XSharp.SyntaxParser.XSharpLexer.RCURLY: case LanguageService.CodeAnalysis.XSharp.SyntaxParser.XSharpLexer.RBRKT: tags.Add(tokenSpan.ToTagSpan(snapshot, xsharpBraceCloseType)); break; default: tags.Add(tokenSpan.ToTagSpan(snapshot, xsharpOperatorType)); break; } } else if (XSharpLexer.IsIdentifier(tokenType)) { tags.Add(tokenSpan.ToTagSpan(snapshot, xsharpIdentifierType)); } else if (XSharpLexer.IsComment(tokenType)) { tags.Add(tokenSpan.ToTagSpan(snapshot, xsharpCommentType)); } } foreach (var tag in xsTagger.Tags) { tags.Add(tag); } if (TagsChanged != null) { TagsChanged(this, new SnapshotSpanEventArgs(new SnapshotSpan(Buffer.CurrentSnapshot, 0, this.Buffer.CurrentSnapshot.Length))); } } }