예제 #1
0
        void FindHiddenRegions(ITextSnapshot snapShot, Irony.Parsing.ParseTreeNode root, ref List <Region> regions)
        {
            foreach (var child in root.ChildNodes)
            {
                Irony.Parsing.Token startToken = null;
                Irony.Parsing.Token endToken   = null;
                int startOffset = 0;

                if (child.Term.Name == LuaTerminalNames.TableConstructor)
                {
                    startToken = child.ChildNodes.First().Token;    // '{' symbol
                    endToken   = child.ChildNodes.Last().Token;     // '}' symbol
                }
                else if (child.Term.Name == LuaTerminalNames.FunctionBody)
                {
                    startToken = child.ChildNodes[2].Token; // ')' symbol
                    endToken   = child.ChildNodes[4].Token; // 'end' keyword

                    //Offset the outline by 1 so we don't hide the ')' symbol.
                    startOffset = 1;
                }
                ////折叠连续的多个注释块
                //else if (child.Token != null && child.Comments != null)
                //{
                //    if (child.Comments.Count > 1)
                //    {
                //        startToken = child.Comments[0];
                //        endToken = child.Comments.Last();
                //        startOffset = startToken.Text.Length;
                //    }
                //}

                if (startToken != null && endToken != null)
                {
                    if (startToken.Location.Line != endToken.Location.Line)
                    {
                        //So the column field of Location isn't always accurate...
                        //Position and Line are accurate though..
                        var startLine       = snapShot.GetLineFromLineNumber(startToken.Location.Line);
                        var startLineOffset = startToken.Location.Position - startLine.Start.Position;

                        var endLine       = snapShot.GetLineFromLineNumber(endToken.Location.Line);
                        var endLineOffset = (endToken.Location.Position + endToken.Length) - endLine.Start.Position;

                        var region = new Region();
                        region.StartLine   = startToken.Location.Line;
                        region.StartOffset = startLineOffset + startOffset;

                        region.EndLine   = endToken.Location.Line;
                        region.EndOffset = endLineOffset;

                        regions.Add(region);
                    }
                }

                FindHiddenRegions(snapShot, child, ref regions);
            }
        }
예제 #2
0
        // Extension to convert an Irony token to one independent of that library.
        public static Pie.Expressions.Token Convert(this Irony.Parsing.Token ironyToken)
        {
            if (ironyToken == null)
            {
                return(null);
            }

            var t = new Pie.Expressions.Token();

            t.Column   = ironyToken.Location.Column;
            t.Line     = ironyToken.Location.Line;
            t.Position = ironyToken.Location.Position;
            return(t);
        }
예제 #3
0
 private bool TryGetTag(Irony.Parsing.Token token, out ClassificationTag tag)
 {
     if (token.EditorInfo.Type == Irony.Parsing.TokenType.Identifier)
     {
         if (Help.Instance.ContainFunction(token.Text))
         {
             tag = _funcionTag;
             return(true);
         }
         if (Help.Instance.ContainTable(token.Text))
         {
             tag = _tableTag;
             return(true);
         }
         Help.Instance.AddIdentifier(token.Text);
     }
     return(_luaTags.TryGetValue(token.EditorInfo.Type, out tag));
 }
예제 #4
0
        bool IScanner.ScanTokenAndProvideInfoAboutIt(TokenInfo tokenInfo, ref int state)
        {
            Irony.Parsing.Token token = parser.Scanner.VsReadToken(ref state);

            // !EOL and !EOF
            if (token != null && token.Terminal != grammar.Eof && token.Category != Irony.Parsing.TokenCategory.Error)
            {
                tokenInfo.StartIndex = token.Location.Position;
                tokenInfo.EndIndex   = tokenInfo.StartIndex + token.Length - 1;

                Debug.WriteLine("token: '" + token.Text + "'");

                if (token.EditorInfo != null)
                {
                    tokenInfo.Color = (Microsoft.VisualStudio.Package.TokenColor)token.EditorInfo.Color;
                    tokenInfo.Type  = (Microsoft.VisualStudio.Package.TokenType)token.EditorInfo.Type;

                    if (token.KeyTerm != null)
                    {
                        tokenInfo.Trigger =
                            (Microsoft.VisualStudio.Package.TokenTriggers)token.KeyTerm.EditorInfo.Triggers;
                    }
                    else
                    {
                        tokenInfo.Trigger =
                            (Microsoft.VisualStudio.Package.TokenTriggers)token.EditorInfo.Triggers;
                    }
                }
                else
                {
                    tokenInfo.Color = TokenColor.Text;
                    tokenInfo.Type  = TokenType.Text;
                }



                return(true);
            }

            return(false);
        }
