コード例 #1
0
        public override void Complete(CompletionContext context, ICompletionItem item)
        {
            using (context.Editor.Document.OpenUndoGroup()) {
                base.Complete(context, item);

                XamlCompletionContext xamlContext = XamlContextResolver.ResolveCompletionContext(context.Editor, context.CompletionChar);

                if (xamlContext.Description == XamlContextDescription.None && (context.StartOffset <= 0 || context.Editor.Document.GetCharAt(context.StartOffset - 1) != '<'))
                {
                    context.Editor.Document.Insert(context.StartOffset, "<");
                    context.EndOffset++;
                }

                if (item is XamlCompletionItem && !item.Text.EndsWith(":", StringComparison.Ordinal))
                {
                    XamlCompletionItem cItem = item as XamlCompletionItem;

                    if (xamlContext.Description == XamlContextDescription.InTag)
                    {
                        context.Editor.Document.Insert(context.EndOffset, "=\"\"");
                        context.CompletionCharHandled = context.CompletionChar == '=';
                        context.Editor.Caret.Offset--;
                        new XamlCodeCompletionBinding().CtrlSpace(context.Editor);
                    }
                    else if (xamlContext.Description == XamlContextDescription.InMarkupExtension && !string.IsNullOrEmpty(xamlContext.RawAttributeValue))
                    {
                        string         valuePart = xamlContext.RawAttributeValue.Substring(0, xamlContext.ValueStartOffset);
                        AttributeValue value     = MarkupExtensionParser.ParseValue(valuePart);

                        if (value != null && !value.IsString)
                        {
                            var markup = Utils.GetMarkupExtensionAtPosition(value.ExtensionValue, context.Editor.Caret.Offset);
                            if (markup.NamedArguments.Count > 0 || markup.PositionalArguments.Count > 0)
                            {
                                int oldOffset = context.Editor.Caret.Offset;
                                context.Editor.Caret.Offset = context.StartOffset;
                                string word          = context.Editor.GetWordBeforeCaret().TrimEnd();
                                int    spaces        = CountWhiteSpacesAtEnd(context.Editor.GetWordBeforeCaret());
                                int    typeNameStart = markup.ExtensionType.IndexOf(':') + 1;

                                if (!(word == "." || word == "," || word == ":") && markup.ExtensionType.Substring(typeNameStart, markup.ExtensionType.Length - typeNameStart) != word)
                                {
                                    context.Editor.Document.Replace(context.Editor.Caret.Offset - spaces, spaces, ", ");
                                    oldOffset += (2 - spaces);
                                }

                                context.Editor.Caret.Offset = oldOffset;
                            }
                        }

                        if (cItem.Text.EndsWith("=", StringComparison.OrdinalIgnoreCase))
                        {
                            new XamlCodeCompletionBinding().CtrlSpace(context.Editor);
                        }
                    }
                }

                if (item is NewEventCompletionItem)
                {
                    CreateEventHandlerCode(xamlContext, item as NewEventCompletionItem);
                }

                if (item is XmlnsCompletionItem)
                {
                    context.Editor.Caret.Offset++;
                }

                switch (item.Text)
                {
                case "![CDATA[":
                    context.Editor.Document.Insert(context.Editor.Caret.Offset, "]]>");
                    context.Editor.Caret.Offset -= 3;
                    break;

                case "?":
                    context.Editor.Document.Insert(context.Editor.Caret.Offset, "?>");
                    context.Editor.Caret.Offset -= 2;
                    break;

                case "!--":
                    context.Editor.Document.Insert(context.Editor.Caret.Offset, "  -->");
                    context.Editor.Caret.Offset -= 4;
                    break;
                }

                if (item.Text.StartsWith("/", StringComparison.OrdinalIgnoreCase))
                {
                    context.Editor.Document.Insert(context.EndOffset, ">");
                    context.CompletionCharHandled = context.CompletionChar == '>';
                    context.Editor.Caret.Offset++;
                }
            }
        }
