确定组件的所有者何时已经加载了

问题描述 投票:1回答:2

我已经创建了一个WinForms应用程序,其中包含一个自定义组件,该组件需要在启动时触发一个事件,但在调用该组件的构造函数时,所有的事件处理程序仍然为空。

该组件需要在启动时触发一个事件,但是在调用该组件的构造函数时,所有的事件处理程序仍然是空的。

我需要的是一个事件,告诉我拥有该组件的窗口已经加载,并且所有的事件处理程序已经被设置。

然而,组件似乎没有 Load 事件。事实上,它们似乎根本不附带任何活动,唯一的例外是 Disposed 事件。

我的组件如何知道什么时候启动事件是安全的?

c# winforms components
2个回答
1
投票

一个可能的解决方案,是当组件被连接到监听器时触发事件。 你需要创建自己的事件属性。

class MyClass
{
    private static readonly _myEvent = new object();

    private EventHandlerList _handlers = new EventHandlerList();

    public event EventHandler MyEvent
    {
        add 
        { 
            _handlers.AddHandler(_myEvent, value); 
           OnMyEvent(); // fire the startup event
        }
        remove { _handlers.RemoveHandler(_myEvent, value); }
    }

    private void OnMyEvent()
    {
        EventHandler myEvent = _handlers[_myEvent] as EventHandler;
        if (myEvent != null) myEvent(this, EventArgs.Empty);
    }

    ...

}

0
投票

至少有2种不同的方法。第一种方法是在设计时使用Site(Site在运行时不被调用)来跟踪容器。它的工作原理是在设计时保存ContainerControl属性,这样在运行时就可以使用了。你可以在框架的一些组件的属性浏览器中看到它。

    private ContainerControl _containerControl;

    [DesignerSerializationVisibility(DesignerSerializationVisibility.Visible)]
    public ContainerControl ContainerControl
    {
        get { return _containerControl; }
        set
        {
            _containerControl = value;
            if (DesignMode || _containerControl == null)
                return;

            if (_containerControl is Form)
                ((Form) _containerControl).Load += (sender, args) => { Load(); };
            else if (_containerControl is UserControl)
                ((UserControl)_containerControl).Load += (sender, args) => { Load(); };
            else
                System.Diagnostics.Debug.WriteLine("Unknown container type. Cannot setup initialization.");
        }
    }

    [DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
    [Browsable(false)]
    public override ISite Site
    {
        get { return base.Site; }
        set
        {
            base.Site = value;
            if (value == null)
                return;

            IDesignerHost host = value.GetService(typeof(IDesignerHost)) as IDesignerHost;
            if (host == null)
                return;

            IComponent componentHost = host.RootComponent;

            if (componentHost is ContainerControl)
                ContainerControl = componentHost as ContainerControl;
        }
    }

    private void Load()
    {

    }

第二种方法是在组件中实现ISupportInitialize.在这种情况下,Visual Studio(2013)在设计时生成调用组件上ISupportInitialize方法(BeginInit和EndInit)的代码。

© www.soinside.com 2019 - 2024. All rights reserved.