C#WinForms控制订单更改事件

时间:2022-09-02 12:35:39

I have a WinForms application with a custom "tab" concept, in that there are 3 buttons that call their respective panels "BringToFront()" method.

我有一个带有自定义“tab”概念的WinForms应用程序,因为有3个按钮可以调用它们各自的面板“BringToFront()”方法。

As these panels are all initialised when the Form is initialised, but contain separate functionality of their own, I don't want to initialise some of the more intensive tasks until that Panel has been "switched" to.

由于这些面板在表单初始化时都已初始化,但包含自己的单独功能,因此我不希望初始化一些更密集的任务,直到该面板已“切换”为止。

For example, one of my Panels has a Twitter connection functionality. If I initialise the Twitter connection on the Panel initialisation, it may fail while in theory the user is on a completely different panel/functionality.

例如,我的一个Panel具有Twitter连接功能。如果我在Panel初始化时初始化Twitter连接,它可能会失败,而理论上用户处于完全不同的面板/功能。

I only want it to try to connect to Twitter once the user has come to this panel.

一旦用户进入此面板,我只希望它尝试连接到Twitter。

So, I've been reading through MSDN but can't find an event that fires when a Controls display order has been changed.

所以,我一直在阅读MSDN,但找不到控件显示顺序发生变化时触发的事件。

I've come across these events, but not sure which/if at all, these work or are best:

我遇到过这些事件,但不确定哪些/如果有的话,这些工作或最好:

Panel.OnVisibleChanged Panel.OnEnter Panel.OnGotFocus

Panel.OnVisibleChanged Panel.OnEnter Panel.OnGotFocus

I'm still learning C#, so any help/comments is appreciated.

我还在学习C#,所以感谢任何帮助/评论。

3 个解决方案

#1


3  