コード例 #2
0
		public IList<ICompletionItem> CreateElementList(XamlCompletionContext context, bool includeAbstract)
		{
			if (context.ParseInformation == null)
				return EmptyList<ICompletionItem>.Instance;
			
			List<ICompletionItem> result = new List<ICompletionItem>();
			AXmlElement last = context.ParentElement;
			ITextEditor editor = context.Editor;
			compilation = SD.ParserService.GetCompilationForFile(editor.FileName);
			IUnresolvedFile file = context.ParseInformation.UnresolvedFile;
			
			foreach (string item in XamlConst.GetAllowedItems(context)) {
				result.Add(new XamlCompletionItem(item));
			}
			
			IType rt = null;

			if (last != null) {
				if (string.Equals(last.Prefix, context.XamlNamespacePrefix, StringComparison.OrdinalIgnoreCase)) {
					if (string.Equals(last.LocalName, "Members", StringComparison.OrdinalIgnoreCase))
						return result;
					if (string.Equals(last.LocalName, "Code", StringComparison.OrdinalIgnoreCase))
						return result;
				}
				// If we have an element that is not a property or an incomplete
				// definition => interpret element as a type.
				XamlResolver resolver = new XamlResolver(compilation);
				int dotIndex = last.LocalName.IndexOf(".", StringComparison.Ordinal) + 1;
				if (dotIndex < 1 || dotIndex == last.LocalName.Length) {
					rt = resolver.ResolveType(last.Namespace, last.LocalName.Trim('.'));
					string contentPropertyName = GetContentPropertyName(rt.GetDefinition());
					// If the type has a content property specified, use its type for completion.
					if (!string.IsNullOrEmpty(contentPropertyName)) {
						IProperty p = rt.GetProperties(m => m.Name == contentPropertyName).FirstOrDefault();
						if (p != null) {
							rt = p.ReturnType;
						}
					}
				} else {
					string typeName = last.LocalName.Substring(0, dotIndex - 1);
					string memberName = last.LocalName.Substring(dotIndex);
					rt = resolver.ResolveType(last.Namespace, typeName);
					IMember member = rt.GetMembers(m => m.Name == memberName).FirstOrDefault();
					if (member != null) {
						rt = member.ReturnType;
					}
				}
			}
			
			bool parentAdded = false;
			var utd = file.GetInnermostTypeDefinition(editor.Caret.Location);
			ITypeDefinition currentTypeDef = null;
			if (utd != null) {
				currentTypeDef = utd.Resolve(new SimpleTypeResolveContext(compilation.MainAssembly)).GetDefinition();
			}
			MemberLookup memberLookup = new MemberLookup(currentTypeDef, compilation.MainAssembly);
			
			IList<ITypeDefinition> possibleTypesInCollection = EmptyList<ITypeDefinition>.Instance;
			if (rt != null && Extensions.IsListType(rt)) {
				possibleTypesInCollection = rt.GetMethods(m => m.Parameters.Count == 1 && "Add".Equals(m.Name, StringComparison.Ordinal))
					.Select(m => m.Parameters[0].Type.GetDefinition())
					.Where(t => t != null)
					.ToList();
			}
			
			var items = GetClassesFromContext(context);
			
			foreach (var ns in items) {
				foreach (ITypeDefinition td in ns.Value) {
					if (td.Kind != TypeKind.Class && (!includeAbstract || td.Kind != TypeKind.Interface))
						continue;
					if (td.IsStatic || (!includeAbstract && td.IsAbstract) || td.IsDerivedFrom(KnownTypeCode.Attribute))
						continue;
					if (td.Kind == TypeKind.Class && !td.GetConstructors().Any(m => memberLookup.IsAccessible(m, false)))
						continue;
					if (possibleTypesInCollection.Count > 0 && !possibleTypesInCollection.Any(td.IsDerivedFrom))
						continue;
					string fullName = td.Name;
					if (!string.IsNullOrEmpty(ns.Key))
						fullName = ns.Key + ":" + fullName;
					XamlCompletionItem item = new XamlCompletionItem(fullName, td);
					parentAdded = parentAdded || (last != null && item.Text == last.Name);
					result.Add(item);
				}
			}
			
			// TODO reimplement this if it is really necessary.
//			if (!parentAdded && last != null && !last.Name.Contains(".")) {
//				IClass itemClass = cu.CreateType(last.Namespace, last.LocalName.Trim('.')).GetUnderlyingClass();
//				if (itemClass != null)
//					result.Add(new XamlCodeCompletionItem(itemClass, last.Prefix));
//			}
			
			return result;
		}
