我正在尝试编写一个Task
,它将一直运行直到被取消为止,它将读取UART接收到的所有数据,并继续通过已定义的event
分派接收到的数据。我希望读循环读取200毫秒,然后返回在该时间片中可能已读取的任何数据(可能包括零数据),或者在读取了完整的缓冲区后(以先到者为准);绝大多数情况下,超时将首先发生。我已经成功地从UART发送了数据,但是即使已经确认设备已在线上接收到数据,我也无法接收任何数据。
SerialDevice device;
// Instantiate the SerialDevice.
device.ReadTimeout = new TimeSpan( 0, 0, 0, 0, 200 );
ReadDataCancellationTokenSource = new CancellationTokenSource();
const uint BufferSize_bytes = 50;
ReadDataTask = Task.Factory.StartNew( async () =>
{
using( DataReader reader = new DataReader( device.InputStream ) )
{
reader.InputStreamOptions = InputStreamOptions.Partial;
while( !ReadDataCancellationTokenSource.IsCancellationRequested )
{
uint dataRead = await reader.LoadAsync( BufferSize_bytes ).AsTask();
if( dataRead > 0 )
{
IBuffer buffer = reader.ReadBuffer( dataRead );
if( buffer.Length > 0 )
PropogateReceivedData( ReadBuffer( buffer ) );
}
}
}
}, ReadDataCancellationTokenSource.Token );
PropogateReceivedData( ReadBuffer( buffer ) )
调用读取缓冲区中的所有数据,然后分派数据;众所周知这可以正常工作。存储ReadDataCancellationTokenSource
成员以在需要时关闭Task
。
鉴于我在尝试这种方法时遇到的挑战,我想知道它是否应该起作用,或者我是否需要做些什么才能使它起作用。
答案 0 :(得分:1)
我已成功从UART发送数据,但未能成功 即使已确认设备已接收到任何数据 线上的数据。
我不确定您如何“确认设备已从网络上收到数据”。设置InputStreamOptions.Partial
时,即使线路上只有一个字节,此行await reader.LoadAsync( BufferSize_bytes ).AsTask();
也会返回,您将在缓冲区中得到这个字节。
我也不知道如何处理PropogateReceivedData( ReadBuffer( buffer ) )
中接收到的数据,这里我使用以下几行代码将数据转换为字符串并显示在UI中,您可以参考:
var dataReader = DataReader.FromBuffer(buffer);
rcvdText.Text = dataReader.ReadString(buffer.Length);
我的建议是,如果要获取字符串数据,可以使用reader.ReadString(dataRead);
;如果要获取字节流,则可以使用reader.ReadBytes(readData);
。您可以参考DataReader来获得更多受支持的API。
鉴于我在尝试这种方法时遇到的挑战,我 想知道它是否应该工作,我需要做些什么才能得到它 工作。
是的,您的逻辑应该起作用,除了我之外,读取超时永远不会发生。您可以在设置device.ReadTimeout = new TimeSpan( 0, 0, 0, 0, 200 );
时确认读取超时对您有用吗?有超时信息吗?
以下是我从您的问题进行测试的整个代码行,对我来说很有效。
device.ReadTimeout = new TimeSpan(0, 0, 0, 0, 200);
var ReadDataCancellationTokenSource = new CancellationTokenSource();
const uint BufferSize_bytes = 50;
using (DataReader reader = new DataReader(device.InputStream))
{
reader.InputStreamOptions = InputStreamOptions.Partial;
while (!ReadDataCancellationTokenSource.IsCancellationRequested)
{
uint dataRead = await reader.LoadAsync(BufferSize_bytes).AsTask();
if (dataRead > 0)
{
IBuffer buffer = reader.ReadBuffer(dataRead);
if (buffer.Length > 0)
{
// rcvdText.Text = reader.ReadString(dataRead);
// var readData = new Byte[dataRead];
// reader.ReadBytes(readData);
var dataReader = DataReader.FromBuffer(buffer);
rcvdText.Text = dataReader.ReadString(buffer.Length);
status.Text = "bytes read successfully!";
}
}
}
}
Official serial sample您可以参考。