/// <summary>
 /// Gets a classifier for the given text buffer.
 /// </summary>
 /// <param name="buffer">The <see cref="ITextBuffer"/> to classify.</param>
 /// <returns>A classifier for the text buffer, or null if the provider cannot do so in its current state.</returns>
 public IClassifier GetClassifier(ITextBuffer buffer)
 {
     // only return a classifier when this is really our document
     if (!factory.IsXSharpDocument(buffer))
     {
         return(null);
     }
     return(buffer.Properties.GetOrCreateSingletonProperty(creator: () =>
                                                           XSharpClassifier.GetColorizer(buffer, this.classificationRegistry, this.factory)));
 }
 private void registerClassifier()
 {
     if (_classifier == null)
     {
         _classifier = _buffer.GetClassifier();
         if (_classifier != null)
         {
             _classifier.ClassificationChanged += Classifier_ClassificationChanged;
         }
     }
 }
Exemple #3
0
        public IEnumerable <ITagSpan <IOutliningRegionTag> > GetTags(NormalizedSnapshotSpanCollection spans)
        {
            //yield break;
            if (spans.Count == 0)
            {
                yield break;
            }
            // Try to retrieve an already parsed list of Tags
            XSharpClassifier xsClassifier = buffer.GetClassifier();

            if (xsClassifier != null)
            {
                //
                ITextSnapshot snapshot        = xsClassifier.Snapshot;
                SnapshotSpan  Span            = new SnapshotSpan(snapshot, 0, snapshot.Length);
                var           classifications = xsClassifier.GetRegionTags();

                SnapshotSpan fullSpan        = new SnapshotSpan(spans[0].Start, spans[spans.Count - 1].End).TranslateTo(snapshot, SpanTrackingMode.EdgeExclusive);
                int          startLineNumber = fullSpan.Start.GetContainingLine().LineNumber;
                int          endLineNumber   = fullSpan.End.GetContainingLine().LineNumber;
                //
                Stack <ClassificationSpan> startStack = new Stack <ClassificationSpan>();
                // convert classifications to an array so there will be no crash when the classifications are changed
                // in another thread.

                // Now, let's have a look at all the Classifications we have in the document
                foreach (var tag in classifications)
                {
                    // Is it a Region ?
                    if (tag.ClassificationType.IsOfType(this.xsharpRegionStartType.Classification))
                    {
                        startStack.Push(tag);
                    }
                    else if (tag.ClassificationType.IsOfType(this.xsharpRegionStopType.Classification) && (startStack.Count > 0))
                    {
                        //
                        var startTag  = startStack.Pop();
                        var startLine = startTag.Span.Start.GetContainingLine();
                        var endLine   = tag.Span.End.GetContainingLine();
                        //
                        if (startTag.Span.Start < tag.Span.End &&
                            startLine.LineNumber <= endLineNumber &&
                            endLine.LineNumber >= startLineNumber)
                        {
                            SnapshotSpan sSpan;
                            try
                            {
                                sSpan = new SnapshotSpan(startLine.Start, endLine.End);
                            }
                            catch (Exception e)
                            {
                                System.Diagnostics.Debug.WriteLine("Incorrect span " + e.Message);
                                sSpan = new SnapshotSpan(startLine.Start, startLine.Start);
                            }
                            hoverText = sSpan.GetText();
                            if (hoverText.Length > 1024)
                            {
                                hoverText = hoverText.Substring(0, 1024) + "\r\n......";
                            }
                            //
                            sSpan = new SnapshotSpan(startLine.Start, startLine.End);
                            ////the region starts at the beginning of the entity, and goes until the *end* of the line that ends.
                            yield return(new TagSpan <IOutliningRegionTag>(
                                             new SnapshotSpan(startLine.End, endLine.End),
                                             new OutliningRegionTag(false, true, ellipsis, hoverText)));
                        }
                    }
                }
            }
            else
            {
                yield break;
            }
        }
