在 .NET 中显示模式对话框时出现小闪烁

发布于 2024-12-01 11:23:29 字数 459 浏览 0 评论 0原文

我在 .NET Windows 窗体 应用程序中遇到了一个烦人的问题。

我有一个 MainForm (A) 和一个进度表单 (B),当我开始长时间操作时,它们会显示为模态。

当操作完成并且 B 关闭时,似乎我的应用程序后面的窗口(通常在 Skype 中出现)在几毫秒内被带到前面,然后我的应用程序正常激活。

虽然只是一点点的闪烁,但是很烦人。在这里我写了一些可以帮助找到解决方案的提示:

  • 我在没有 IWin32Window 的情况下调用了 showDialog,但我添加了它但没有成功结果。
  • 我使用 Close() 关闭了 B,然后尝试了 Hide()Close() 但没有帮助。
  • 执行 ShowDialog() 的代码是从 UI 线程调用的,因此它似乎不是线程问题。

I'm experiencing a annoying issue in my .NET Windows Forms application.

I have a MainForm (A) and a progress form (B) that is shown modal when I start a long operation.

When the operation finishes, and B is closed, it seems that the window that is behind my application (is occurs usually with Skype) is brought to front during few milliseconds and, then my application is activated normally.

Is only a small flickering, but annoying. Here I write some tips that could help to find the solution:

  • I called showDialog without IWin32Window, but I added it without success result.
  • I closed B using Close(), then I tried Hide() and then Close() but did not help.
  • The code that executes the ShowDialog() is invoked from the UI thread, so it don't seem to be a threading issue.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

哑剧 2024-12-08 11:23:29

我也经历过这些同样的症状,这让我发疯。

我终于发现问题是我调用 this.Dispose() 而不是 this.Close() 来关闭模式窗口我不知道为什么我调用 <首先是 code>this.Dispose() 。

切换方法后,问题就消失了。

我意识到这个线程很旧,这不是你的问题的原因,我只是想帮助其他犯了与我相同错误的人。

I was experiencing these same symptoms and it was driving me crazy.

I finally discovered the problem was that i was calling this.Dispose() instead of this.Close() to close the modal window I'm not sure why I called this.Dispose() in the first place.

After switching methods, the problem went away.

I realize that this thread is old and this is not the cause of your problem, i am just trying to help anyone else who made the same mistake that I did.

忱杏 2024-12-08 11:23:29

检查您是否不调用隐藏或关闭。避免闪烁的唯一方法是 DialogResult。
更新:
this.DialogResult = DialogResult.Ok

检查处理程序 OnFormClosing 等。它们可能包含错误的方法调用。

小技巧是明确设置所有者

_dialog.Owner = this;
_dialog.ShowDialog();

正在编辑帖子的人 - _dialog.ShowDialog(this) 的工作方式有点不同。
查看反编译代码中的owner = ((Control)owner).TopLevelControlInternal;

由某人编辑:

或者...

_dialog.ShowDialog(this);

根据 MSDN,这些调用是相同的

Check if you DON'T call Hide or Close. The only way to avoid flickering is DialogResult.
Upd:
this.DialogResult = DialogResult.Ok

Check handlers OnFormClosing and etc. They might containt wrong method call.

The little trick is to set Owner explicitly

_dialog.Owner = this;
_dialog.ShowDialog();

People who are editing the post - _dialog.ShowDialog(this) works a bit different.
Look at owner = ((Control) owner).TopLevelControlInternal; in decompiled code

Edited by someone:

Or...

_dialog.ShowDialog(this);

These calls are identical according to MSDN

柠檬心 2024-12-08 11:23:29
  1. 不要对模态窗口调用Close(不会被释放,保证内存泄漏)

  2. Set this.DialogResult = DialogResult.OK

  3. Call Dispose() 来自父级,切勿从您要关闭的表单

  4. 记住处置表单所持有的所有组件 < Dispose(bool) 中的 code>IContainer (Dispose(bool) 的 VS Designer 实现通常不足以避免内存泄漏)

  1. Do not call Close for modal window (it will not be disposed and memory leak is guaranteed)

  2. Set this.DialogResult = DialogResult.OK

  3. Call Dispose() from the parent, NEVER from the form you are closing

  4. Remember of disposing all of your components holding by the form IContainer in Dispose(bool) (VS Designer implementation of Dispose(bool) is usually not enough not to have memory leaks)

嗳卜坏 2024-12-08 11:23:29

