首页 > 解决方案 > 动态对象随处调用相关功能以扩展库 C#

问题描述

我在同一个父类“ Control ”下有不同类型的对象。我有一个List<Control>,我知道它可以引用VideoControl、HtmlControl等。它们都是“控制”。调试还显示运行时强制转换正确地将它们解析为相关的Control并且所有其他特定属性都存在。

现在这些 Control 对象包含在两个项目中,并且我知道使用 signalR 我将收到多种类型的 Control 对象的序列化列表。

我想在每个控件上调用一个Draw函数,但我的 Xamarin.Android 项目知道如何以自己的方式绘制wach 控件。

          foreach (Control control in listControls)
            {
                try
                {

                   control.Draw(this, myLayout);

                }
                catch (Exception ex)
                {
                }
            }

PS Draw 是在一个接口中定义的,所以它被强加给每个控件。我的问题是我想让所有项目自己扩展或提供功能,并用我封装的数据绘制每个控件。

我已经搜索了很多,并找到了一种可能的方法,即扩展方法,但问题是我必须进行显式类型转换,这将再次使我的代码冗长且难以处理。

为了进一步的帮助,如果可以在没有显式类型转换的情况下处理它们,我将添加我的扩展方法。

    public static void Render(this Control Player, object context, object container)
    {
    }

    public static void Render(this VideoPlayer Player, object context, object container)
    {

    }
    public static void Render(this HTMLControl Player, object context, object container)
    {
    }
    public static void Render(this Button Player, object context, object container)
    {
    }

如果我不进行类型转换,那么每次我的类型控制扩展方法都会运行,但我想为每个对象运行相关方法。

处理此问题的可能方法是一些部分实现或一些扩展方法或其他方式。

标签: c#design-patternsdynamicextension-methods

解决方案


您应该为此使用普通的 OOP 功能。你有你的控制界面:

public interface IControl
{
    void Draw();
}

和一个抽象基类:

public abstract class Control
{
    // Use abstract if you don't want to have a default
    // Draw() method in the base Control:
    public abstract void Draw();

    // Use abstract if you do want to have a default
    // Draw() method in the base Control:
    public virtual void Draw()
    {
        // basic drawing code here
    }
}

然后你有你的派生类:

public class Button : Control
{
    public override void Draw()
    {
        // custom drawing code here
    }
}

然后最后使用它:

List<IControl> controls = new List<IControl>();
controls.Add(new Button());
controls.Add(new Player());
controls.Add(new Image());

foreach (IControl control in controls)
{
    control.Draw();
}

推荐阅读