简体   繁体   English

使用 Activator.CreateInstance(Type t),如何将“对象”转换为“T”以添加到列表<t></t>

[英]Using Activator.CreateInstance(Type t), how to cast 'object' to 'T' to add to List<T>

Working in a custom WPF control, we need to allow the user to add a new object to a list (similar to the ComboBox when IsEditable = true).在自定义 WPF 控件中工作,我们需要允许用户将新的 object 添加到列表中(类似于 IsEditable = true 时的 ComboBox)。
The ItemsSource is an ObservableCollection<T>. ItemsSource 是一个 ObservableCollection<T>。

When the user enters a string, the control needs to create a new T object and add it to the list.当用户输入字符串时,控件需要新建一个 T object 并添加到列表中。
We have a method to determine what type T is from the ItemsSource object, and then use Activator.CreateInstance() to create a T:我们有一个方法可以从ItemsSource object中判断T是什么类型,然后使用Activator.CreateInstance()创建一个T:

 private Type _typ;
 public void AddSomething(object o)
 {
     var iCollection = o as ICollection;
     if (iCollection != null)
     {
        dynamic oc = iCollection;
        _typ = GetGenericType(oc);
        Debug.WriteLine($"    ICollection<T> T type: {_typ}");

        var thng = Activator.CreateInstance(_typ);  

        Debug.WriteLine($"    thng Type: {thng.GetType()}");  
        
        ItemsSourceClass.Things.Add(thng as _typ);  
        // Compile time error:
        CS0246  The type or namespace name '_typ' could not be found (are you missing a using directive or an assembly reference?)
        /* snip */  
            

This all works as expected - thng is a new instance of T - until we try to add the new object to the ItemsSource collection.这一切都按预期工作 - thng 是 T 的一个新实例 - 直到我们尝试将新的 object 添加到 ItemsSource 集合中。

Since Activator.CreateInstance(Type t) returns object , it seems like we need to cast thng to T to add to the ObservableCollection<T>.由于 Activator.CreateInstance(Type t) 返回object ,看来我们需要将 thng 转换为T以添加到 ObservableCollection<T>。
We have tried various ways to convince the ItemsSource collection that thng is the correct type, but have not found one that works.我们尝试了各种方法来让 ItemsSource 集合相信 thng 是正确的类型,但还没有找到一种有效的方法。
What are we missing?我们缺少什么?
Update更新
We added a dependency variable:我们添加了一个依赖变量:

    public static readonly DependencyProperty ListObjectTypeProperty =
      DependencyProperty.Register("ListObjectType", typeof(Type), typeof(AutoCompleteComboBox));  

In xaml:在 xaml 中:

   ListObjectType="{x:Type local:SimpleClass}"

This usage of the ListObjectTypeProperty delivers the correct object, but it still is Type object : ListObjectTypeProperty 的这种用法提供了正确的 object,但它仍然是类型object

Same result doing it this way:这样做的结果相同:

   var assemName = System.Reflection.Assembly.GetExecutingAssembly().GetName().Name;

   var thng = Activator.CreateInstance(assemName, ListObjectType.FullName);
   var thng2 = thng.Unwrap();

You need to use reflection to call Add also:您还需要使用反射来调用Add

ItemsSourceClass.Things
    .GetType()
    .GetMethod(nameof(ItemsSourceClass.Things.Add))
    .Invoke(ItemsSourceClass.Things, new object[] { thng });

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM