Example #1
0
 public ColoredSegment(ISegment segment, ScopeStack scopeStack) : base(segment)
 {
     this.scopeStack = scopeStack;
 }
Example #2
0
            public Task <HighlightedLine> GetColoredSegments(ITextSource text, int startOffset, int length)
            {
                if (ContextStack.IsEmpty)
                {
                    return(Task.FromResult(new HighlightedLine(new TextSegment(startOffset, length), new [] { new ColoredSegment(0, length, ScopeStack.Empty) })));
                }
                SyntaxContext        currentContext = null;
                List <SyntaxContext> lastContexts   = new List <SyntaxContext> ();
                Match       match              = null;
                SyntaxMatch curMatch           = null;
                var         segments           = new List <ColoredSegment> ();
                int         offset             = 0;
                int         curSegmentOffset   = 0;
                int         endOffset          = offset + length;
                int         lastMatch          = -1;
                var         highlightedSegment = new TextSegment(startOffset, length);
                string      lineText           = text.GetTextAt(startOffset, length);
                var         initialState       = state.Clone();
                int         timeoutOccursAt;

                unchecked {
                    timeoutOccursAt = Environment.TickCount + (int)matchTimeout.TotalMilliseconds;
                }
restart:
                if (lastMatch == offset)
                {
                    if (lastContexts.Contains(currentContext))
                    {
                        offset++;
                        length--;
                    }
                    else
                    {
                        lastContexts.Add(currentContext);
                    }
                }
                else
                {
                    lastContexts.Clear();
                    lastContexts.Add(currentContext);
                }
                if (length <= 0)
                {
                    goto end;
                }
                lastMatch      = offset;
                currentContext = ContextStack.Peek();
                match          = null;
                curMatch       = null;
                foreach (var m in currentContext.Matches)
                {
                    if (m.GotTimeout)
                    {
                        continue;
                    }
                    var r = m.GetRegex();
                    if (r == null)
                    {
                        continue;
                    }
                    try {
                        var possibleMatch = r.Match(lineText, offset, length, matchTimeout);
                        if (possibleMatch.Success)
                        {
                            if (match == null || possibleMatch.Index < match.Index)
                            {
                                match    = possibleMatch;
                                curMatch = m;
                                // Console.WriteLine (match.Index + " possible match : " + m + "/" + possibleMatch.Index + "-" + possibleMatch.Length);
                            }
                            else
                            {
                                // Console.WriteLine (match.Index + " skip match : " + m + "/" + possibleMatch.Index + "-" + possibleMatch.Length);
                            }
                        }
                        else
                        {
                            // Console.WriteLine ("fail match : " + m);
                        }
                    } catch (RegexMatchTimeoutException) {
                        LoggingService.LogWarning("Warning: Regex " + m.Match + " timed out on line:" + text.GetTextAt(offset, length));
                        m.GotTimeout = true;
                        continue;
                    }
                }
                if (Environment.TickCount >= timeoutOccursAt)
                {
                    curMatch.GotTimeout = true;
                    goto end;
                }

                if (match != null)
                {
                    // Console.WriteLine (match.Index + " taken match : " + curMatch + "/" + match.Index + "-" + match.Length);
                    var matchEndOffset = match.Index + match.Length;
                    if (curSegmentOffset < match.Index && match.Length > 0)
                    {
                        segments.Add(new ColoredSegment(curSegmentOffset, match.Index - curSegmentOffset, ScopeStack));
                        curSegmentOffset = match.Index;
                    }
                    if (curMatch.Pop)
                    {
                        PopMetaContentScopeStack(currentContext, curMatch);
                    }

                    PushScopeStack(curMatch.Scope);

                    if (curMatch.Captures.Groups.Count > 0)
                    {
                        for (int i = 0; i < curMatch.Captures.Groups.Count; ++i)
                        {
                            var capture = curMatch.Captures.Groups[i];
                            var grp     = match.Groups [capture.Item1];
                            if (grp == null || grp.Length == 0)
                            {
                                continue;
                            }
                            if (curSegmentOffset < grp.Index)
                            {
                                ReplaceSegment(segments, new ColoredSegment(curSegmentOffset, grp.Index - curSegmentOffset, ScopeStack));
                            }
                            ReplaceSegment(segments, new ColoredSegment(grp.Index, grp.Length, ScopeStack.Push(capture.Item2)));
                            curSegmentOffset = Math.Max(curSegmentOffset, grp.Index + grp.Length);
                        }
                    }

                    if (curMatch.Captures.NamedGroups.Count > 0)
                    {
                        for (int i = 0; i < curMatch.Captures.NamedGroups.Count; ++i)
                        {
                            var capture = curMatch.Captures.NamedGroups[i];
                            var grp     = match.Groups [capture.Item1];
                            if (grp == null || grp.Length == 0)
                            {
                                continue;
                            }
                            if (curSegmentOffset < grp.Index)
                            {
                                ReplaceSegment(segments, new ColoredSegment(curSegmentOffset, grp.Index - curSegmentOffset, ScopeStack));
                            }
                            ReplaceSegment(segments, new ColoredSegment(grp.Index, grp.Length, ScopeStack.Push(capture.Item2)));
                            curSegmentOffset = grp.Index + grp.Length;
                        }
                    }

                    if (curMatch.Scope.Count > 0 && curSegmentOffset < matchEndOffset && match.Length > 0)
                    {
                        segments.Add(new ColoredSegment(curSegmentOffset, matchEndOffset - curSegmentOffset, ScopeStack));
                        curSegmentOffset = matchEndOffset;
                    }

                    if (curMatch.Pop)
                    {
                        if (matchEndOffset - curSegmentOffset > 0)
                        {
                            segments.Add(new ColoredSegment(curSegmentOffset, matchEndOffset - curSegmentOffset, ScopeStack));
                        }
                        //if (curMatch.Scope != null)
                        //	scopeStack = scopeStack.Pop ();
                        PopStack(currentContext, curMatch);
                        curSegmentOffset = matchEndOffset;
                    }
                    else if (curMatch.Set != null)
                    {
                        // if (matchEndOffset - curSegmentOffset > 0)
                        //	segments.Add (new ColoredSegment (curSegmentOffset, matchEndOffset - curSegmentOffset, ScopeStack));
                        //if (curMatch.Scope != null)
                        //	scopeStack = scopeStack.Pop ();
                        PopMetaContentScopeStack(currentContext, curMatch);
                        PopStack(currentContext, curMatch);
                        //curSegmentOffset = matchEndOffset;
                        var nextContexts = curMatch.Set.GetContexts(currentContext);
                        PushStack(curMatch, nextContexts);
                        goto skip;
                    }
                    else if (curMatch.Push != null)
                    {
                        var nextContexts = curMatch.Push.GetContexts(currentContext);
                        PushStack(curMatch, nextContexts);
                    }
                    else
                    {
                        if (curMatch.Scope.Count > 0)
                        {
                            for (int i = 0; i < curMatch.Scope.Count; i++)
                            {
                                ScopeStack = ScopeStack.Pop();
                            }
                        }
                    }

                    if (curSegmentOffset < matchEndOffset && match.Length > 0)
                    {
                        segments.Add(new ColoredSegment(curSegmentOffset, matchEndOffset - curSegmentOffset, ScopeStack));
                        curSegmentOffset = matchEndOffset;
                    }
skip:
                    length -= curSegmentOffset - offset;
                    offset  = curSegmentOffset;
                    goto restart;
                }

end:
                if (endOffset - curSegmentOffset > 0)
                {
                    segments.Add(new ColoredSegment(curSegmentOffset, endOffset - curSegmentOffset, ScopeStack));
                }

                return(Task.FromResult(new HighlightedLine(highlightedSegment, segments)
                {
                    IsContinuedBeyondLineEnd = !initialState.Equals(state)
                }));
            }
        public RoslynClassificationHighlighting(MonoDevelopWorkspace workspace, DocumentId documentId, string defaultScope)
        {
            this.workspace    = workspace;
            this.documentId   = documentId;
            this.defaultScope = new ScopeStack(defaultScope);
            this.userScope    = this.defaultScope.Push(EditorThemeColors.UserTypes);

            classificationMap = new Dictionary <string, ScopeStack> {
                [ClassificationTypeNames.Comment]             = MakeScope("comment." + defaultScope),
                [ClassificationTypeNames.ExcludedCode]        = MakeScope("comment.excluded." + defaultScope),
                [ClassificationTypeNames.Identifier]          = MakeScope(defaultScope),
                [ClassificationTypeNames.Keyword]             = MakeScope("keyword." + defaultScope),
                [ClassificationTypeNames.NumericLiteral]      = MakeScope("constant.numeric." + defaultScope),
                [ClassificationTypeNames.Operator]            = MakeScope(defaultScope),
                [ClassificationTypeNames.PreprocessorKeyword] = MakeScope("meta.preprocessor." + defaultScope),
                [ClassificationTypeNames.StringLiteral]       = MakeScope("string." + defaultScope),
                [ClassificationTypeNames.WhiteSpace]          = MakeScope("text." + defaultScope),
                [ClassificationTypeNames.Text] = MakeScope("text." + defaultScope),

                [ClassificationTypeNames.PreprocessorText]      = MakeScope("meta.preprocessor.region.name." + defaultScope),
                [ClassificationTypeNames.Punctuation]           = MakeScope("punctuation." + defaultScope),
                [ClassificationTypeNames.VerbatimStringLiteral] = MakeScope("string.verbatim." + defaultScope),

                [ClassificationTypeNames.ClassName]         = MakeScope("entity.name.class." + defaultScope),
                [ClassificationTypeNames.DelegateName]      = MakeScope("entity.name.delegate." + defaultScope),
                [ClassificationTypeNames.EnumName]          = MakeScope("entity.name.enum." + defaultScope),
                [ClassificationTypeNames.InterfaceName]     = MakeScope("entity.name.interface." + defaultScope),
                [ClassificationTypeNames.ModuleName]        = MakeScope("entity.name.module." + defaultScope),
                [ClassificationTypeNames.StructName]        = MakeScope("entity.name.struct." + defaultScope),
                [ClassificationTypeNames.TypeParameterName] = MakeScope("entity.name.typeparameter." + defaultScope),

                [ClassificationTypeNames.FieldName]           = MakeScope("entity.name.field." + defaultScope),
                [ClassificationTypeNames.EnumMemberName]      = MakeScope("entity.name.enummember." + defaultScope),
                [ClassificationTypeNames.ConstantName]        = MakeScope("entity.name.constant." + defaultScope),
                [ClassificationTypeNames.LocalName]           = MakeScope("entity.name.local." + defaultScope),
                [ClassificationTypeNames.ParameterName]       = MakeScope("entity.name.parameter." + defaultScope),
                [ClassificationTypeNames.ExtensionMethodName] = MakeScope("entity.name.extensionmethod." + defaultScope),
                [ClassificationTypeNames.MethodName]          = MakeScope("entity.name.function." + defaultScope),
                [ClassificationTypeNames.PropertyName]        = MakeScope("entity.name.property." + defaultScope),
                [ClassificationTypeNames.EventName]           = MakeScope("entity.name.event." + defaultScope),

                [ClassificationTypeNames.XmlDocCommentAttributeName]         = MakeScope("comment.line.documentation." + defaultScope),
                [ClassificationTypeNames.XmlDocCommentAttributeQuotes]       = MakeScope("comment.line.documentation." + defaultScope),
                [ClassificationTypeNames.XmlDocCommentAttributeValue]        = MakeScope("comment.line.documentation." + defaultScope),
                [ClassificationTypeNames.XmlDocCommentCDataSection]          = MakeScope("comment.line.documentation." + defaultScope),
                [ClassificationTypeNames.XmlDocCommentComment]               = MakeScope("comment.line.documentation." + defaultScope),
                [ClassificationTypeNames.XmlDocCommentDelimiter]             = MakeScope("comment.line.documentation." + defaultScope),
                [ClassificationTypeNames.XmlDocCommentEntityReference]       = MakeScope("comment.line.documentation." + defaultScope),
                [ClassificationTypeNames.XmlDocCommentName]                  = MakeScope("comment.line.documentation." + defaultScope),
                [ClassificationTypeNames.XmlDocCommentProcessingInstruction] = MakeScope("comment.line.documentation." + defaultScope),
                [ClassificationTypeNames.XmlDocCommentText]                  = MakeScope("comment.line.documentation." + defaultScope),

                [ClassificationTypeNames.XmlLiteralAttributeName]      = MakeScope("entity.other.attribute-name." + defaultScope),
                [ClassificationTypeNames.XmlLiteralAttributeQuotes]    = MakeScope("punctuation.definition.string." + defaultScope),
                [ClassificationTypeNames.XmlLiteralAttributeValue]     = MakeScope("string.quoted." + defaultScope),
                [ClassificationTypeNames.XmlLiteralCDataSection]       = MakeScope("text." + defaultScope),
                [ClassificationTypeNames.XmlLiteralComment]            = MakeScope("comment.block." + defaultScope),
                [ClassificationTypeNames.XmlLiteralDelimiter]          = MakeScope(defaultScope),
                [ClassificationTypeNames.XmlLiteralEmbeddedExpression] = MakeScope(defaultScope),
                [ClassificationTypeNames.XmlLiteralEntityReference]    = MakeScope(defaultScope),
                [ClassificationTypeNames.XmlLiteralName] = MakeScope("entity.name.tag.localname." + defaultScope),
                [ClassificationTypeNames.XmlLiteralProcessingInstruction] = MakeScope(defaultScope),
                [ClassificationTypeNames.XmlLiteralText] = MakeScope("text." + defaultScope),
            };
        }