I had the same problem and I fixed it by making each tab to implement an interface and trigering it whenever i try to load it (i hope that makes sense)(https://github.com/WithoutCaps/LimitlessUI/blob/master/LimitlessUI/TabsAdapter_WOC.cs)

我有同样的问题,我通过使每个选项卡实现一个接口并解决它,每当我尝试加载它时修复它(我希望这是有道理的)(https://github.com/WithoutCaps/LimitlessUI/blob/master/ LimitlessUI / TabsAdapter_WOC.cs)

lines 30/31

第30/31行

if(tab is Tab_WOC)
     ((Tab_WOC)tab).onShowTab();

feel free to use this code/library

随意使用此代码/库

NOTE: there is demo app too!

注意:还有演示应用程序!

#2


0  

This problem is a good example for back ground task. Once you feel current panel's properties are set, you can start initializing the other panels in background. Panel's tag property can be used to preserve a boolean value if its set or not. Moreover, you can hide and show the panel's rather than BringToFront. This will fire the VisibleChanged event and easy to capture and process once they are visible. This is to show you how background worker code will be.

这个问题是背景任务的一个很好的例子。一旦感觉设置了当前面板的属性,就可以开始在后台初始化其他面板。如果设置与否,Panel的tag属性可用于保留布尔值。此外,您可以隐藏和显示面板而不是BringToFront。这将触发VisibleChanged事件,并且一旦可见就很容易捕获和处理。这是为了向您展示后台工作者代码的方式。

private void BackgroundWorker1_DoWork(object sender, System.ComponentModel.DoWorkEventArgs e)
    {
        if (!Convert.ToBoolean(Panel1.Tag)) {
            //Intialize panel1
            Panel1.Tag = true;
        }
        if (!Convert.ToBoolean(Panel2.Tag)) {
            //Intialize panel2
            Panel2.Tag = true;
        }
        if (!Convert.ToBoolean(Panel3.Tag)) {
            //Intialize panel3
            Panel3.Tag = true;
        }
    }

#3


0  

Obviously I do not know how you have your project laid out but I see two options.

显然我不知道你的项目是如何布局的,但我看到了两个选择。

Option 1: Property that lazy loads

选项1:延迟加载的属性

Create a property that when you call it checks to see if a field is null and if it is, initialize it with a call to whatever expensive class constructor you want.

创建一个属性,当你调用它时检查一个字段是否为null,如果是,则通过调用你想要的任何昂贵的类构造函数来初始化它。

public TwitterCommunicator TwitterCommunicator => _twitterCommunicator ?? (_twitterCommunicator = new TwitterCommunicator());

public void AnotherTwitterPanelMethod()
{
    TwitterCommunicator.LoadTweets();
}

Option 2: Use Lazy<T>

选项2:使用Lazy

Similar to lazy loading property. Actually use Lazy which provides lazy initialization of your object when you actually want it to initialize.

与延迟加载属性类似。实际上使用Lazy,它实际上希望它初始化时提供对象的延迟初始化。

public partial class MainForm : Form
{
    public MainForm()
    {
        Lazy<TwitterCommunicator> _lazyTwitter = new Lazy<TwitterCommunicator>();
    }
}

public void SomeTwitterPanelMethod()
{
    _lazyTwitter.Value.LoadTweets();
}

#1


3  

I had the same problem and I fixed it by making each tab to implement an interface and trigering it whenever i try to load it (i hope that makes sense)(https://github.com/WithoutCaps/LimitlessUI/blob/master/LimitlessUI/TabsAdapter_WOC.cs)

我有同样的问题,我通过使每个选项卡实现一个接口并解决它,每当我尝试加载它时修复它(我希望这是有道理的)(https://github.com/WithoutCaps/LimitlessUI/blob/master/ LimitlessUI / TabsAdapter_WOC.cs)

lines 30/31

第30/31行

if(tab is Tab_WOC)
     ((Tab_WOC)tab).onShowTab();

feel free to use this code/library

随意使用此代码/库

NOTE: there is demo app too!

注意:还有演示应用程序!

#2


0  

This problem is a good example for back ground task. Once you feel current panel's properties are set, you can start initializing the other panels in background. Panel's tag property can be used to preserve a boolean value if its set or not. Moreover, you can hide and show the panel's rather than BringToFront. This will fire the VisibleChanged event and easy to capture and process once they are visible. This is to show you how background worker code will be.

这个问题是背景任务的一个很好的例子。一旦感觉设置了当前面板的属性,就可以开始在后台初始化其他面板。如果设置与否,Panel的tag属性可用于保留布尔值。此外,您可以隐藏和显示面板而不是BringToFront。这将触发VisibleChanged事件,并且一旦可见就很容易捕获和处理。这是为了向您展示后台工作者代码的方式。

private void BackgroundWorker1_DoWork(object sender, System.ComponentModel.DoWorkEventArgs e)
    {
        if (!Convert.ToBoolean(Panel1.Tag)) {
            //Intialize panel1
            Panel1.Tag = true;
        }
        if (!Convert.ToBoolean(Panel2.Tag)) {
            //Intialize panel2
            Panel2.Tag = true;
        }
        if (!Convert.ToBoolean(Panel3.Tag)) {
            //Intialize panel3
            Panel3.Tag = true;
        }
    }

#3


0  

Obviously I do not know how you have your project laid out but I see two options.

显然我不知道你的项目是如何布局的,但我看到了两个选择。

Option 1: Property that lazy loads

选项1:延迟加载的属性

Create a property that when you call it checks to see if a field is null and if it is, initialize it with a call to whatever expensive class constructor you want.

创建一个属性,当你调用它时检查一个字段是否为null,如果是,则通过调用你想要的任何昂贵的类构造函数来初始化它。

public TwitterCommunicator TwitterCommunicator => _twitterCommunicator ?? (_twitterCommunicator = new TwitterCommunicator());

public void AnotherTwitterPanelMethod()
{
    TwitterCommunicator.LoadTweets();
}

Option 2: Use Lazy<T>

选项2:使用Lazy

Similar to lazy loading property. Actually use Lazy which provides lazy initialization of your object when you actually want it to initialize.

与延迟加载属性类似。实际上使用Lazy,它实际上希望它初始化时提供对象的延迟初始化。

public partial class MainForm : Form
{
    public MainForm()
    {
        Lazy<TwitterCommunicator> _lazyTwitter = new Lazy<TwitterCommunicator>();
    }
}

public void SomeTwitterPanelMethod()
{
    _lazyTwitter.Value.LoadTweets();
}