问题描述
这是一个很大的不相关的code翻阅..但pretty的多发送一个数据包,并侦听数据包的回报。
如果我评论的部分在哪里,它调用ReceiveAuthPacket()方法,在发送数据包的结束,它会工作,标签会变成蓝色..但除此之外,它绝不会激活打开标签的蓝色,而是将转向标签红色或绿色(取决于返回的数据包)。
基本上我只是使用标签作为状态的指标......不管我怎么努力我不能让它变成蓝色,因为它似乎在等待着所有的code被执行完毕,并它只是将无法正常工作。
我甚至用数据试图触发WPF和它仍然是行不通的。
任何变通?我只是不明白这一点。
私人只读UdpMessageAuthentication _msgAuth;
私人无效Button_Authenticate_OnClick(对象发件人,RoutedEventArgs E)
{
Label_Authentication.Content =试图验证;
Label_Authentication.Foreground =新的SolidColorBrush(Colors.Blue);
_msgAuth.SendAuthPacket(IPAddress.Parse(TextBox_IP.Text),TextBox_ClientID.Text);
}
公共无效SendAuthPacket(ip地址IP,字符串userid)
{
_ip = IP;
_userID =用户ID;
如果(_udpClient.Client == NULL)
_udpClient =新UdpClient();
// GSISClockRegRequest,<客户ID和GT; ,, 1
弦乐味精=的String.Format(GSISClockRegRequest,{0} ,, 1,_userID);
byte []的sendBytes = Encoding.ASCII.GetBytes(MSG);
布尔发= FALSE;
尝试
{
_label.Content =试图验证;
_label.Foreground =新的SolidColorBrush(Colors.Blue);
而(_label.Content!=试图验证)
{
//循环
}
_udpClient.Connect(_ip,5001);
_udpClient.Send(sendBytes,sendBytes.Length);
Console.WriteLine(发送{0}字节消息:{1},sendBytes.Length,味精);
发送= TRUE;
}
赶上(例外)
{
Console.WriteLine(UDP数据包验证发送失败);
}
_udpClient.Close();
如果(发送)
ReceiveAuthPacket(); //如果我评论了这一点,它会工作
}
私人无效ReceiveAuthPacket()
{
IPEndPoint E =新IPEndPoint(IPAddress.Any,5001);
UdpClient U =新的UdpClient(E);
u.Client.ReceiveTimeout = 3000;
Console.WriteLine(听消息:);
尝试
{
字节[] receiveBytes = u.Receive(REF E);
字符串receiveString = Encoding.ASCII.GetString(receiveBytes);
Console.WriteLine(接收:{0},receiveString);
字符串ERRMSG =;
如果(AuthMessageParser.ParseMessage(receiveString,楼盘ERRMSG))
{
_label.Content =验证成功!;
_label.Foreground =新的SolidColorBrush(Colors.Green);
}
其他
{
_label.Content =身份验证失败:+ ERRMSG;
_label.Foreground =新的SolidColorBrush(Colors.Red);
}
}
赶上(例外)
{
_label.Content =身份验证失败;
_label.Foreground =新的SolidColorBrush(Colors.Red);
Console.WriteLine(UDP数据包验证未收到。);
}
u.Close();
}
您UI线程被阻塞通过调用像 _udpClient.Connect()
和 _udpClient.Send()
(和接收,太)
一个解决方法是利用任务并行库和异步地进行通信,以避免阻塞UI线程。
这将管理线程你,只要你正确定义的任务。奥莱如果你需要一个例子。
保护无效SomeButton_Click(对象发件人,EventArgs的)
{
//任务扫尾工作,不要等待,这里不堵。
Task.Run(PerformConnection);
}
私人异步任务PerformConnection()
{
//此方法的行为方式的线程应该。我们等待异步通讯科的结果。
//这不会阻止用户界面,但也可能会或可能不会在它自己的线程中运行。
//你不需要关心线程多。
VAR康恩=等待ListenerOrSomething.AwaitConnectionsAsync(/ * ...... * /);
//现在,你有你的结果,因为它期待已久的。
使用(VAR newClient = conn.Client())
{
VAR缓冲区=新的字节[];
VAR的recv =等待newClient.ReceiveAsyncOrSomething(出缓冲器);
//收到的数据不是零,处理它,或返回
如果(recv的大于0)
newClient.Response =等待的ProcessRequest(缓冲区);
其他
返回;
}
}
It's a lot of irrelevant code to look through.. but pretty much it sends a packet and listens for a packet in return
if i comment the part out where it calls the ReceiveAuthPacket() method at the end of sending a packet, it will work and the label will turn blue.. but otherwise it will never activate turning the label blue and will instead turn the label red or green (depending on the returned packet).
basically im just using the label as an indicator of the status.. and no matter what i try i can't get it to turn blue because it seems to be waiting for all the code to be finished executing and it just won't work..
i even tried using data triggers in WPF and it still won't work.
any work arounds? i just don't get it..
private readonly UdpMessageAuthentication _msgAuth;
private void Button_Authenticate_OnClick(object sender, RoutedEventArgs e)
{
Label_Authentication.Content = "Attempting Authentication";
Label_Authentication.Foreground = new SolidColorBrush(Colors.Blue);
_msgAuth.SendAuthPacket(IPAddress.Parse(TextBox_IP.Text), TextBox_ClientID.Text);
}
public void SendAuthPacket(IPAddress ip, string userID)
{
_ip = ip;
_userID = userID;
if (_udpClient.Client == null)
_udpClient = new UdpClient();
//GSISClockRegRequest,<Client Id>,,1
string msg = string.Format("GSISClockRegRequest,{0},,1", _userID);
byte[] sendBytes = Encoding.ASCII.GetBytes(msg);
bool sent = false;
try
{
_label.Content = "Attempting Authentication";
_label.Foreground = new SolidColorBrush(Colors.Blue);
while (_label.Content != "Attempting Authentication")
{
//loop
}
_udpClient.Connect(_ip, 5001);
_udpClient.Send(sendBytes, sendBytes.Length);
Console.WriteLine("Sending {0} bytes. Message: {1}", sendBytes.Length, msg);
sent = true;
}
catch (Exception)
{
Console.WriteLine("UDP Auth Packet Failed to Send");
}
_udpClient.Close();
if (sent)
ReceiveAuthPacket(); //IF I COMMENT THIS OUT IT'LL WORK
}
private void ReceiveAuthPacket()
{
IPEndPoint e = new IPEndPoint(IPAddress.Any, 5001);
UdpClient u = new UdpClient(e);
u.Client.ReceiveTimeout = 3000;
Console.WriteLine("Listening for Messages: ");
try
{
Byte[] receiveBytes = u.Receive(ref e);
string receiveString = Encoding.ASCII.GetString(receiveBytes);
Console.WriteLine("Received: {0}", receiveString);
string errMsg = "";
if (AuthMessageParser.ParseMessage(receiveString, ref errMsg))
{
_label.Content = "Authentication Successful!";
_label.Foreground = new SolidColorBrush(Colors.Green);
}
else
{
_label.Content = "Authentication Unsuccessful: " + errMsg;
_label.Foreground = new SolidColorBrush(Colors.Red);
}
}
catch (Exception)
{
_label.Content = "Authentication Unsuccessful";
_label.Foreground = new SolidColorBrush(Colors.Red);
Console.WriteLine("UDP Auth Packet was NOT Received.");
}
u.Close();
}
Your UI thread is blocked by calls to things like _udpClient.Connect()
and _udpClient.Send()
(and the receives, too)
A workaround would be to leverage the task parallel library and perform communications asynchronously to avoid blocking the UI thread.
It will manage threads for you as long as you define tasks properly. Holler if you need an example.
protected void SomeButton_Click(Object sender, EventArgs e)
{
// Task off the work and do not wait, no blocking here.
Task.Run(PerformConnection);
}
private async Task PerformConnection()
{
// This method acts the way a thread should. We await the result of async comms.
// This will not block the UI but also may or may not run on its own thread.
// You don't need to care about the threading much.
var conn = await ListenerOrSomething.AwaitConnectionsAsync( /* ... */ );
// Now you have your result because it awaited.
using(var newClient = conn.Client())
{
var buffer = new byte[];
var recv = await newClient.ReceiveAsyncOrSomething(out buffer);
// Data received is not zero, process it or return
if(recv > 0)
newClient.Response = await ProcessRequest(buffer);
else
return;
}
}
这篇关于标签不会改变颜色后,code执行完毕,直到的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!