コード例 #1
0
        private string GetModVis(IXMemberSymbol mbr)
        {
            string desc = mbr.ModVis;

            if ((mbr is XPEMethodSymbol) || (mbr is XPEPropertySymbol))
            {
                desc = desc.Replace(" ABSTRACT ", "");
                desc = desc.Replace(" NEW ", "");
                desc = desc.Replace(" OVERRIDE ", "");
            }
            return(desc);
        }
コード例 #2
0
        private string getProto(IXMemberSymbol xMember, XSharpSignatureProperties props)
        {
            var proto = xMember.Prototype;

            // Adjust SELF() and SUPER: remove typename and replace {} with ()
            if (xMember.Kind == Kind.Constructor && props.triggerChar == '(')
            {
                var parlist = proto.Substring(proto.IndexOf('{') + 1);
                parlist = parlist.Substring(0, parlist.Length - 1);
                proto   = props.triggerToken + "(" + parlist + ")";
            }
            return(proto);
        }
コード例 #3
0
 internal XMemberAnalysis(IXMemberSymbol member)
 {
     TypeName = "";
     if (member == null)
     {
         return;
     }
     Member = member;
     Name   = member.Name;
     Value  = member.Value;
     if (member.Kind.HasReturnType())
     {
         TypeName = member.TypeName;
     }
 }
コード例 #4
0
        private XSharpVsSignature CreateSignature(ITextBuffer textBuffer, IXMemberSymbol member, string methodSig, ITrackingSpan span, bool isCtor, XFile file)
        {
            var    doc = "";
            string returns;
            string remarks;

            if (member != null)
            {
                doc = XSharpXMLDocMember.GetMemberSummary(member, file.Project, out returns, out remarks);
            }

            Debug($"XSharpSignatureHelpSource.CreateSignature( {methodSig})");
            var sig          = new XSharpVsSignature(textBuffer, methodSig, doc, null);
            var names        = new List <string>();
            var descriptions = new List <string>();

            if (member != null)
            {
                XSharpXMLDocMember.GetMemberParameters(member, file.Project, names, descriptions);
            }
            // Moved : Done in the XSharpSignature constructor
            // textBuffer.Changed += new EventHandler<TextContentChangedEventArgs>(sig.OnSubjectBufferChanged);

            // find the parameters in the method signature :
            // MyMethod( param1 AS TYPE1, param2 AS TYPE2 ) AS TYPE3 will turn to
            // 0 : MyMethod
            // 1 : param1 AS TYPE1
            // 2 : param2 AS TYPE2
            // 3 : AS TYPE3
            var pars = methodSig.Split(new char[] { '(', '{', ',', '}', ')' });
            List <IParameter> paramList = new List <IParameter>();
            int locusSearchStart        = 0;

            // i = 1 to skip the MethodName; Length-1 to Skip the ReturnType
            while (names.Count < pars.Length)
            {
                names.Add("");
                descriptions.Add("");
            }
            for (int i = 1; i < pars.Length - 1; i++)
            {
                string param = pars[i].Trim();
                if (string.IsNullOrEmpty(param))
                {
                    continue;
                }

                //find where this parameter is located in the method signature
                int locusStart = methodSig.IndexOf(param, locusSearchStart);
                if (locusStart >= 0)
                {
                    Span locus = new Span(locusStart, param.Length);
                    locusSearchStart = locusStart + param.Length;
                    // paramList.Add(new XSharpParameter("Documentation for the parameter.", locus, param, sig));
                    if (!string.IsNullOrEmpty(names[i - 1]))
                    {
                        param = names[i - 1];
                    }
                    paramList.Add(new XSharpVsParameter(descriptions[i - 1], locus, param, sig));
                }
            }

            sig.Parameters       = new ReadOnlyCollection <IParameter>(paramList);
            sig.ApplicableToSpan = span;
            sig.ComputeCurrentParameter();
            return(sig);
        }