Exemple #4
0
        public IEnumerable <ITagSpan <TextMarkerTag> > GetTags(NormalizedSnapshotSpanCollection spans)
        {
            // Todo: the classifier is now marking open and close keywords with (invisible) classification
            // on another location the classifier is building regions based on Open/Close keywords.
            // During this process of building regions we can also 'remember' the open/close pairs
            // so we do not have to look for these in this code.

            DateTime oStart, oEnd;
            TimeSpan timeSpan;

            oStart = DateTime.Now;

            if (spans.Count == 0 || _currentChar == null)   //there is no content in the buffer
            {
                yield break;
            }
            WriteOutputMessage($"GetTags() Spans: {spans.Count}");

            //don't do anything if the current SnapshotPoint is not initialized or at the end of the buffer
            if (!_currentChar.HasValue || _currentChar.Value.Position >= _currentChar.Value.Snapshot.Length)
            {
                yield break;
            }


            //hold on to a snapshot of the current character
            SnapshotPoint currentChar = _currentChar.Value;

            //if the requested snapshot isn't the same as the one the brace is on, translate our spans to the expected snapshot
            if (spans[0].Snapshot != currentChar.Snapshot)
            {
                currentChar = currentChar.TranslateTo(spans[0].Snapshot, PointTrackingMode.Positive);
            }

            //get the current char and the previous char
            SnapshotSpan pairSpan = new SnapshotSpan();


            // check to see if we are on a closing or opening keyword
            if (!cursorOnKwOpenClose(currentChar))
            {
                yield break;
            }

            // Try to Match Keywords
            // Try to retrieve an already parsed list of Tags
            XSharpClassifier xsClassifier = _buffer.GetClassifier();

            if (xsClassifier == null)
            {
                yield break;
            }
            else
            {
                ITagSpan <TextMarkerTag> result1 = null;
                ITagSpan <TextMarkerTag> result2 = null;
                ITagSpan <TextMarkerTag> result3 = null;
                ITagSpan <TextMarkerTag> result4 = null;
                try
                {
                    WriteOutputMessage("Match Open/Close keywords : " + oStart.ToString("hh:mm:ss.fff"));

                    ITextSnapshot snapshot = xsClassifier.Snapshot;
                    if (snapshot.Version != currentChar.Snapshot.Version)
                    {
                        yield break;
                    }
                    SnapshotSpan Span            = new SnapshotSpan(snapshot, 0, snapshot.Length);
                    var          classifications = xsClassifier.GetTags();
                    // We cannot use SortedList, because we may have several Classification that start at the same position
                    List <ClassificationSpan> sortedTags = new List <ClassificationSpan>();
                    foreach (var tag in classifications)
                    {
                        // Only keep the Brace matching Tags
                        if ((tag.ClassificationType.IsOfType(ColorizerConstants.XSharpKwOpenFormat)) ||
                            (tag.ClassificationType.IsOfType(ColorizerConstants.XSharpKwCloseFormat)))
                        {
                            sortedTags.Add(tag);
                        }
                    }
                    sortedTags.Sort((a, b) => a.Span.Start.Position.CompareTo(b.Span.Start.Position) * 1000 + string.Compare(a.ClassificationType.Classification, b.ClassificationType.Classification));
                    //
                    var tags = sortedTags.Where(x => currentChar.Position >= x.Span.Start.Position && currentChar.Position <= x.Span.End.Position);
                    foreach (var currentTag in tags)
                    {
                        var index = sortedTags.IndexOf(currentTag);
                        if (currentTag.ClassificationType.IsOfType(ColorizerConstants.XSharpKwOpenFormat) && result1 == null)
                        {
                            if (FindMatchingCloseTag(sortedTags, index, snapshot, out pairSpan))
                            {
                                var span = currentTag.Span;
                                result1 = new TagSpan <TextMarkerTag>(span, _tag);
                                result2 = new TagSpan <TextMarkerTag>(pairSpan, _tag);
                            }
                        }
                        else if (result3 == null)
                        {
                            if (FindMatchingOpenTag(sortedTags, index, snapshot, out pairSpan))
                            {
                                var span = currentTag.Span;
                                result3 = new TagSpan <TextMarkerTag>(pairSpan, _tag);
                                result4 = new TagSpan <TextMarkerTag>(span, _tag);
                            }
                        }
                    }
                }
                catch (Exception e)
                {
                    XSettings.LogException(e, "KeywordMatchingTagger.GetTags failed");
                }
                finally
                {
                    oEnd     = DateTime.Now;
                    timeSpan = oEnd - oStart;
                    WriteOutputMessage("Finished Match Open/Close keywords: " + oEnd.ToString("hh:mm:ss.fff"));
                    WriteOutputMessage("Finished Match Open/Close keywords - total ms: " + timeSpan.TotalMilliseconds.ToString());
                }
                if (result1 != null)
                {
                    yield return(result1);
                }
                if (result2 != null)
                {
                    yield return(result2);
                }
                if (result3 != null)
                {
                    yield return(result3);
                }
                if (result4 != null)
                {
                    yield return(result4);
                }
            }
        }