就我而言,我在 VB.Net winform 应用程序中也面临着同样的问题,但情况略有不同。
我有一个用户控件,它使用 showdialog() 打开一个对话框,比如“dialog1”,在填充一些数据时,它会隐藏“dialog1”并再次使用“showdialog()”打开“dialog2”。

在隐藏dialog1和显示dialog2的过程中,会发生闪烁,并且会在后台显示窗口一段时间。

在尝试了这么多解决方案和解决方法之后,没有一个对我有用。我自己找到了一种可能对其他人有帮助的解决方法。

为了隐藏dialog1,我使用了Me.Hide(),解决方案是更改表单的不透明度,而不是调用Hide()方法。

'Me.Hide()

Me.Opacity = 0

在此解决方法之后,应用程序可以正常工作,没有任何闪烁问题。

PS:以上代码行位于 VB.Net 中,但足以让 .Net winform 应用程序开发人员了解解决此问题的想法。

In my case I was also facing the same issue in my VB.Net winform application but a bit different scenario.
I was having a user control which opens up a dialog using showdialog() say dialog1 and on filling some data it hides dialog1 and opens up dialog2 using showdialog() again.

In the process of hiding dialog1 and showing dialog2 flickering occurs and it shows the window at background for a moment.

After trying so many solutions and workarounds none work for me. I found one workaround myself which might help others.

To hide dialog1 I was using Me.Hide(), The solution is to change the opacity of form instead of calling Hide() method.

'Me.Hide()

Me.Opacity = 0

After this workaround the application works fine without any flickering issue.

PS: The above code lines are in VB.Net but enough for a .Net winform application developer to get the idea for fixing this issue.

墨落成白 2024-12-08 11:23:29

好的,
听起来像

  1. 在主窗口中用户开始长时间操作
  2. 您显示进度模式窗口
  3. 操作完成您关闭进度窗口
  4. 您的主窗口不会立即显示。相反,其背后的某些东西会显示出来一秒钟或更短的时间。
  5. 您的主窗口完成了重绘操作并且 100% 可见。
  6. 当您运行 Skype 等应用程序时,这种情况会更频繁地发生。

如果是这种情况,则可能有许多不同的原因。例如,您的视频驱动程序中可能存在错误,导致在某些条件下离屏合成出现延迟。

系统本身此时甚至可能正在经历阻塞 CPU 操作。这可能是由于代码关闭对话框并返回主窗体所需的时间造成的。您可能会查看在进度关闭和将 UI 控制权返回给用户之间是否正在执行任何其他操作。

系统可能只是内存受限,并且您的操作会导致大量交换到磁盘。当操作完成时,Windows 可能会收到通知,它需要从磁盘中提取先前交换的内存并将其推回 RAM,从而导致延迟。


我会运行该应用程序,除了任务管理器或资源监视器外,什么都没有加载,然后看看会发生什么。如果问题不再出现,请考虑向您的计算机添加更多 RAM 和/或忽略它。

如果这种情况仍然发生,并且您的内存使用量几乎所剩无几,那么请再次添加 RAM 或忽略。

如果这种情况仍然发生,但内存使用率较低,请检查您的代码,看看在关闭对话框和将主窗口的控制权释放给用户之间您正在做什么。

Okay,
it sounds like

  1. In the main window a user starts a long operation
  2. You display a progress modal window
  3. Operation completes you close the progress window
  4. Your main window doesn't display immediately. Instead something behind it shows through for a second or less.
  5. Your main window completes it's redraw operation and is 100% visible.
  6. This happens more often when you have applications such as Skype running.

If that's the case there are many different possible causes. For example, your video drivers might have a bug in them causing delays in off screen compositing under certain conditions.

The system itself might even be experiencing a blocking CPU operation at the moment. This is something that could be caused by the time it takes your code to close the dialog and go back to the main form. You might look to see if there is anything else you are doing between the time the progress closes and you return UI control back to the user.

The system might simply be memory constrained and your operation causes a huge swap to disk. When the operation completes, windows might be notified that it needs to pull previously swapped memory from disk and shove it back into RAM, causing a delay.


I'd run the app with Nothing else loaded but task manager or resource monitor and see what happens. If the problem no longer occurs, then look into adding more RAM to your machine and/or ignore it.

If it's still occuring, and your memory usage leaves nearly nothing left then, again, add RAM or ignore.

If it's still occuring but memory usage is low, investigate your code to see what you are doing between the closing of the dialog and release of control of the main window back to the user.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文