コード例 #5
0
        public void AugmentSignatureHelpSession(ISignatureHelpSession session, IList <ISignature> signatures)
        {
            try
            {
                Debug("XSharpSignatureHelpSource.AugmentSignatureHelpSession()");
                m_session = session;
                XSharpModel.ModelWalker.Suspend();
                ITextSnapshot             snapshot = m_textBuffer.CurrentSnapshot;
                XSharpSignatureProperties props;
                int position = session.GetTriggerPoint(m_textBuffer).GetPosition(snapshot);
                session.Properties.TryGetProperty(typeof(XSharpSignatureProperties), out props);
                m_applicableToSpan = m_textBuffer.CurrentSnapshot.CreateTrackingSpan(new Span(props.Start, props.Length), SpanTrackingMode.EdgeInclusive, 0);

                object elt = props.Element;
                if (elt is IXSymbol)
                {
                    IXMemberSymbol element = elt as IXMemberSymbol;
                    //
                    if (elt is IXMemberSymbol xMember)
                    {
                        var names = new List <string>();
                        var proto = getProto(xMember, props);
                        names.Add(proto);
                        signatures.Add(CreateSignature(m_textBuffer, xMember, proto, ApplicableToSpan, xMember.Kind == XSharpModel.Kind.Constructor, m_file));
                        var overloads = xMember.GetOverloads();

                        foreach (var member in overloads)
                        {
                            if (member.Visibility < props.Visibility)
                            {
                                continue;
                            }
                            // prevent duplicate prototypes in the list  (when a child has overriden a method)
                            proto = getProto(member, props);
                            if (!names.Contains(proto))
                            {
                                signatures.Add(CreateSignature(m_textBuffer, member, proto, ApplicableToSpan, member.Kind == XSharpModel.Kind.Constructor, m_file));
                                names.Add(proto);
                            }
                        }
                    }
                    else if (element != null)
                    {
                        // Type ??
                        signatures.Add(CreateSignature(m_textBuffer, null, element.Prototype, ApplicableToSpan, false, m_file));
                    }
                    // why not ?
                    int paramCount = int.MaxValue;
                    foreach (ISignature sig in signatures)
                    {
                        if (sig.Parameters.Count < paramCount)
                        {
                            paramCount = sig.Parameters.Count;
                        }
                    }
                    //
                    m_textBuffer.Changed += new EventHandler <TextContentChangedEventArgs>(OnSubjectBufferChanged);
                }
                session.Dismissed += OnSignatureHelpSessionDismiss;
            }
            catch (Exception ex)
            {
                XSettings.LogException(ex, "XSharpSignatureHelpSource.AugmentSignatureHelpSession Exception failed ");
            }
            finally
            {
                XSharpModel.ModelWalker.Resume();
            }
        }
コード例 #6
0
        internal bool StartSignatureSession(bool comma, IXTypeSymbol type = null, string methodName = null, char triggerchar = '\0')
        {
            WriteOutputMessage("StartSignatureSession()");

            if (_signatureSession != null)
            {
                return(false);
            }
            IXMemberSymbol currentElement = null;
            SnapshotPoint  ssp            = this._textView.Caret.Position.BufferPosition;

            if (triggerchar == '(' && ssp.Position < ssp.Snapshot.Length && ssp.GetChar() == ')')
            {
                ssp -= 1;
            }
            var location = _textView.FindLocation(ssp);

            if (location == null || location.Member == null)
            {
                return(false);
            }
            if (location.Member.Range.StartLine == location.LineNumber)
            {
                return(false);
            }

            var props = new XSharpSignatureProperties(location);

            props.triggerChar     = triggerchar;
            props.triggerPosition = this._textView.Caret.Position.BufferPosition.Position;

            if (type != null && methodName != null)
            {
                var findStatic = triggerchar == '.';
                currentElement = XSharpLookup.SearchMethod(location, type, methodName, Modifiers.Private, findStatic).FirstOrDefault();
            }
            else
            {
                currentElement = findElementAt(comma, ssp, props);
            }
            if (currentElement == null)
            {
                return(false);
            }

            SnapshotPoint caret         = _textView.Caret.Position.BufferPosition;
            ITextSnapshot caretsnapshot = caret.Snapshot;

            //
            if (_signatureBroker.IsSignatureHelpActive(_textView))
            {
                _signatureSession = _signatureBroker.GetSessions(_textView)[0];
            }
            else
            {
                _signatureSession = _signatureBroker.CreateSignatureHelpSession(_textView, caretsnapshot.CreateTrackingPoint(caret, PointTrackingMode.Positive), true);
            }
            _signatureSession.Properties[typeof(XSharpSignatureProperties)] = props;

            if (location.Member.Kind.IsGlobalTypeMember())
            {
                props.Visibility = Modifiers.Public;
            }
            else
            {
                props.Visibility = Modifiers.Protected;
            }
            _signatureSession.Dismissed += OnSignatureSessionDismiss;
            props.Element = currentElement;
            if (comma)
            {
                var  tokenList = XSharpTokenTools.GetTokenListBeforeCaret(location, out var state);
                bool done      = false;
                int  nested    = 0;
                for (int i = tokenList.Count - 1; i >= 0 && !done; i--)
                {
                    var token = tokenList[i];
                    switch (token.Type)
                    {
                    case XSharpLexer.LPAREN:
                    case XSharpLexer.LCURLY:
                    case XSharpLexer.LBRKT:
                        done = nested == 0;
                        if (done)
                        {
                            props.Start  = token.Position;
                            props.Length = _textView.Caret.Position.BufferPosition.Position - token.Position;
                        }
                        nested -= 1;
                        break;

                    case XSharpLexer.RPAREN:
                    case XSharpLexer.RCURLY:
                    case XSharpLexer.RBRKT:
                        nested += 1;
                        break;
                    }
                }
            }
            else
            {
                props.Start  = ssp.Position;
                props.Length = _textView.Caret.Position.BufferPosition.Position - ssp.Position;
            }


            try
            {
                _signatureSession.Start();
            }
            catch (Exception e)
            {
                XSettings.LogException(e, "Start Signature session failed:");
            }
            //
            return(true);
        }