コード例 #3
0
        public IList <ICompletionItem> CreateElementList(XamlCompletionContext context, bool includeAbstract)
        {
            if (context.ParseInformation == null)
            {
                return(EmptyList <ICompletionItem> .Instance);
            }

            List <ICompletionItem> result = new List <ICompletionItem>();
            AXmlElement            last   = context.ParentElement;
            ITextEditor            editor = context.Editor;

            compilation = SD.ParserService.GetCompilationForFile(editor.FileName);
            IUnresolvedFile file = context.ParseInformation.UnresolvedFile;

            foreach (string item in XamlConst.GetAllowedItems(context))
            {
                result.Add(new XamlCompletionItem(item));
            }

            IType rt = null;

            if (last != null)
            {
                if (string.Equals(last.Prefix, context.XamlNamespacePrefix, StringComparison.OrdinalIgnoreCase))
                {
                    if (string.Equals(last.LocalName, "Members", StringComparison.OrdinalIgnoreCase))
                    {
                        return(result);
                    }
                    if (string.Equals(last.LocalName, "Code", StringComparison.OrdinalIgnoreCase))
                    {
                        return(result);
                    }
                }
                // If we have an element that is not a property or an incomplete
                // definition => interpret element as a type.
                XamlResolver resolver = new XamlResolver(compilation);
                int          dotIndex = last.LocalName.IndexOf(".", StringComparison.Ordinal) + 1;
                if (dotIndex < 1 || dotIndex == last.LocalName.Length)
                {
                    rt = resolver.ResolveType(last.Namespace, last.LocalName.Trim('.'));
                    string contentPropertyName = GetContentPropertyName(rt.GetDefinition());
                    // If the type has a content property specified, use its type for completion.
                    if (!string.IsNullOrEmpty(contentPropertyName))
                    {
                        IProperty p = rt.GetProperties(m => m.Name == contentPropertyName).FirstOrDefault();
                        if (p != null)
                        {
                            rt = p.ReturnType;
                        }
                    }
                }
                else
                {
                    string typeName   = last.LocalName.Substring(0, dotIndex - 1);
                    string memberName = last.LocalName.Substring(dotIndex);
                    rt = resolver.ResolveType(last.Namespace, typeName);
                    IMember member = rt.GetMembers(m => m.Name == memberName).FirstOrDefault();
                    if (member != null)
                    {
                        rt = member.ReturnType;
                    }
                }
            }

            bool            parentAdded    = false;
            var             utd            = file.GetInnermostTypeDefinition(editor.Caret.Location);
            ITypeDefinition currentTypeDef = null;

            if (utd != null)
            {
                currentTypeDef = utd.Resolve(new SimpleTypeResolveContext(compilation.MainAssembly)).GetDefinition();
            }
            MemberLookup memberLookup = new MemberLookup(currentTypeDef, compilation.MainAssembly);

            IList <ITypeDefinition> possibleTypesInCollection = EmptyList <ITypeDefinition> .Instance;

            if (rt != null && Extensions.IsListType(rt))
            {
                possibleTypesInCollection = rt.GetMethods(m => m.Parameters.Count == 1 && "Add".Equals(m.Name, StringComparison.Ordinal))
                                            .Select(m => m.Parameters[0].Type.GetDefinition())
                                            .Where(t => t != null)
                                            .ToList();
            }

            var items = GetClassesFromContext(context);

            foreach (var ns in items)
            {
                foreach (ITypeDefinition td in ns.Value)
                {
                    if (td.Kind != TypeKind.Class && (!includeAbstract || td.Kind != TypeKind.Interface))
                    {
                        continue;
                    }
                    if (td.IsStatic || (!includeAbstract && td.IsAbstract) || td.IsDerivedFrom(KnownTypeCode.Attribute))
                    {
                        continue;
                    }
                    if (td.Kind == TypeKind.Class && !td.GetConstructors().Any(m => memberLookup.IsAccessible(m, false)))
                    {
                        continue;
                    }
                    if (possibleTypesInCollection.Count > 0 && !possibleTypesInCollection.Any(td.IsDerivedFrom))
                    {
                        continue;
                    }
                    string fullName = td.Name;
                    if (!string.IsNullOrEmpty(ns.Key))
                    {
                        fullName = ns.Key + ":" + fullName;
                    }
                    XamlCompletionItem item = new XamlCompletionItem(fullName, td);
                    parentAdded = parentAdded || (last != null && item.Text == last.Name);
                    result.Add(item);
                }
            }

            // TODO reimplement this if it is really necessary.
//			if (!parentAdded && last != null && !last.Name.Contains(".")) {
//				IClass itemClass = cu.CreateType(last.Namespace, last.LocalName.Trim('.')).GetUnderlyingClass();
//				if (itemClass != null)
//					result.Add(new XamlCodeCompletionItem(itemClass, last.Prefix));
//			}

            return(result);
        }