Windows 窗体 - 等到窗体完全绘制(绘制)

Posted

技术标签:

【中文标题】Windows 窗体 - 等到窗体完全绘制(绘制)【英文标题】:Windows forms - wait until form is completely drawn (painted) 【发布时间】:2013-05-09 22:42:57 【问题描述】:

我设计了一个唯一的目标是运行一个方法。 这是一个please wait 表单。

我给它一个代表,然后打电话给ShowDialog。 它只接受该委托并在Shown 事件中执行它。之后,Hide()

目的只是在那里告诉用户等到委托运行。

但是:它在完全显示之前开始执行委托。我的意思是,表单出现在屏幕上,但是please wait 标签被正在运行的代码卡住,显示得很晚,甚至没有显示。 (一个空的矩形留在窗体的中间)。

我可以让表单在运行委托之前等待大约两秒钟,但是在表单完全绘制并显示标签之后是否有另一种方式(更好和更可靠)调用委托???

谢谢。

【问题讨论】:

"窗体出现在屏幕上,但是请等待标签被运行代码卡住,显示很晚,甚至没有显示。(一个空的矩形留在窗体中间) 。”听起来您需要在单独的线程中执行委托,以便表单可以正确显示和更新自身。 在运行委托之前调用 this.Update()。 @Idle_Mind,单独的线程会更慢吗???这是繁重的主要代码。 您可以像 Hans 建议的那样调用 Update(),您甚至可能需要在其中添加一些 Application.DoEvents() 以允许表单自行刷新...但如果该过程“繁重” " 足以阻止表单更新,那么处理它的“正确”方法是使用后台线程。如果您想要更好的答案,请向我们展示一些代码。 代码就是这样:表单显示调用委托和隐藏。两行。 【参考方案1】:

尝试使用BackgroundWorker BackgroundWorker 组件有 4 个事件。

您需要实现其中的 2 个:DoWork 和 RunWorkerCompleted

DoWork 方法在线程中执行,是您工作的地方(或者在您的情况下,调用您的委托) 工作完成时会调用 RunWorkerCompleted,您可以在那里调用 Hide() 方法。

如果你碰巧想显示进度,你可以实现 ProgressChanged 事件,它允许你传入一个完成的百分比和一个对象(通常我会传递一个关于我正在做的事情的消息)

然后像平常一样进行绘图,然后调用后台工作人员 RunWorkerAsync 来调用它。

public class Wait : Form

    BackgroundWorker _bgWorker = new BackgroundWorker(); 
    public delegate void toExecuteDele(object args); 

    public toExecuteDele ToExecute; 

    public Wait()
    
        InitializeComponent(); 
        _bgWorker.DoWork += new DoWorkEventHandler( DoWork )
        _bgWorker.RunWorkerCompleted += new RunWorkerCompletedEventHandler (WorkDone); 
      

    public void Execute(object args)
    
         // Display Stuff (label, start a progress bar pulsing, maybe enable disable stuff 
            DispalyStuff(" Plate Wait"); 
         _bgWorker.RunBackgroundAsync(args); 
    

    private void DoWork(object sender, DoWorkEventArgs e)
    

         if( ToExecute != null )
            ToExecute(e.Argument); 

      

    public void WorkDone(object sender, RunWorkerCompletedEventArgs e)
      
        // Display an Error if there is an exception in the event args 
        Hide(); 
    

DoWork 中的一切都发生在另一个线程中,您所做的一切都在 UI 线程中运行,并且在执行时不会挂起。

【讨论】:

以上是关于Windows 窗体 - 等到窗体完全绘制(绘制)的主要内容,如果未能解决你的问题,请参考以下文章

在具有一些控件的 Windows 窗体上绘制半透明覆盖图像

在 Windows 窗体 c# 中绘制动态面板

C# windows 窗体,Line 不会绘制!画布未定义

如何在 C# windows 窗体中绘制可缩放图像

窗体背景的绘制(Windows窗体每次都会重绘其窗体背景,所以我们可以通过拦截窗体重绘背景的消息(WM_ERASEBKGND),并自定义方法来实现重绘窗体背景)

windows 窗体刷新 - 我怎样才能使它更平滑?