刷新 Visual Studio 输出窗口
我有一些 C# 代码将进度消息写入 Visual Studio 2010 EnvDTE.OutputWindowPane。该代码是从 Visual Studio 菜单(位于 VSPackage 中)调用的。
问题在于,在菜单选择调用的所有处理完成之前,不会重新绘制输出窗口,因此输出会立即全部显示,而不是在添加每一行时显示。我怀疑这与主线程上执行的所有处理有关,因此 Visual Studio UI 无法重新绘制。
有没有办法在 Visual Studio 中“泵送消息”来更新 UI——比如 Application.DoEvents()? VSPackage 还在项目中插入了一些项目,这似乎是“即时”发生的——只是输出窗口看起来滞后。
我仔细研究了各种 DTE 对象,但没有找到任何适合此功能的候选对象。
I have some C# code writing progress messages to a Visual Studio 2010 EnvDTE.OutputWindowPane. The code is invoked from a Visual Studio menu (it's in a VSPackage).
The problem is that the output window is not repainted until all processing invoked by the menu pick is complete, so the output appears all at once rather than when each line is added. I suspect that this is related to all processing being performed on the main thread, so the Visual Studio UI can't repaint.
Is there a way to "pump messages" in Visual Studio to update the UI -- like Application.DoEvents()? The VSPackage also inserts some items in the project and that seems to happen "on the fly" -- it's only the output window that appears to lag behind.
I spelunked through the various DTE objects without finding any candidates for this functionality.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
很抱歉保持沉默——我只是想起了这个问题,并想我自己来回答。
通过创建一个进度条窗口,当主 Visual Studio 线程关闭运行我的代码并且不更新 UI 时出现该窗口,我能够在很大程度上解决该问题。进度条 (IVsThreadedWaitDialog2) 的记录非常少,但它似乎在工作线程上运行,并在活动时将 Visual Studio 置于模式状态。这样,至少可以防止 Visual Studio 在处理过程中看起来像是挂起的。
进度条窗口与 Visual Studio 加载大型解决方案时出现的窗口相同,并且具有“取消”按钮选项。
不幸的是,进度条对话框有几个错误(已向 Microsoft 报告),其中最重要的是它经常出现在 Visual Studio 窗口后面 - 确实很烦人。这是一种阻止程序,因此每当进度条更新时,我都会使用代码的变体 此处 通过标题定位进度窗口并将其置于 Visual Studio 窗口堆栈的顶部。
将处理转移到工作线程效果不太好,因为它执行在 Visual Studio 编辑器中操作文本的共享代码,并且这些操作的结果不稳定(有时会起作用,有时会返回一个难以理解的 COM 错误,这似乎取决于时间)。
我最终还在 Visual Studio 中找到了一个消息泵——该 shell 包含一个名为 CommonMessagePump 的类。同样,它的记录非常少,并且根据可用的信息,我永远无法让它正常工作。无论如何,进度对话框已经解决了我的问题。
Sorry for the silence -- I was just reminded of this question and thought I'd answer it myself.
I was able to largely solve the problem by creating a progress bar window that appears while the main Visual Studio thread is off running my code and not updating the UI. The progress bar (IVsThreadedWaitDialog2) is very poorly documented, but it appears to run on a worker thread and puts Visual Studio into a modal state while active. So that, at least, keeps Visual Studio from looking like it's hung during during processing.
The progress bar window is the same one that appears when Visual Studio is loading a large solution and has the option of a Cancel button.
Unfortunately, the progress bar dialog has several bugs (reported to Microsoft), the most significant of which is that it often appears behind the Visual Studio window -- truly annoying. That's kind of a show-stopper, so whenever the progress bar is updated, I use a variation of the code here to locate the progress window by its title and bring it to the top of the Visual Studio window stack.
Moving the processing to a worker thread didn't work very well, as it executes shared code that manipulates text in the Visual Studio editor, and the results of those manipulations were erratic (sometimes it would work, sometimes an inscrutable COM error was returned, which seemed to be timing-dependent).
I also did finally find a message pump in Visual Studio -- the shell contains a class called CommonMessagePump. Again, it is very poorly documented and I could never get it working quite right based on the information that was available. In any case the progress dialog has solved my problem.
就我而言,我能够在写入输出窗口后立即调用 System.Windows.Forms.Application.DoEvents() ,从而解决了问题。
In my case, I was able to call System.Windows.Forms.Application.DoEvents() immediately after writing to the output window and that solved the problem.