【问题标题】:WPF - Encapsulate custom Canvas in ScrollViewerWPF - 在 ScrollViewer 中封装自定义 Canvas
【发布时间】:2015-05-25 08:41:13
【问题描述】:

我需要一个自定义面板,它充当画布,但实际上是一个内部带有画布的 ScrollViewer。用户应该能够像在画布中一样添加控件;我需要 ScrollViewer 包装器来处理缩放和平移行为。

所以,我开始编写控件:

[ContentProperty("Children")]
public class MyContainer : ScrollViewer, IAddChild
{
    private Canvas _innerCanvas;

    [DesignerSerializationVisibility(DesignerSerializationVisibility.Content)]
    public UIElementCollection Children
    {
        get { return _innerCanvas.Children; }
    }

    public MyContainer()
    {
        this._innerCanvas = new Canvas();
        this.Content = _innerCanvas;

        _innerCanvas.Height = this.ActualHeight;
        _innerCanvas.Width = this.ActualWidth;
    }

    void IAddChild.AddChild(object value)
    {
        _innerCanvas.Children.Add(value as UIElement);
    }

    void IAddChild.AddText(string text)
    {
        ;
    }
}

但它不起作用。如果我尝试在 XAML 中使用它

<Controls:MyContainer>
    <TextBlock Height="92" Canvas.Left="324" TextWrapping="Wrap" Text="TextBlock 1" Canvas.Top="267" Width="284"/>
    <TextBlock Height="92" Canvas.Left="462" TextWrapping="Wrap" Text="TextBlock 1" Canvas.Top="267" Width="284"/>
</Controls:MyContainer>

孩子们不可见。

怎么了?

【问题讨论】:

    标签: c# wpf xaml canvas scrollviewer


    【解决方案1】:

    您在 Ctor 处将画布的大小设置为 ActualWidthActualHeight,但此时它们尚未初始化。 ActualWidthActualHeight 仅在控件出现在屏幕上时才有意义。尝试订阅 ScrollViewer 的 Loaded 事件,然后更改 Canvas 大小:

    public MyContainer()
    {
        this._innerCanvas = new Canvas();
        this.Content = _innerCanvas;
    
        this.Loaded += ScrollViewer_Loaded;
    }
    
    public void ScrollViewer_Loaded(object sender, EventArgs e)
    {
        _innerCanvas.Height = this.ActualHeight;
        _innerCanvas.Width = this.ActualWidth;
    } 
    

    【讨论】:

    • 是的,你是对的,谢谢。但是还有另一个问题。 MyContainer 控件内的控件是固定的。在 XAML 编辑器中,我无法用鼠标移动它们。
    • 我不太确定。我尽量避开设计师。只需手动更新值。无论如何,最好像这样编写 xaml,因为设计人员倾向于添加许多您不需要的额外代码,如果必须,请尝试在不同的画布中设计控件,而不是将代码复制到您的画布中.
    • 我同意你的观点,但这个控件的主要目标是通过 XAML 图形编辑器使用。你知道是什么让孩子们在容器中“可移动”吗?
    • 不。设计师真的很复杂,不是最稳定的产品。本质上,它会编译并运行您的代码并进行有意更改(例如,它会更改单击功能,因此它不会执行您的方法,而是选择设计器中的控件)。尝试使用正确的标签提出不同的问题,希望您能得到更好的答案。
    • 好的,谢谢。我会将此问题标记为已回答并尝试使用另一个适当的问题。
    猜你喜欢
    • 2010-10-31
    • 2013-03-26
    • 1970-01-01
    • 1970-01-01
    • 2014-10-20
    • 2010-10-13
    • 2017-01-03
    • 2012-05-20
    • 1970-01-01
    相关资源
    最近更新 更多