Example #4
0
 public ColoredSegment(int offset, int length, ScopeStack scopeStack) : base(offset, length)
 {
     this.scopeStack = scopeStack;
 }
 public abstract Tuple <bool, ScopeStack> MatchesStack(ScopeStack scopeStack, ref string matchExpr);
Example #6
0
 public override int GetHashCode()
 {
     unchecked {
         return((ScopeStack != null ? ScopeStack.GetHashCode() : 0) ^ Foreground.GetHashCode() ^ Background.GetHashCode() ^ FontWeight.GetHashCode() ^ FontStyle.GetHashCode());
     }
 }
 public abstract (bool, ScopeStack) MatchesStack(ScopeStack scopeStack, ref string matchExpr);
Example #8
0
        public static Dictionary <string, ScopeStack> GetClassificationMap(string scope)
        {
            Dictionary <string, ScopeStack> result;

            if (classificationMapCache.TryGetValue(scope, out result))
            {
                return(result);
            }
            var defaultScopeStack = new ScopeStack(scope);

            result = new Dictionary <string, ScopeStack> {
                [ClassificationTypeNames.Comment]             = MakeScope(defaultScopeStack, "comment." + scope),
                [ClassificationTypeNames.ExcludedCode]        = MakeScope(defaultScopeStack, "comment.excluded." + scope),
                [ClassificationTypeNames.Identifier]          = MakeScope(defaultScopeStack, scope),
                [ClassificationTypeNames.Keyword]             = MakeScope(defaultScopeStack, "keyword." + scope),
                [ClassificationTypeNames.NumericLiteral]      = MakeScope(defaultScopeStack, "constant.numeric." + scope),
                [ClassificationTypeNames.Operator]            = MakeScope(defaultScopeStack, scope),
                [ClassificationTypeNames.PreprocessorKeyword] = MakeScope(defaultScopeStack, "meta.preprocessor." + scope),
                [ClassificationTypeNames.StringLiteral]       = MakeScope(defaultScopeStack, "string." + scope),
                [ClassificationTypeNames.WhiteSpace]          = MakeScope(defaultScopeStack, "text." + scope),
                [ClassificationTypeNames.Text] = MakeScope(defaultScopeStack, "text." + scope),

                [ClassificationTypeNames.PreprocessorText]      = MakeScope(defaultScopeStack, "meta.preprocessor.region.name." + scope),
                [ClassificationTypeNames.Punctuation]           = MakeScope(defaultScopeStack, "punctuation." + scope),
                [ClassificationTypeNames.VerbatimStringLiteral] = MakeScope(defaultScopeStack, "string.verbatim." + scope),

                [ClassificationTypeNames.ClassName]         = MakeScope(defaultScopeStack, "entity.name.class." + scope),
                [ClassificationTypeNames.DelegateName]      = MakeScope(defaultScopeStack, "entity.name.delegate." + scope),
                [ClassificationTypeNames.EnumName]          = MakeScope(defaultScopeStack, "entity.name.enum." + scope),
                [ClassificationTypeNames.InterfaceName]     = MakeScope(defaultScopeStack, "entity.name.interface." + scope),
                [ClassificationTypeNames.ModuleName]        = MakeScope(defaultScopeStack, "entity.name.module." + scope),
                [ClassificationTypeNames.StructName]        = MakeScope(defaultScopeStack, "entity.name.struct." + scope),
                [ClassificationTypeNames.TypeParameterName] = MakeScope(defaultScopeStack, "entity.name.typeparameter." + scope),

                [ClassificationTypeNames.FieldName]           = MakeScope(defaultScopeStack, "entity.name.field." + scope),
                [ClassificationTypeNames.EnumMemberName]      = MakeScope(defaultScopeStack, "entity.name.enummember." + scope),
                [ClassificationTypeNames.ConstantName]        = MakeScope(defaultScopeStack, "entity.name.constant." + scope),
                [ClassificationTypeNames.LocalName]           = MakeScope(defaultScopeStack, "entity.name.local." + scope),
                [ClassificationTypeNames.ParameterName]       = MakeScope(defaultScopeStack, "entity.name.parameter." + scope),
                [ClassificationTypeNames.ExtensionMethodName] = MakeScope(defaultScopeStack, "entity.name.extensionmethod." + scope),
                [ClassificationTypeNames.MethodName]          = MakeScope(defaultScopeStack, "entity.name.function." + scope),
                [ClassificationTypeNames.PropertyName]        = MakeScope(defaultScopeStack, "entity.name.property." + scope),
                [ClassificationTypeNames.EventName]           = MakeScope(defaultScopeStack, "entity.name.event." + scope),

                [ClassificationTypeNames.XmlDocCommentAttributeName]         = MakeScope(defaultScopeStack, "comment.line.documentation." + scope),
                [ClassificationTypeNames.XmlDocCommentAttributeQuotes]       = MakeScope(defaultScopeStack, "comment.line.documentation." + scope),
                [ClassificationTypeNames.XmlDocCommentAttributeValue]        = MakeScope(defaultScopeStack, "comment.line.documentation." + scope),
                [ClassificationTypeNames.XmlDocCommentCDataSection]          = MakeScope(defaultScopeStack, "comment.line.documentation." + scope),
                [ClassificationTypeNames.XmlDocCommentComment]               = MakeScope(defaultScopeStack, "comment.line.documentation." + scope),
                [ClassificationTypeNames.XmlDocCommentDelimiter]             = MakeScope(defaultScopeStack, "comment.line.documentation." + scope),
                [ClassificationTypeNames.XmlDocCommentEntityReference]       = MakeScope(defaultScopeStack, "comment.line.documentation." + scope),
                [ClassificationTypeNames.XmlDocCommentName]                  = MakeScope(defaultScopeStack, "comment.line.documentation." + scope),
                [ClassificationTypeNames.XmlDocCommentProcessingInstruction] = MakeScope(defaultScopeStack, "comment.line.documentation." + scope),
                [ClassificationTypeNames.XmlDocCommentText]                  = MakeScope(defaultScopeStack, "comment.line.documentation." + scope),

                [ClassificationTypeNames.XmlLiteralAttributeName]      = MakeScope(defaultScopeStack, "entity.other.attribute-name." + scope),
                [ClassificationTypeNames.XmlLiteralAttributeQuotes]    = MakeScope(defaultScopeStack, "punctuation.definition.string." + scope),
                [ClassificationTypeNames.XmlLiteralAttributeValue]     = MakeScope(defaultScopeStack, "string.quoted." + scope),
                [ClassificationTypeNames.XmlLiteralCDataSection]       = MakeScope(defaultScopeStack, "text." + scope),
                [ClassificationTypeNames.XmlLiteralComment]            = MakeScope(defaultScopeStack, "comment.block." + scope),
                [ClassificationTypeNames.XmlLiteralDelimiter]          = MakeScope(defaultScopeStack, scope),
                [ClassificationTypeNames.XmlLiteralEmbeddedExpression] = MakeScope(defaultScopeStack, scope),
                [ClassificationTypeNames.XmlLiteralEntityReference]    = MakeScope(defaultScopeStack, scope),
                [ClassificationTypeNames.XmlLiteralName] = MakeScope(defaultScopeStack, "entity.name.tag.localname." + scope),
                [ClassificationTypeNames.XmlLiteralProcessingInstruction] = MakeScope(defaultScopeStack, scope),
                [ClassificationTypeNames.XmlLiteralText] = MakeScope(defaultScopeStack, "text." + scope),
            };
            classificationMapCache = classificationMapCache.SetItem(scope, result);

            return(result);
        }
Example #9
0
 static ScopeStack MakeScope(ScopeStack defaultScope, string scope)
 {
     return(defaultScope.Push(scope));
 }