예제 #5
0
 public static SnapshotSpan AsSnapshotSpan(this Irony.Parsing.Token token, ITextSnapshot snapshot)
 {
     return(new SnapshotSpan(snapshot, token.Location.Position, Math.Max(token.Length, 1)));
 }
예제 #6
0
        /// <summary>
        /// 匹配自定义折叠标签,类似  --region [title]  和--endregion之间的内容;
        /// 匹配多行注释,类似--[[ content --]]
        /// </summary>
        /// <param name="root"></param>
        /// <param name="regions"></param>
        void FindUserRegions(ITextSnapshot snapShot, Irony.Parsing.ParseTree tree, ref List <Region> regions)
        {
            Irony.Parsing.Token startRegion = null;

            foreach (var token in tree.Tokens)
            {
                Region region = null;

                if (token.Category == Irony.Parsing.TokenCategory.Comment)
                {
                    if (token.Text.Contains('\n'))//多行注释,折叠
                    {
                        region             = new Region();
                        region.StartLine   = token.Location.Line;
                        region.StartOffset = 0;

                        region.EndLine   = token.Location.Line + token.Text.Count(c => { return(c == '\n'); });
                        region.EndOffset = snapShot.GetLineFromLineNumber(region.EndLine).Length;

                        region.Preview = snapShot.GetLineFromLineNumber(region.StartLine).GetText().Replace("--[[", "");

                        region.IsCollapsed = true;
                    }
                    else
                    {
                        if (token.Text.StartsWith("--region ") && startRegion == null)
                        {
                            startRegion = token;
                        }

                        else if (token.Text.StartsWith("--endregion") && startRegion != null)
                        {
                            try
                            {
                                region = new Region();
                                var startLine       = snapShot.GetLineFromLineNumber(startRegion.Location.Line);
                                var startLineOffset = startRegion.Location.Position - startLine.Start.Position;

                                var endLine       = snapShot.GetLineFromLineNumber(token.Location.Line);
                                var endLineOffset = (token.Location.Position + token.Length) - endLine.Start.Position;

                                region.StartLine   = startRegion.Location.Line;
                                region.StartOffset = startLineOffset;

                                region.EndLine   = token.Location.Line;
                                region.EndOffset = endLineOffset;

                                region.Preview = startRegion.Text.Replace("--region ", "");

                                startRegion = null;
                            }
                            catch
                            {
                                StringBuilder sb = new StringBuilder();
                                sb.AppendLine("LuaOutline.FindUserRegions cause an exception.");
                                sb.AppendLine("Args:");
                                sb.AppendLine("StartLine:" + startRegion.Location.Line + "," + startRegion.Location.Column);
                                sb.AppendLine("EndLine:" + token.Location.Line + "," + token.Location.Column);
                                sb.AppendLine("TextSnapshot Line:" + snapShot.LineCount);

                                Package.BabePackage.Setting.LogError(sb.ToString());
                                return;
                            }
                        }
                    }

                    if (region != null)
                    {
                        regions.Add(region);
                    }
                }
            }
        }
예제 #7
0
        public static ClassificationTag GetTag(Irony.Parsing.Token token)
        {
            ClassificationTag tag = null;

            if (token.EditorInfo.Type == Irony.Parsing.TokenType.Identifier)
            {
                if (C != null && C.Contains(token.Text))
                {
                    tag = CTag;
                }
                else if (LuaFramework != null && LuaFramework.Contains(token.Text))
                {
                    tag = LuaFrameworkTag;
                }
                else if (UserTags != null)
                {
                    for (int i = 0; i < UserTags.Count; i++)
                    {
                        if (Users[i].Contains(token.Text))
                        {
                            tag = UserTags[i];
                        }
                    }
                }

                if (m_table != null)
                {
                    var mem = m_table.Members.Find((lm) => { return(lm is LuaFunction && lm.Name == token.Text); });
                    if (mem != null)
                    {
                        m_table = null;
                        m_clear = false;
                        if (tag == null)
                        {
                            tag = LuaFunctionTag;
                        }
                    }
                    else if (m_clear == true)
                    {
                        m_table = null;
                        m_clear = false;
                    }
                    else
                    {
                        m_clear = true;
                    }
                }
                else if (IntellisenseHelper.ContainsFunction(token.Text))
                {
                    if (tag == null)
                    {
                        tag = LuaFunctionTag;
                    }
                }
                else if ((m_table = IntellisenseHelper.GetTable(token.Text)) != null)
                {
                    if (tag == null)
                    {
                        tag = LuaTableTag;
                    }
                }
            }

            if (OtherTags.ContainsKey(token.EditorInfo.Type) && tag == null)
            {
                tag = OtherTags[token.EditorInfo.Type];
            }

            return(tag);
        }
