【CC2640R2F】香瓜CC2640R2F之从机通信状态的显示

 本文最后修改时间:2017年11月27日 12:00

 

一、本节简介

本节以simple_peripheral工程为例,介绍如何添加从机通信状态的显示,如显示“Advertising”、“Connected”等状态。


二、实验平台

1)CC2640R2F平台

①协议栈版本:CC2640R2 SDK v1.40.00.45

②编译软件:CCS7.3.0.00019

③硬件平台:香瓜CC2640R2F开发板

④仿真器:香瓜XDS100V3下载器

2)手机平台
①手机型号:红米1S
②安卓版本:安卓4.3
③安卓app:BLE Reader


三、版权声明

1)作者:甜甜的大香瓜

2)声明:喝水不忘挖井人,转载请注明出处。

3)纠错/业务合作:[email protected]

4)香瓜BLE之CC2640R2F群:557278427

5)本文出处:原创连载资料《简单粗暴学蓝牙5》

6)完整开源资料下载地址(电脑端打开):

https://shop217632629.taobao.com/?spm=2013.1.1000126.d21.hd2o8i

7)香瓜CC2640R2F开发板购买链接:

https://item.taobao.com/item.htm?spm=a1z10.1-c-s.w4023-16963296339.8.21bfc58419sWKt&id=558653143169

8)香瓜XDS100V3下载器购买链接:

https://item.taobao.com/item.htm?spm=a230r.1.14.1.1d150040zvJBco&id=558356989143&ns=1&abbucket=6#detail


四、实验前提

1、在进行本文步骤前,请先阅读以下章节:

1)《简单粗暴学蓝牙5》的“第一章至第四章”章节​。


2、在进行本文步骤前,请先实现以下章节:

1)《简单粗暴学蓝牙5》的“第三章 软件的安装及使用”章节。

2)《简单粗暴学蓝牙5》的《香瓜CC2640R2F之LCD》:http://blog.csdn.net/feilusia/article/details/78371371


五、基础知识

1、从机通信状态是指什么?
答:
在peripheral.h中有介绍

/// @brief GAP Peripheral Role States.
typedef enum
{
  GAPROLE_INIT = 0,                       //!< Waiting to be started
  GAPROLE_STARTED,                        //!< Started but not advertising
  GAPROLE_ADVERTISING,                    //!< Currently Advertising
  GAPROLE_ADVERTISING_NONCONN,            //!< Currently using non-connectable Advertising
  GAPROLE_WAITING,                        //!< Device is started but not advertising, is in waiting period before advertising again
  GAPROLE_WAITING_AFTER_TIMEOUT,          //!< Device just timed out from a connection but is not yet advertising, is in waiting period before advertising again
  GAPROLE_CONNECTED,                      //!< In a connection
  GAPROLE_CONNECTED_ADV,                  //!< In a connection + advertising
  GAPROLE_ERROR                           //!< Error occurred - invalid state
} gaprole_States_t;
其中,我们最关心的是如下几种状态:

1)GAPROLE_STARTED:表明蓝牙初始化结束,此时可以显示本机的mac地址、显示"Initialized"。

2)GAPROLE_ADVERTISING:表明当前蓝牙已在广播,此时显示"Advertising"。

3)GAPROLE_CONNECTED:表明当前已被主机连接上了,此时显示“Connected”。

4)GAPROLE_WAITING:表明当前已与主机断开连接,比如主机主动断开、强行关闭手机的蓝牙app、强行关闭手机的蓝牙开关、强行手机关机,此时显示"Disconnected"。


2、为何要为这些状态增加显示?

答:

有了通信状态显示,可以更直观地知道设备运行的状态。是很实用的功能。


六、硬件原理

暂无


七、实验步骤

1、修改状态回调函数(替换simple_peripheral.c的SimpleBLEPeripheral_processStateChangeEvt函数)

