创建一个用于存储额外信息并将其链接到主机类的类

时间:2011-03-14 14:05:22

标签: c# wpf inheritance

所以我一直试图找出解决这个问题的最佳方法,但最终还是会碰到某个墙壁。

基本上,我的问题是这样的:我有一个可以绘制UIElement类型的项目的图层。在我的例子中,我需要能够绘制两种类型的图像和形状的UIElements。它们都是从UIElement继承而来的。

现在我想创建一个自己的类,让我们调用一个LayerItem类。 LayerItem包含有关特定项的一些其他信息,例如名称。

我的第一个解决方案是从Image-class继承LayerItem并添加新字段。这样我就能够捕获Image-object接收的所有事件(例如MouseOver),然后将对象强制转换为LayerItem以检索额外的相关信息。显示图像是通过设置对象的Source-property来完成的。

但是,如果对象也可以是形状,则此方法不起作用,因为形状没有Source属性。

基本上我正在寻找的是“正确的方法”来实现这一点,以一种允许我直接使用事件的方式。我目前唯一能提出的解决方案是使用字典将UIElements映射到LayerItems,然后通过使用其事件被引发的UIElement从那里获取LayerItem。那么,是否有一些更好,也许更复杂的方法来实现这一目标?

修改

感谢您的回复,但我不确定这正是我要找的。让我试着澄清一下。基本上,我有一个图层,我可以通过将有问题的图形添加到图层并给它坐标来绘制不同的东西(图像或形状)。

这个想法是用户可以点击图层并从一个列表中选择他/她想要用来表示添加项目的图形。有关该项目的额外信息(如id和name)存储在数据库中,我需要一种方法将此信息链接到图形项目。

所以这一切都将由代码处理,项目是动态创建和删除的。这也是事件的来源。为了能够识别用户点击的项目(显示额外信息,允许拖放等),我认为UIElement生成的事件最容易使用。 / p>

关于提供代码作为一个例子,这有点难,因为它在很大程度上取决于实现:)但是如果我的解释仍然不够明确,我当然可以试着提出一些建议!

2 个答案:

答案 0 :(得分:0)

似乎您可以使用attached properties来存储您的图层所需的额外信息。

如何使用它的一个很好的例子是在msdn页面上。

<DockPanel>
  <CheckBox DockPanel.Dock="Top">Hello</CheckBox>
</DockPanel>

Checkbox未定义Dock属性,DockPanel。现在,任何元素都可以设置Dock属性。

答案 1 :(得分:0)

我首先创建一个UIElement的LayerItem后代,然后创建所有其他所需的类LayerItem的后代。最终的层次结构如下所示:

  • 的UIElement
    • LayerItem
      • ImageLayerItem
      • ShapeLayerItem

并且,如果您希望LayerItem报告来自子类的任何事件,那么只需在LayerItem中使用该事件,并让子类在其自己的事件上引发该事件,如下所示:

class LayerItem
{
    public string Name { get; set; }

    public event EventHandler ItemEvent;
    protected virtual void OnItemEvent(EventArgs e)
    {
    if (this.ItemEvent != null)
        this.ItemEvent(this, e);
    }
}

class ImageLayerItem : LayerItem
{
    private Image _image;

    public ImageLayerItem()
    {
        //here create Image element and think of rendering it.
        _image = new Image();
        //attach event handlers.
        _image.Click += ... //don't forget to call LayerItem.OnItemEvent() inside the event handler.
    }
}

此外:

  • 我建议在LayerItem中使用特殊的事件处理程序类型和相应的特殊事件参数类型,而不仅仅是EventHandler和EventArgs。一个很好的例子是LayerItemEventArgs,它包含由其中一个子类(如ImageLayerItem)及其参数引发的事件名称。这样,您只需处理LayerItem.ItemEvent事件即可处理所有事件;或者您可以将子类的事件作为经典方法处理。

我希望这有助于成为一个良好的开端。