簡體   English   中英

C#-接收數據時的事件和委托

[英]C# - Events and delegates when receiving data

從服務器接收數據時,我想顯示一個字符串。 為此,我正在考慮使用委托和事件。 我是這個主題的新手(代表和活動),所以我無法進行設置。 這是我所做的:

public delegate void ClientHandleData(byte[] data, int bytesRead);
public event ClientHandleData OnDataReceived;

public void ConnectToServer(string ipAddress, int port)
{
    this.port = port;
    tcpClient = new TcpClient(ipAddress, port);
    clientStream = tcpClient.GetStream();

    Thread t = new Thread(new ThreadStart(ListenForData));
    started = true;
    t.Start();
}
private void ListenForData()
{
   int bytesRead;

   while (started)
   {
      bytesRead = 0;

      try
      {
          bytesRead = clientStream.Read(buffer.ReadBuffer, 0, readBufferSize);      
      }
      catch
      {
        //A socket error has occurred
        MessageBox.Show("A socket error has occurred);
        break;
      }

      if (OnDataReceived != null)
      {

                // display string to a textbox on the UI
      }

    Thread.Sleep(15);
   }

   started = false;

   Disconnect();
}

你可以寫

OnDataReceived?.Invoke(buffer.ReadBuffer, bytesRead);

如果要確保在if語句后不會將事件設置為nullif可以執行以下操作:

var handler = OnDataReceived;
handler?.Invoke(buffer.ReadBuffer, bytesRead);

更新UI時要小心,因為您只能從UI線程更新UI。 如果您使用的是WPF,則可以執行以下操作:

Dispatcher.Invoke(() => {
   // Update your UI.
});

還要確保有人確實訂閱了該活動:

public void Foo()
{
    objectWithTheEvent.OnDataReceived += OnOnDataReceived;
}

private void OnOnDataReceived(byte[] data, int count)
{

}

讓我們看看您的TcpClient偵聽代碼。 當您調用stream.Read()您無法確定將從套接字中讀取多少數據,因此您必須讀取直到流末尾,否則您必須知道應該從套接字中讀取多少日期。 讓我們假設您知道應該讀取多少數據

var readSofar = 0;
var iNeedToRead = 500;//500Bytes
try{
    while(readSoFar<iNeedToRead){
       var readFromSocket = clientStream.Read(buffer.ReadBuffer, readSofar, readBufferSize-readSofar);
       if(readFromSocket==0){
         //Remote server ended your connection or timed out etc
         //Do your error handling may be stop reading
       } 
       readSofar += readFromSocket;
    }

    }
     catch {
       //A socket error has occurred
       MessageBox.Show("A socket error has occurred);
       break;
     }
 if (OnDataReceived != null){
    // display string to a textbox on the UI
 }

您可以像這樣使用null傳播運算符。

OnDataReceived?.Invoke(buffer.ReadBuffer, bytesRead);

如果您使用的是WindowsForm,則每個控制器都必須從UI線程進行更新,因此必須從訂閱者方法中調用

private void IReceivedData(byte[] data, int count){
    this.Invoke(()=>{...Your code});
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM