假设我想创建一个直接从 UIElement 继承的类,并且能够包含一个或多个 [外部添加] UIElement s 作为子项 - 如 Panel s 和其他容器控件。让类(class)以某种形式或其他形式容纳 UIElement 的集合显然很容易,但是我如何让它们与我的类(class)一起显示/呈现?

我认为它们必须以某种方式作为我自己的 UIElement 的子项添加到可视化树中(或者,可能,通过 VisualTreeHelper.GetDrawing 手动渲染它们并使用 OnRenderDrawingContext 来完成?但这似乎很笨拙)。

我做 而不是 想知道我可以 - 或者应该 - 从更多现成的控件继承,比如 FrameworkElement , Panel , ContentControl 等(如果有的话,我想知道 他们 是如何实现外部显示/渲染的在适用的情况下添加了子元素)。

我有自己希望在层次结构中尽可能高的原因,所以请不要给我任何关于为什么 XAML/WPF 框架“兼容”等是件好事的讲座。

最佳答案

以下类在子元素的布局和呈现方面提供了绝对最小值:

public class UIElementContainer : UIElement
{
    private readonly UIElementCollection children;

    public UIElementContainer()
    {
        children = new UIElementCollection(this, null);
    }

    public void AddChild(UIElement element)
    {
        children.Add(element);
    }

    public void RemoveChild(UIElement element)
    {
        children.Remove(element);
    }

    protected override int VisualChildrenCount
    {
        get { return children.Count; }
    }

    protected override Visual GetVisualChild(int index)
    {
        return children[index];
    }

    protected override Size MeasureCore(Size availableSize)
    {
        foreach (UIElement element in children)
        {
            element.Measure(availableSize);
        }

        return new Size();
    }

    protected override void ArrangeCore(Rect finalRect)
    {
        foreach (UIElement element in children)
        {
            element.Arrange(finalRect);
        }
    }
}

不需要有 UIElementCollection。另一种实现可能如下所示:
public class UIElementContainer : UIElement
{
    private readonly List<UIElement> children = new List<UIElement>();

    public void AddChild(UIElement element)
    {
        children.Add(element);
        AddVisualChild(element);
    }

    public void RemoveChild(UIElement element)
    {
        if (children.Remove(element))
        {
            RemoveVisualChild(element);
        }
    }

    // plus the four overrides
}

关于c# - 如何创建包含(并显示)其他 UIElement 作为子项的自定义 UIElement 派生类?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/20338044/

10-12 03:34