WinForms:将父控件的引用传递给多个子控件是否是一种良好的做法?

huangapple go评论60阅读模式
英文:

WinForms: Is it a good practice to pass a reference of the parent control into multiple child controls

问题

我有以下的模式。有一个包含按钮的父表单,以及用于创建子表单的抽象基类。多个子表单,如ChildForm1ChildForm2,将在按下按钮等事件时从ParentForm中生成。这是我目前正在做的事情的简单表示。

public partial class ParentForm : Form
{
    public ParentForm()
    {
        InitializeComponent();
    }

    private void Button1_OnClick(object sender, EventArgs e)
    {
        new ChildForm1(this).Show();
    }

    // Some other methods
}

public abstract partial class BaseChildForm : Form
{
    protected readonly Form _parent;

    public BaseChildForm(Form parent)
    {
        _parent = parent;
        InitializeComponent();
    }

    private void ThisForm_OnAppear(object sender, EventArgs e)
    {
        // 通过 _parent 字段在父表单中进行一些更改
    }

    // Some other methods as well
}

public partial class ChildForm1 : BaseChildForm
{
    public ChildForm1(Form parent) : base(parent) { }

    // 覆盖的抽象方法和其他方法
    // 对父表单进行一些干预
}

public partial class ChildForm2 : BaseChildForm
{
    public ChildForm2(Form parent) : base(parent) { }

    // 覆盖的抽象方法和其他方法
    // 对父表单进行一些干预
}

在这段代码中,实际上我想在子表单中执行某些操作时访问和控制ParentForm的行为和其他属性。但正如您所见,ParentForm的公共成员完全暴露给子表单。此外,当多个ChildForm实例在给定时间内操作ParentForm时,可能会导致问题并导致意外结果。

到目前为止,这个模式对我来说“完成任务”。但我想知道是否有其他更好的方法来满足我的需求?

英文:

I have the following pattern. There is a parent form with buttons in it and an abstract base class for creating child forms. Multiple child forms like ChildForm1, ChildForm2 will be spawned from the ParentForm on events like pressing buttons etc. This is a simple representation of what I'm currently doing.

public partial class ParentForm : Form
{
    public ParentForm()
    {
        InitializeComponent();
    }

    private void Button1_OnClick(object sender, EventArgs e)
    {
        new ChildForm1(this).Show();
    }

    // Some other methods
}

public abstract partial class BaseChildForm : Form
{
    protected readonly Form _parent;

    public BaseChildForm(Form parent)
    {
        _parent = parent;
        InitializeComponent();
    }

    private void ThisForm_OnAppear(object sender, EventArgs e)
    {
        // Do some changes in the parent form through _parent field
    }

    // Some other methods as well
}

public partial class ChildForm1 : BaseChildForm
{
    public ChildForm1(Form parent) : base(parent){}

    // Overridden abstract methods and other methods
    // Do some tampering with the parent form
}

public partial class ChildForm2 : BaseChildForm
{
    public ChildForm2(Form parent) : base(parent){}

    // Overridden abstract methods and other methods
    // Do some tampering with the parent form
}

In this code, I actually want to access and control the behavior and other properties of the ParentForm when doing certain things in the child forms. But as you see the public members of the ParentForm are completely exposed to the child forms. Also, it can be an issue and cause unexpected results when multiple ChildForm instances manipulate the ParentForm at a given time.

So far, this pattern "gets things done" for me. But I wonder if there is any other better way to achieve my requirement?

答案1

得分: 4

我认为将ParentForm暴露给子窗体是一种不好的做法。你可以提取一个接口来定义ParentForm的常见操作/属性,然后在ParentForm中实现这些操作,并将接口实例注入到子窗体中,如下所示:

interface IParent
{
    int Property1 { get; set; }
    void Method1();
}

class ParentForm : Form, IParent
{
    public int Property1 { get; set; }

    public void Method1()
    {
        // 在此处实现。
    }
}

class ChildForm1 : Form
{
    private readonly IParent parent;

    public ChildForm1(IParent parent)
    {
        this.parent = parent;
    }

    // 根据需要使用 parent
}
英文:

I don't think it is a good practice to expose the ParentForm to the child forms that much. You can extract an interface for the common ParentForm operations/properties, implement them in the ParentForm and inject the interface instance to the child forms as follows:

interface IParent
{
    int Property1 { get; set; }
    void Method1();
}

class ParentForm : Form, IParent
{
    public int Property1 { get; set; }

    public void Method1()
    {
        // Implementation here.
    }
}

class ChildForm1 : Form
{
    private readonly IParent parent;

    public ChildForm1(IParent parent)
    {
        this.parent = parent;
    }

    // Use parent accordingly
}

huangapple
  • 本文由 发表于 2023年6月11日 23:59:27
  • 转载请务必保留本文链接:https://go.coder-hub.com/76451308.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定