Пример #1
0
        /// <summary>
        /// Gets the range of the expression to the left of our starting span.
        /// </summary>
        /// <param name="nesting">1 if we have an opening parenthesis for sig completion</param>
        /// <param name="paramIndex">The current parameter index.</param>
        /// <returns></returns>
        public SnapshotSpan?GetExpressionRange(int nesting, out int paramIndex, out SnapshotPoint?sigStart, bool forCompletion = true)
        {
            SnapshotSpan?start   = null;
            var          endText = String.Empty;

            paramIndex = 0;
            sigStart   = null;
            bool nestingChanged = false;

            ClassificationSpan lastToken = null;

            // Walks backwards over all the lines
            if (Tokens.Count > 0)
            {
                lastToken = Tokens[Tokens.Count - 1];
                while (true)
                {
                    // Walk backwards over the tokens in the current line
                    for (int t = Tokens.Count - 1; t >= 0; t--)
                    {
                        var token = Tokens[t];
                        var text  = token.Span.GetText();

                        if (token.ClassificationType == Classifier.Provider.Keyword ||
                            (token.ClassificationType == Classifier.Provider.Operator &&
                             text != "[" && text != "]" && text != "}" && text != "{"))
                        {
                            if (nesting == 0)
                            {
                                if (start == null)
                                {
                                    // hovering directly over a keyword, don't provide a tooltip
                                    return(null);
                                }
                                else if ((nestingChanged || forCompletion) && token.ClassificationType == Classifier.Provider.Keyword && text == "def")
                                {
                                    return(null);
                                }
                                break;
                            }
                        }
                        else if (token.ClassificationType == Classifier.Provider.OpenGroupingClassification || text == "[" || text == "{")
                        {
                            if (nesting != 0)
                            {
                                nesting--;
                                nestingChanged = true;
                                if (nesting == 0 && sigStart == null)
                                {
                                    sigStart = token.Span.Start;
                                }
                            }
                            else
                            {
                                break;
                            }
                        }
                        else if (token.ClassificationType == Classifier.Provider.CloseGroupingClassification ||
                                 text == "]" || text == "}")
                        {
                            nesting++;
                            nestingChanged = true;
                        }
                        else if (token.ClassificationType == Classifier.Provider.CommaClassification)
                        {
                            if (nesting == 0)
                            {
                                if (start == null)
                                {
                                    return(null);
                                }
                                break;
                            }
                            else if (nesting == 1 && sigStart == null)
                            {
                                paramIndex++;
                            }
                        }
                        else if (token.ClassificationType == Classifier.Provider.Comment)
                        {
                            return(null);
                        }

                        start = token.Span;
                    }

                    if (nesting == 0 || CurrentLine.LineNumber == 0)
                    {
                        break;
                    }

                    // We're in a nested paren context, continue to the next line
                    // to capture the entire expression
                    endText     = CurrentLine.GetText() + endText;
                    CurrentLine = Snapshot.GetLineFromLineNumber(CurrentLine.LineNumber - 1);

                    var classSpan = new SnapshotSpan(Snapshot, CurrentLine.Start, CurrentLine.Length);
                    Tokens = Classifier.GetClassificationSpans(classSpan);
                }
            }

            if (start.HasValue)
            {
                return(new SnapshotSpan(
                           Snapshot,
                           new Span(
                               start.Value.Start.Position,
                               //_span.GetEndPoint(_snapshot).Position - start.Value.Start.Position
                               lastToken.Span.End.Position - start.Value.Start.Position
                               )
                           ));
            }

            return(_span.GetSpan(_snapshot));
        }