WPF强制重绘画布

17

在 Windows Forms 中,您可以使用.refresh()方法使元素重新绘制。在WPF中有类似的解决方案吗?

我正在画迷宫,希望能够观察迷宫的绘制过程(以便能看到进度),而不是等待28分钟后突然出现最终结果。我是用一系列Rectangle在画布上绘制方块。刷新操作应该是针对矩形还是画布?

这里是最近的一次输出:http://imgur.com/ftFOv

如果可能的话,我需要使用C#来解决问题。谢谢。

4个回答

39
这就是你要找的东西。
element.InvalidateVisual();

18

这对我起作用...

element.UpdateLayout();

12

15
这并不是100%的解决方案,但它让我朝着正确的方向开始了。最终成功的方法如下:canvas.Dispatcher.Invoke(emptyDelegate, DispatcherPriority.Render);其中emptyDelegate为Action emptyDelegate = delegate { }; - ohmusama
谢谢你今天早些时候所做的编辑,Simon。我现在正在阅读这篇文章。 - philologon
2
“使用 Dispatcher 构建更具响应性的应用程序”链接已失效。” - Bob Kaufman
1
它可以工作,但你需要浏览到2007年并点击十月。我故意没有放置精确的链接(而且它是一个CHM文件),以避免未来的链接失效。 - Simon Mourier

5

如果没有一个良好的最小化、完整和可验证的代码示例清楚地展示你正在做什么,就不可能确定这里的最佳答案。但是,从你的描述中可以看出,迷宫生成算法正在执行UI线程,阻止UI更新自身。

就像在Winforms中一样,人们试图调用Refresh()Application.DoEvents()等方法,真正的问题在于你正在阻塞UI线程。解决这个问题的正确方法是,不要那样做

有很多替代方案,但如果没有更详细的问题,就无法知道哪种方法最适合您的情况。然而,最常用且最可能适用的两种技术是使用BackgroundWorker或在Task.Run()中结合Progress<T>类。在任一情况下,您的算法在不同的线程中运行,定期向UI线程传递更新(例如每个矩形、每十个矩形等)。UI线程接收更新,将数据添加到可视化中,然后返回等待下一个更新。 BackgroundWorkerProgress<T>都提供了内置机制,可自动将数据调度回UI线程。唯一的注意事项是,无论您使用哪个类,该类的实例都需要在UI线程上创建。由于它们需要在开始执行异步工作之前设置,因此通常不会出现问题;这是免费的。
如果您以这种方式操作,就不需要任何像目前为止已经建议的三种黑客手段(其中两种似乎在“我阻塞了我的UI线程,现在怎么办?”的情况下不太可能适用)那样的东西。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接