static void SimpleBLEPeripheral_processStateChangeEvt(gaprole_States_t newState)
{
#ifdef PLUS_BROADCASTER
  static bool firstConnFlag = false;
#endif // PLUS_BROADCASTER

  //蓝牙状态
  switch ( newState )
  {
    //蓝牙初始化好时
    case GAPROLE_STARTED:
      {
        uint8_t ownAddress[B_ADDR_LEN];
        uint8_t systemId[DEVINFO_SYSTEM_ID_LEN];

        //获取本设备的8字节mac地址
        GAPRole_GetParameter(GAPROLE_BD_ADDR, ownAddress);

        //将8字节mac地址转为6字节系统ID
        // use 6 bytes of device address for 8 bytes of system ID value
        systemId[0] = ownAddress[0];
        systemId[1] = ownAddress[1];
        systemId[2] = ownAddress[2];

        // set middle bytes to zero
        systemId[4] = 0x00;
        systemId[3] = 0x00;

        // shift three bytes up
        systemId[7] = ownAddress[5];
        systemId[6] = ownAddress[4];
        systemId[5] = ownAddress[3];

        //保存系统ID
        DevInfo_SetParameter(DEVINFO_SYSTEM_ID, DEVINFO_SYSTEM_ID_LEN, systemId);

        //显示(协议栈原显示驱动未用,使用香瓜的显示驱动)
        // Display device address
        Display_print0(dispHandle, SBP_ROW_BDADDR, 0, Util_convertBdAddr2Str(ownAddress));
        Display_print0(dispHandle, SBP_ROW_ROLESTATE, 0, "Initialized");

        //GUA
        GUA_LCD_WriteString(Util_convertBdAddr2Str(ownAddress), GUA_LCD_LINE4);
        GUA_LCD_WriteString("Initialized", GUA_LCD_LINE5);
        //GUA
      }
      break;

    //开始广播时
    case GAPROLE_ADVERTISING:
      Display_print0(dispHandle, SBP_ROW_ROLESTATE, 0, "Advertising");
      //GUA
      GUA_LCD_WriteString("Advertising", GUA_LCD_LINE5);
      //GUA
      break;

#ifdef PLUS_BROADCASTER
    // After a connection is dropped, a device in PLUS_BROADCASTER will continue
    // sending non-connectable advertisements and shall send this change of
    // state to the application.  These are then disabled here so that sending
    // connectable advertisements can resume.
    case GAPROLE_ADVERTISING_NONCONN:
      {
        uint8_t advertEnabled = FALSE;

        // Disable non-connectable advertising.
        GAPRole_SetParameter(GAPROLE_ADV_NONCONN_ENABLED, sizeof(uint8_t),
                           &advertEnabled);

        advertEnabled = TRUE;

        // Enabled connectable advertising.
        GAPRole_SetParameter(GAPROLE_ADVERT_ENABLED, sizeof(uint8_t),
                             &advertEnabled);

        // Reset flag for next connection.
        firstConnFlag = false;

        SimpleBLEPeripheral_freeAttRsp(bleNotConnected);
      }
      break;
#endif //PLUS_BROADCASTER

    //连接时
    case GAPROLE_CONNECTED:
      {
        linkDBInfo_t linkInfo;
        uint8_t numActive = 0;

        //开启周期事件
        Util_startClock(&periodicClock);

        //获取已连接设备总数
        numActive = linkDB_NumActive();

        // Use numActive to determine the connection handle of the last
        // connection
        //提取到了设备信息,则说明之前已有连接设备,则显示已连接设备总数、显示此刻连接上的主机地址
        if ( linkDB_GetInfo( numActive - 1, &linkInfo ) == SUCCESS )
        {
          Display_print1(dispHandle, SBP_ROW_ROLESTATE, 0, "Num Conns: %d", (uint16_t)numActive);
          Display_print0(dispHandle, SBP_ROW_STATUS_1, 0, Util_convertBdAddr2Str(linkInfo.addr));

          //GUA
          GUA_LCD_WriteStringValue("Num Conns:", (uint16_t)numActive, 10, GUA_LCD_LINE5);           //显示当前连接数
          GUA_LCD_WriteString(Util_convertBdAddr2Str(linkInfo.addr), GUA_LCD_LINE6);                //显示最后连接的主机地址
          //GUA
        }
        //提取不到设备信息,则说明之前没有已连接设备,则显示此刻的设备已连接、显示此刻连接上的主机地址
        else
        {
          uint8_t peerAddress[B_ADDR_LEN];

          GAPRole_GetParameter(GAPROLE_CONN_BD_ADDR, peerAddress);

          Display_print0(dispHandle, SBP_ROW_ROLESTATE, 0, "Connected");
          Display_print0(dispHandle, SBP_ROW_STATUS_1, 0, Util_convertBdAddr2Str(peerAddress));

          //GUA
          GUA_LCD_WriteString("Connected", GUA_LCD_LINE5);                                          //显示为已连接
          GUA_LCD_WriteString(Util_convertBdAddr2Str(peerAddress), GUA_LCD_LINE6);                  //显示当前连接的主机地址
          //GUA
        }

#if !defined(Display_DISABLE_ALL)
        tbm_setItemStatus(&sbpMenuMain, TBM_ITEM_ALL, TBM_ITEM_NONE);
#endif  // !Display_DISABLE_ALL

        #ifdef PLUS_BROADCASTER
          // Only turn advertising on for this state when we first connect
          // otherwise, when we go from connected_advertising back to this state
          // we will be turning advertising back on.
          if (firstConnFlag == false)
          {
            uint8_t advertEnabled = FALSE; // Turn on Advertising

            // Disable connectable advertising.
            GAPRole_SetParameter(GAPROLE_ADVERT_ENABLED, sizeof(uint8_t),
                                 &advertEnabled);

            // Set to true for non-connectable advertising.
            advertEnabled = TRUE;

            // Enable non-connectable advertising.
            GAPRole_SetParameter(GAPROLE_ADV_NONCONN_ENABLED, sizeof(uint8_t),
                                 &advertEnabled);
            firstConnFlag = true;
          }
        #endif // PLUS_BROADCASTER
      }
      break;

    //连接时广播
    case GAPROLE_CONNECTED_ADV:
      Display_print0(dispHandle, SBP_ROW_ROLESTATE, 0, "Connected Advertising");
      //GUA
      GUA_LCD_WriteString("Connected Advertising", GUA_LCD_LINE5);
      //GUA
      break;

    //设备启动了但是没有广播出来,等待下一次广播
    case GAPROLE_WAITING:
      Util_stopClock(&periodicClock);
      SimpleBLEPeripheral_freeAttRsp(bleNotConnected);

      Display_print0(dispHandle, SBP_ROW_ROLESTATE, 0, "Disconnected");

#if !defined(Display_DISABLE_ALL)
      // Disable PHY change
      tbm_setItemStatus(&sbpMenuMain, TBM_ITEM_NONE, TBM_ITEM_ALL);
#endif  // !Display_DISABLE_ALL

      // Clear remaining lines
      Display_clearLines(dispHandle, SBP_ROW_RESULT, SBP_ROW_STATUS_2);

      //GUA
      GUA_LCD_WriteString("Disconnected", GUA_LCD_LINE5);
      GUA_LCD_ClearLine(GUA_LCD_LINE6);
      //GUA

      break;

    //等待超时
    case GAPROLE_WAITING_AFTER_TIMEOUT:
      SimpleBLEPeripheral_freeAttRsp(bleNotConnected);

      Display_print0(dispHandle, SBP_ROW_RESULT, 0, "Timed Out");

#if !defined(Display_DISABLE_ALL)
      tbm_setItemStatus(&sbpMenuMain, TBM_ITEM_NONE, TBM_ITEM_ALL);
#endif  // !Display_DISABLE_ALL

      // Clear remaining lines
      Display_clearLines(dispHandle, SBP_ROW_STATUS_1, SBP_ROW_STATUS_2);

      //GUA
      GUA_LCD_WriteString("Timed Out", GUA_LCD_LINE5);
      GUA_LCD_ClearLine(GUA_LCD_LINE6);
      //GUA

      #ifdef PLUS_BROADCASTER
        // Reset flag for next connection.
        firstConnFlag = false;
      #endif // PLUS_BROADCASTER
      break;

    //异常状态时
    case GAPROLE_ERROR:
      Display_print0(dispHandle, SBP_ROW_RESULT, 0, "Error");
      //GUA
      GUA_LCD_WriteString("Error", GUA_LCD_LINE5);
      //GUA
      break;

    default:
      Display_clearLines(dispHandle, SBP_ROW_RESULT, SBP_ROW_STATUS_2);
      //GUA
      GUA_LCD_ClearLine(GUA_LCD_LINE6);
      //GUA
      break;
  }

}
增加了oled显示、增加了部分注释。

八、注意事项
暂无


九、实验结果
仿真并全速运行,可以看到:

1、上电后自动广播的显示

【CC2640R2F】香瓜CC2640R2F之从机通信状态的显示_第1张图片

2、连接后的显示

【CC2640R2F】香瓜CC2640R2F之从机通信状态的显示_第2张图片


注:由于断开连接等状态显示的时间过短,会快速地被重新广播刷新掉,所以其他状态只有仿真设置断点时能看到。

因此,实验成功。





你可能感兴趣的:(BLE-CC2640R2F)