Tibrv 与 wpf 冲突? (.net 3.5)
我正在尝试用 2 个测试示例在 C# 中收听 tib rv msg(使用 7.5.3):一个是纯 c# 控制台应用程序,另一个是 c# WPF 应用程序。我发现控制台应用程序工作正常,但 WPF 一段时间后停止获取消息(情况各不相同,有时在 50 条消息后,有时在 30 条后等)任何人对此有任何线索吗?
控制台应用程序代码:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using TIBCO.Rendezvous;
using System.Threading;
namespace testTibcoListener
{
class Program
{
static int count = 0;
static void Main(string[] args)
{
TIBCO.Rendezvous.Environment.Open();
TIBCO.Rendezvous.Transport aa = new NetTransport(service, network, daemon);
Connection cn = new Connection("TEST.>", aa);
cn.MessageReceived += OnDeleteOrderMessageReceived;
WaitCallback wc = (o) =>
{
while (true)
{
Queue.Default.TimedDispatch(0);
}
};
ThreadPool.QueueUserWorkItem(wc);
while (true)
{
Thread.Sleep(200);
}
}
static private void OnDeleteOrderMessageReceived(object listener, MessageReceivedEventArgs args)
{
TIBCO.Rendezvous.Message msg = args.Message;
Console.WriteLine(count);
count++;
}
}
public class Connection : IDisposable
{
private string sendSubject;
private string inbox;
private TIBCO.Rendezvous.Transport transport;
private TIBCO.Rendezvous.Listener listener;
public Connection(string sendSubject,
Transport transport)
{
this.sendSubject = sendSubject;
this.transport = transport;
this.inbox = this.transport.CreateInbox();
this.listener = new TIBCO.Rendezvous.Listener(
TIBCO.Rendezvous.Queue.Default, this.transport, this.sendSubject, null);
}
public event TIBCO.Rendezvous.MessageReceivedEventHandler MessageReceived
{
add { this.listener.MessageReceived += value; }
remove { this.listener.MessageReceived -= value; }
}
public void Send(TIBCO.Rendezvous.Message msg)
{
try
{
this.transport.Send(msg);
}
catch (Exception e)
{
Console.WriteLine(e.Message);
Console.WriteLine(e.StackTrace);
}
}
#region IDisposable Members
public void Dispose()
{
this.listener.Destroy();
}
#endregion
}
}
WPF 应用程序代码:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using TIBCO.Rendezvous;
using System.ComponentModel;
using System.Threading;
using System.Windows.Threading;
namespace WpfApplication2
{
public partial class Window1 : Window
{
public int count_;
public Window1()
{
InitializeComponent();
count_ = 0;
TIBCO.Rendezvous.Environment.Open();
TIBCO.Rendezvous.NetTransport aa = new NetTransport(service, network, daemon);
Connection cn = new Connection("TEST.>", aa, this);
cn.MessageReceived += OnDeleteOrderMessageReceived;
WaitCallback wc = (o) =>
{
while (true)
{
Queue.Default.TimedDispatch(0); //
}
};
ThreadPool.QueueUserWorkItem(wc);
}
private void OnDeleteOrderMessageReceived(object listener, MessageReceivedEventArgs args)
{
TIBCO.Rendezvous.Message msg = args.Message;
int aaa = 1111;
aaa = msg.FieldCountAsInt;
this.textBox1.Dispatcher.BeginInvoke(System.Windows.Threading.DispatcherPriority.Normal,
new DispatcherOperationCallback(delegate
{
int a = 1;// rd.Next(2);
this.count_++;
if (a == 1)
{
this.textBox1.Text = "total count: " + System.Convert.ToString(this.count_) + ",queue: " + System.Convert.ToString(Queue.Default.Count);
}
else
{
this.textBox1.Text = "11111";
a = 1;
}
return null;
}), null);
}
}
public class Connection : IDisposable
{
private string sendSubject;
private string inbox;
private TIBCO.Rendezvous.Transport transport;
private TIBCO.Rendezvous.Listener listener;
private WpfApplication2.Window1 myWindow;
public Connection(string sendSubject,
Transport transport,WpfApplication2.Window1 window)
{
this.sendSubject = sendSubject;
this.transport = transport;
this.inbox = this.transport.CreateInbox();
this.listener = new TIBCO.Rendezvous.Listener(
TIBCO.Rendezvous.Queue.Default, this.transport, this.sendSubject, null);
this.myWindow = window;
}
public event TIBCO.Rendezvous.MessageReceivedEventHandler MessageReceived
{
add { this.listener.MessageReceived += value; }
remove { this.listener.MessageReceived -= value; }
}
public void Send(TIBCO.Rendezvous.Message msg)
{
try
{
this.transport.Send(msg);
}
catch (Exception e)
{
Console.WriteLine(e.Message);
Console.WriteLine(e.StackTrace);
}
}
#region IDisposable Members
public void Dispose()
{
this.listener.Destroy();
}
#endregion
}
}
在 WPF 代码中,Queue.Default.TimedDispatch(0);是不会从队列中发送任何消息的地方。就像队列中没有消息一样。
I'm trying to listen to tib rv msg (using 7.5.3) in c# with 2 test examples: one is pure c# console app, the other is c# WPF app. What I found is the console app works fine but the WPF one stop getting msg after a while(it varies, sometime after 50 msg, sometime after 30 etc) Any1 has any clue on this?
console app code:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using TIBCO.Rendezvous;
using System.Threading;
namespace testTibcoListener
{
class Program
{
static int count = 0;
static void Main(string[] args)
{
TIBCO.Rendezvous.Environment.Open();
TIBCO.Rendezvous.Transport aa = new NetTransport(service, network, daemon);
Connection cn = new Connection("TEST.>", aa);
cn.MessageReceived += OnDeleteOrderMessageReceived;
WaitCallback wc = (o) =>
{
while (true)
{
Queue.Default.TimedDispatch(0);
}
};
ThreadPool.QueueUserWorkItem(wc);
while (true)
{
Thread.Sleep(200);
}
}
static private void OnDeleteOrderMessageReceived(object listener, MessageReceivedEventArgs args)
{
TIBCO.Rendezvous.Message msg = args.Message;
Console.WriteLine(count);
count++;
}
}
public class Connection : IDisposable
{
private string sendSubject;
private string inbox;
private TIBCO.Rendezvous.Transport transport;
private TIBCO.Rendezvous.Listener listener;
public Connection(string sendSubject,
Transport transport)
{
this.sendSubject = sendSubject;
this.transport = transport;
this.inbox = this.transport.CreateInbox();
this.listener = new TIBCO.Rendezvous.Listener(
TIBCO.Rendezvous.Queue.Default, this.transport, this.sendSubject, null);
}
public event TIBCO.Rendezvous.MessageReceivedEventHandler MessageReceived
{
add { this.listener.MessageReceived += value; }
remove { this.listener.MessageReceived -= value; }
}
public void Send(TIBCO.Rendezvous.Message msg)
{
try
{
this.transport.Send(msg);
}
catch (Exception e)
{
Console.WriteLine(e.Message);
Console.WriteLine(e.StackTrace);
}
}
#region IDisposable Members
public void Dispose()
{
this.listener.Destroy();
}
#endregion
}
}
WPF app code:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using TIBCO.Rendezvous;
using System.ComponentModel;
using System.Threading;
using System.Windows.Threading;
namespace WpfApplication2
{
public partial class Window1 : Window
{
public int count_;
public Window1()
{
InitializeComponent();
count_ = 0;
TIBCO.Rendezvous.Environment.Open();
TIBCO.Rendezvous.NetTransport aa = new NetTransport(service, network, daemon);
Connection cn = new Connection("TEST.>", aa, this);
cn.MessageReceived += OnDeleteOrderMessageReceived;
WaitCallback wc = (o) =>
{
while (true)
{
Queue.Default.TimedDispatch(0); //
}
};
ThreadPool.QueueUserWorkItem(wc);
}
private void OnDeleteOrderMessageReceived(object listener, MessageReceivedEventArgs args)
{
TIBCO.Rendezvous.Message msg = args.Message;
int aaa = 1111;
aaa = msg.FieldCountAsInt;
this.textBox1.Dispatcher.BeginInvoke(System.Windows.Threading.DispatcherPriority.Normal,
new DispatcherOperationCallback(delegate
{
int a = 1;// rd.Next(2);
this.count_++;
if (a == 1)
{
this.textBox1.Text = "total count: " + System.Convert.ToString(this.count_) + ",queue: " + System.Convert.ToString(Queue.Default.Count);
}
else
{
this.textBox1.Text = "11111";
a = 1;
}
return null;
}), null);
}
}
public class Connection : IDisposable
{
private string sendSubject;
private string inbox;
private TIBCO.Rendezvous.Transport transport;
private TIBCO.Rendezvous.Listener listener;
private WpfApplication2.Window1 myWindow;
public Connection(string sendSubject,
Transport transport,WpfApplication2.Window1 window)
{
this.sendSubject = sendSubject;
this.transport = transport;
this.inbox = this.transport.CreateInbox();
this.listener = new TIBCO.Rendezvous.Listener(
TIBCO.Rendezvous.Queue.Default, this.transport, this.sendSubject, null);
this.myWindow = window;
}
public event TIBCO.Rendezvous.MessageReceivedEventHandler MessageReceived
{
add { this.listener.MessageReceived += value; }
remove { this.listener.MessageReceived -= value; }
}
public void Send(TIBCO.Rendezvous.Message msg)
{
try
{
this.transport.Send(msg);
}
catch (Exception e)
{
Console.WriteLine(e.Message);
Console.WriteLine(e.StackTrace);
}
}
#region IDisposable Members
public void Dispose()
{
this.listener.Destroy();
}
#endregion
}
}
In WPF code, Queue.Default.TimedDispatch(0); is the place won't dispatch any msg from the queue. It's like there's no msg in the queue.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
两个建议:
1) 使用BackgroundWorker 代替ThreadPool.QueueUserWorkItem,以确保使用后台线程并且不会导致UI 线程挨饿。
2) 如果您最终在 UI 线程上运行 while 循环,请使用 WPF DoEvents 循环或仅调用 System.Windows.Forms.Application.DoEvents() 以确保消息循环运行。
Two suggestions:
1) Instead of ThreadPool.QueueUserWorkItem, use BackgroundWorker to ensure a background thread is used and you're not starving the UI thread.
2) If you do end up running your while loop on the UI thread, use a WPF DoEvents loop or just call System.Windows.Forms.Application.DoEvents() to make sure that the message loop gets run.