我在Windows窗体中具有此功能,现在我正尝试将工作转移到WPF,
传输后,我注意到WPF不支持InvokeRequired
和BeginInvoke
。我正在寻找将函数转换为WPF的正确方法:
delegate void DisplayInvoker(string text, MessageType type);
private void DisplayinRichbox(string text, MessageType type = MessageType.Normal)
{
if (this.InvokeRequired) // not support by WPF
{
this.BeginInvoke(new DisplayInvoker(DisplayinRichbox), text, type); // Not support by WPF
return;
}
txt_Log.AppendText(String.Format("[{0}] {1}{2}\r\n",
DateTime.Now, type == MessageType.Incoming ? "<< " : type == MessageType.Outgoing ? ">> " : "", text));
txt_Log.ScrollToCaret(); // not support by WPF
}
这是我主类中的线程循环:
while (bWaiting == true)
{
//System.Windows.Forms.Application.DoEvents(); // i comment it because i cant find equivalent in WPF
System.Threading.Thread.Sleep(15);
}
最佳答案
WPF中的等价物是Dispatcher.CheckAccess和Dispatcher.BeginInvoke:
if (!this.Dispatcher.CheckAccess())
{
this.Dispatcher.BeginInvoke(new Action(() => DisplayInRichbox(text, type)));
return;
}
编辑:
RichTextBox
永不更新的原因是您阻止了UI线程: while (bWaiting == true)
{
//System.Windows.Forms.Application.DoEvents(); // i comment it because i cant find equivalent in WPF
System.Threading.Thread.Sleep(15);
}
这将阻止任何内容在UI中进行更新,因为您将其阻止,并且从不提供对其进行正确更新的方法。在旧的Win Forms代码中,您调用了
DoEvents()
,它处理了消息(但是由于许多原因,这是一个非常糟糕的主意)。没有该呼叫,它将无法正常工作。您应该尝试避免在UI线程中阻塞和循环-而是在后台线程中进行工作,并让UI线程正常运行。与TPL中的许多选项一样,
BackgroundWorker
使这一过程变得更加简单。