예제 #8
0
        /// <summary>
        /// In the context of a classification tagger, this is called initially w/ spans for all
        /// content in the file.
        /// It is called immediately after the user modifies text given the span of text that was modified.
        /// It is also called for all lines that are newly visible due to scrolling.
        /// This function gets called ALOT.  Keep processing times to a minimal and try to only handle 1 line at a
        /// time.
        /// </summary>
        /// <param name="spans"></param>
        /// <returns></returns>
        public IEnumerable <ITagSpan <ClassificationTag> > GetTags(NormalizedSnapshotSpanCollection spans)
        {
            if (spans.Count == 0)
            {
                yield break;
            }

            var snapShot = spans[0].Snapshot;

            foreach (var span in spans)
            {
                var startLine = span.Start.GetContainingLine();
                var endLine   = span.End.GetContainingLine();

                var startLineNumber = startLine.LineNumber;
                var endLineNumber   = endLine.LineNumber;

                for (int i = startLineNumber; i <= endLineNumber; i++)
                {
                    var line = spans[0].Snapshot.GetLineFromLineNumber(i);
                    _parser.Scanner.VsSetSource(line.GetText(), 0);

                    int state = 0;
                    _lineStates.TryGetValue(i, out state);

                    Irony.Parsing.Token token = _parser.Scanner.VsReadToken(ref state);
                    while (token != null)
                    {
                        if (token.Category == Irony.Parsing.TokenCategory.Content)
                        {
                            if (token.EditorInfo != null)
                            {
                                ClassificationTag tag;
                                if (TryGetTag(token, out tag))
                                {
                                    var location = new SnapshotSpan(snapShot, line.Start.Position + token.Location.Position, token.Length);
                                    yield return(new TagSpan <ClassificationTag>(location, tag));
                                }
                            }
                        }
                        else if (token.Category == Irony.Parsing.TokenCategory.Comment)
                        {
                            var location = new SnapshotSpan(snapShot, line.Start.Position + token.Location.Position, token.Length);
                            yield return(new TagSpan <ClassificationTag>(location, _commentTag));
                        }

                        token = _parser.Scanner.VsReadToken(ref state);
                    }

                    int oldState = 0;
                    _lineStates.TryGetValue(i + 1, out oldState);
                    _lineStates[i + 1] = state;

                    //We're going into overtime, process new tags and send the event that these spans need updating!
                    if (oldState != state)
                    {
                        var lineNumber = endLineNumber;
                        while (oldState != state && lineNumber < snapShot.LineCount)
                        {
                            lineNumber++;
                            var dummyToken = _parser.Scanner.VsReadToken(ref state);
                            while (dummyToken != null)
                            {
                                dummyToken = _parser.Scanner.VsReadToken(ref state);
                            }

                            _lineStates.TryGetValue(lineNumber + 1, out oldState);
                            _lineStates[lineNumber + 1] = state;
                        }

                        if (lineNumber >= snapShot.LineCount)
                        {
                            lineNumber = snapShot.LineCount - 1;
                        }

                        var lastLine = snapShot.GetLineFromLineNumber(lineNumber);
                        if (lastLine != null && this.TagsChanged != null)
                        {
                            int length       = lastLine.End.Position - endLine.End.Position;
                            var snapShotSpan = new SnapshotSpan(snapShot, endLine.End.Position, length);
                            this.TagsChanged(this, new SnapshotSpanEventArgs(snapShotSpan));
                        }
                    }
                }
            }
        }