コード例 #7
0
        IXMemberSymbol findElementAt(bool comma, SnapshotPoint ssp, XSharpSignatureProperties props)
        {
            // when coming from the completion list then there is no need to check a lot of stuff
            // we can then simply lookup the method and that is it.
            // Also no need to filter on visibility since that has been done in the completionlist already !
            // First, where are we ?
            var location = props.Location;

            // When we have a multi line source line this is the line where the open paren or open curly is

            if (location.Member != null && location.Member.Range.StartLine == ssp.GetContainingLine().LineNumber)
            {
                // if we are at the start of an entity then do not start a signature session
                return(null);
            }
            // Then, the corresponding Type/Element if possible
            // Check if we can get the member where we are

            var tokenList = XSharpTokenTools.GetTokenListBeforeCaret(location, out var state);
            // tokenlist may look like ID1 ( ID2 ( e1 , e2)
            // after the closing paren we come here and want to completely remove the  ID2 ( e1, e2 ) part
            // when we have this ID1 ( e1 ) then there should be no parameter completion at all
            // The same for ID1 { e1 }
            // so we need to see if LPAREN / RPAREN is closed and if LCURLY / RCURLY is closed and if LBRKT / RBRKT is closed
            int nested     = 0;
            var openTokens = new Stack <XSharpToken>();

            for (int i = 0; i < tokenList.Count; i++)
            {
                var token = tokenList[i];
                switch (token.Type)
                {
                case XSharpLexer.LPAREN:
                case XSharpLexer.LCURLY:
                case XSharpLexer.LBRKT:
                    openTokens.Push(token);
                    break;

                case XSharpLexer.RPAREN:
                    if (openTokens.Count > 0 && openTokens.Peek().Type == XSharpLexer.LPAREN)
                    {
                        openTokens.Pop();
                    }
                    break;

                case XSharpLexer.RCURLY:
                    if (openTokens.Count > 0 && openTokens.Peek().Type == XSharpLexer.LCURLY)
                    {
                        openTokens.Pop();
                    }
                    break;

                case XSharpLexer.RBRKT:
                    if (openTokens.Count > 0 && openTokens.Peek().Type == XSharpLexer.LBRKT)
                    {
                        openTokens.Pop();
                    }
                    break;

                case XSharpLexer.STRING_CONST:
                case XSharpLexer.INTERPOLATED_STRING_CONST:
                case XSharpLexer.CHAR_CONST:
                    if (token.Position < location.Position && location.Position < token.Position + token.Text.Length)
                    {
                        // comma inside literal !
                        return(null);
                    }
                    break;
                }
            }

            if (openTokens.Count == 0)
            {
                tokenList.Clear();
            }
            else
            {
                var pos = tokenList.IndexOf(openTokens.Peek());
                if (pos >= 0)
                {
                    tokenList.RemoveRange(pos + 1, tokenList.Count - pos - 1);
                }
            }
            if (comma)
            {
                // check to see if there is a lparen or lcurly before the comma
                bool done = false;
                nested = 0;
                while (tokenList.Count > 0 && !done)
                {
                    var  token  = tokenList[tokenList.Count - 1];
                    bool delete = false;
                    switch (token.Type)
                    {
                    case XSharpLexer.RPAREN:
                    case XSharpLexer.RBRKT:
                    case XSharpLexer.RCURLY:
                        nested += 1;
                        delete  = true;
                        break;

                    case XSharpLexer.LBRKT:
                        nested -= 1;
                        delete  = true;
                        break;

                    case XSharpLexer.LPAREN:
                    case XSharpLexer.LCURLY:
                        nested -= 1;
                        if (nested < 0)
                        {
                            done = true;
                        }
                        else
                        {
                            delete = true;
                        }
                        break;

                    default:
                        delete = true;
                        break;
                    }
                    if (delete)
                    {
                        tokenList.RemoveAt(tokenList.Count - 1);
                    }
                }
            }

            IXMemberSymbol currentElement = null;
            // We don't care of the corresponding Type, we are looking for the currentElement
            var element = XSharpLookup.RetrieveElement(location, tokenList, state, out var notProcessed, true).FirstOrDefault();

            if (element is IXMemberSymbol mem)
            {
                currentElement = mem;
                if (currentElement.Kind == Kind.Constructor)
                {
                    bool done = false;
                    for (int i = tokenList.Count - 1; !done && i > 0; i--)
                    {
                        var token = tokenList[i];
                        switch (token.Type)
                        {
                        case XSharpLexer.LPAREN:
                        case XSharpLexer.LCURLY:
                            props.triggerToken = tokenList[i - 1].Text;
                            break;
                        }
                    }
                }
            }
            else if (element is IXTypeSymbol xtype)
            {
                currentElement = xtype.Members.Where(m => m.Kind == Kind.Constructor).FirstOrDefault();
            }
            return(currentElement);
        }
コード例 #8
0
 internal QuickInfoTypeMember(IXMemberSymbol tm) : base(tm)
 {
     this.typeMember = tm;
 }