如何在uwp平台中使用反射克隆控件或uielement?

时间:2019-04-30 13:21:11

标签: c# uwp

我已经使用canvas动态创建了一个customcontrol。我需要将其转换为图像。由于画布未添加到xaml中,因此我将其添加到rootgrid并转换为图像然后将其删除。为了避免添加和删除视图时出现视觉延迟,我尝试使用反射克隆视图,但无法复制元素的所有属性。在克隆属性时会遇到Stackoverflow异常

     public static T DeepClone<T>(this T source) where T : UIElement
      {

        T result;

        // Get the type
        Type type = source.GetType();

        // Create an instance

        result = Activator.CreateInstance(type) as T;

        CopyProperties<T>(source, result, type);

        DeepCopyChildren<T>(source, result);

        return result;
    }

    private static void DeepCopyChildren<T>(T source, T result) where T : UIElement
    {
        // Deep copy children.
        Panel sourcePanel = source as Panel;
        if (sourcePanel != null)
        {
            Panel resultPanel = result as Panel;
            if (resultPanel != null)
            {
                foreach (UIElement child in sourcePanel.Children)
                {
                    // RECURSION!
                    UIElement childClone = DeepClone(child);
                    resultPanel.Children.Add(childClone);
                }
            }
        }
    }

    private static void CopyProperties<T>(T source, T result, Type type) where T : UIElement
    {
        // Copy all properties.

        IEnumerable<PropertyInfo> properties = type.GetProperties();


        foreach (var property in properties)
        {
            Type types = property.GetType();


            if (property.Name != "Name" && property.Name!="Resources"  ) // do not copy names or we cannot add the clone to the same parent as the original.
            {
                try
                {
                    if ((property.CanWrite) && (property.CanRead) )
                    {
                        object sourceProperty = property.GetValue(source,null);

                        UIElement element = sourceProperty as UIElement;
                        if (element != null)
                        {
                            UIElement propertyClone = element.DeepClone();
                            property.SetValue(result, propertyClone);
                        }
                        else
                        {

                            try
                            {
                               // if (property.GetIndexParameters().Any())
                                {
                                    MethodInfo mi = property.GetSetMethod(true);
                                    if (mi != null)
                                    {
                                        property.SetValue(result, sourceProperty, null);
                                    }
                                }
                            }
                            catch (Exception)
                            {

                            }

                        }
                    }

                }
                catch(Exception e)
                {

                }
                }
        }


    }

0 个答案:

没有答案