小R科技-WIFI机器人网·机器人创意工作室

标题: 【机器人创意工作室教程八】WIFI/蓝牙智能小车机器人操控平台双向数据引擎与功能拓展 [打印本页]

作者: liuviking    时间: 2012-11-19 23:38
标题: 【机器人创意工作室教程八】WIFI/蓝牙智能小车机器人操控平台双向数据引擎与功能拓展
本期教程分为两部分,第一部分为新的双向数据引擎V2R03的使用。第二部分应一些车友的要求,特此介绍一下如何在工作室发布的WIFI/蓝牙智能小车机器人操控平台上位机源码基础上,拓展出自己需要的指令功能。
首先说一下WIFI机器人网·机器人创意工作室上位机的源码工程下载地址:   WIFI/蓝牙智能小车机器人操控平台源工程文件
                                                                                                                  WIFI/蓝牙智能小车机器人操控平台源码API调用说明

先下载这个工程文件,解压后得到一个文件目录,同时下载该帖中的CommandEngineV2R03.rar压缩包,解压得到MainForm.cs和CommandEngine.dll文件,将MainForm.cs文件拷贝到WIFI-Robot_Code_www.wifi-robots.com\WIFI-Robot_Release\WIFIRobots\目录下,将CommandEngine.dll文件拷贝到WIFI-Robot_Code_www.wifi-robots.com\WIFI-Robot_Release\WIFIRobots\bin\Debug目录下,覆盖同名文件,这样V2R03双向数据引擎就升级成功了。
在此重点介绍一下新的引擎所增加的特性和调用方法。

新引擎的特性为:
1、数据回传采用事件驱动,精确度大幅度提升,确保与下位机进行大数据量交换时,数据的稳定与准确。
2、新增域名、IP转换接口Domain2ip(string str);该接口用于动态域名转化为IP。
3、新增调试打印接口WR_DEBUG(string Moudules, string debugstring);该接口用于在程序中加入打印,方便查看各个变量值的实时变化情况
其他接口大家一般用不着,就不再细述了。

下面逐一进行介绍:(以下代码请参考MainForm.cs文件)
1、数据回传
      之前版本的引擎在数据回传这一块精度不高,有时候有丢包现象,导致数据回传时实时性不够,或者接受不到数据,新的引擎改进了数据接收算法,使用事件驱动机制,保证一旦接收到数据,引擎立刻进行处理,将处理后的数据及时发送给用户进行处理。
使用新引擎的数据回传,需要在主程序的初始化函数MainForm_Load()中,注册数据回传的回调函数 InitDataCallBack();该函数的原型为:
  1. private void InitDataCallBack()
  2. {

  3. RobotEngine2.Setcallbackvalue += new WifiRobotCMDEngineV2.SetCallBackDataValue(DataCallBack);//注册数据回调函数
  4. }
复制代码
接下来,需要对注册的回调函数DataCallBack();进行具体的数据处理,回调函数的概念可以百度一下,相当于对函数地址的调用,这个用法非常经典,注册了回调函数之后,在引擎接收到来自下位机的数据包后,将自动调用到所注册的回调函数中,从而及时将数据传递给主进程。
DataCallBack()回调函数的实现如下:

  1. void DataCallBack(byte[] CallbackDataValue)
  2. {

  3. /*数据回传回调函数
  4. * 当有数据从下位机到达上位机后,将执行到此函数
  5. * CallbackDataValue[0]为类型位
  6. * CallbackDataValue[1]为命令位
  7. * CallbackDataValue[2]为数据位
  8. * 包头包尾已经去掉
  9. *
  10. * 协议说明
  11. * 0x03 雷达
  12. * 0x89 拍照
  13. * 0x60 电量
  14. * 0x61 湿度
  15. * 0x62 辐射
  16. * 0x63 温度
  17. *
  18. * 数据位不允许超过10,步长1
  19. *
  20. */

  21. foreach (byte b in CallbackDataValue)
  22. {
  23. builder.Append(b.ToString("X2") + " ");

  24. }
  25. DelegateUI(builder.ToString());
  26. builder.Clear();


  27. /////雷达数据开始
  28. if (CallbackDataValue[0] == 0x03)
  29. {
  30. this.Invoke((EventHandler)(delegate
  31. {

  32. try
  33. {

  34. if (Int32.Parse(CallbackDataValue[1].ToString()) == 0)//雷达数据:角度值
  35. {
  36. x_data = 0;
  37. }
  38. else
  39. {
  40. x_data = Int32.Parse(CallbackDataValue[1].ToString());
  41. }

  42. if (Int32.Parse(CallbackDataValue[2].ToString()) == 0)//雷达数据:距离值
  43. {
  44. y_data = 0;
  45. }
  46. else
  47. {
  48. y_data = Int32.Parse(CallbackDataValue[2].ToString());
  49. }

  50. RobotEngine2.WR_DEBUG("RADER", "x_data is:" + x_data.ToString() + ";++y_data is :" + y_data.ToString());

  51. }
  52. catch
  53. {
  54. x_data = 0;
  55. y_data = 0;
  56. }
  57. if (RadarStatus)
  58. {
  59. GetTarget(x_data, y_data);
  60. }

  61. }));
  62. }
  63. ////////雷达数据结束

  64. ///////自定义数据开始
  65. else if (CallbackDataValue[0] == 0x99)
  66. {
  67. //标志位为0x99
  68. //CallbackDataValue[1]即为数据内容。
  69. //请自行拓展
  70. }

  71. else
  72. {

  73. RobotEngine2.WR_DEBUG("DATACALLBACK", "+++++++DATACALLBACK NOTHING+++++++++");
  74. }

  75. }
复制代码
上面就是回调函数了,只要注册了回调函数之后,引擎收到了数据,就会调用到这个函数里面来,所以称之为“回调函数”是再适合不过的。
此函数中的CallbackDataValue数组就是来自引擎的下位机数据,CallbackDataValue这个数组的第0位为类型位,第1位为命令位,第2位为数据位,包头包尾已经被引擎过滤了,因为我们用不着~
                                      FF   (实际不存在)
CallbackDataValue[0]  类型位
CallbackDataValue[1]  命令位                                                   看看左边的图示,就可以明白了,其实和我们上位机发下去的协议是一模一样的。
CallbackDataValue[2]  数据位
                                      FF   (实际不存在)

上面的函数第一部分是雷达数据,由于我们规定雷达数据的类型位为0x03,所以可以看到,程序首先判断类型位CallbackDataValue[0] 是不是0x03,是的话继续进行接下去的解析,由于雷达数据的特殊性(有角度有距离),所以我们把命令位也当成了数据位来使用了,这里的命令位作为角度值,数据位作为距离值,并将这两组数据输出到雷达屏幕,就形成了雷达上面的亮点了。
接下去一个是个示例,当类型位为0x99的时候,执行大家自定义的动作,当然后面可以无限的拓展,看个人发挥了。
目前要注意,数据回传必须符合特定的协议 FF 类型位 命令位 数据位 FF,不然会导致回调线程异常,这样就无法继续回传数据了。下位机那边发送数据函数调用很简单,比如说需要发送FF 03 45 60 FF这个雷达数据给上位机,那么下位机那边只需要这样写:
  1. UART_send_byte(0xFF);
  2. UART_send_byte(0x03);
  3. UART_send_byte(0x45);
  4. UART_send_byte(0x60);
  5. UART_send_byte(0xFF);
复制代码
2、域名转换接口string  Domain2ip(string str);
参数:字符串类型域名/IP
返回值:字符串类型IP
该接口可以自动判断填入的参数是域名还是IP,如果是域名,则自动将其转换为对应的IP,这点在外网控制上非常重要,免去了每次开启家庭路由后都需要重新设置IP的烦恼,只需要填入动态域名即可。如果是IP,则直接交给引擎进行连接处理。

3、调试信息打印接口 void WR_DEBUG(string Modules,string debugstring);
参数1:字符串类型模块名
参数2:字符串类型调试信息
返回值:空
该接口用于打印特定的调试信息,可以在代码中任何地方加入该函数和需要打印的变量,执行到此函数后,可以在VS2010的“输出”窗口看到调试信息与打印,模块名是可以自己随便定义的。
例如:设aa变量值为12345,现在想打印aa变量的值,可以在某段代码处加入WR_DEBUG(”MAIN“,aa);执行后可以看到“输出”窗口的结果为:

[WIFI-ROBOTS]++MAIN++++++++++++++liuviking DEBUG+++++++++++++++++ 12345

新引擎还有新增许多特性,由于用户一般不需要调用,故不再多做介绍。下面介绍一下怎么在上位机源工程上拓展自己的功能。

============================简单介绍如何拓展上位机功能====================================
上位机使用C#.net语言编写,IDE为Visual Studio 2010,大家可以自行百度下载,也很好破解的。下载完成后安装,安装时C#语言必须选上,其他C++,VB,J++可以按个人爱好添加。
安装完毕之后,到下载的上位机源工程目录,可以看到WIFI-Robot.sln文件,该文件就是上位机的源工程文件,直接双击它,就可以打开整个工程。

打开工程后,直接点击VS2010的“运行”按钮,就可以跑起来了,如下图:
(, 下载次数: 193)