X-NUCLEO-IKS01A1 Environmental/Motion sensors data transmitted via X-NUCLEO-IDB04A1 BLE board. Compatible with iOS/Android ST BlueMS V2.1 application.

Dependencies:   BLE_API X_NUCLEO_IDB0XA1 X_NUCLEO_IKS01A1 mbed

Fork of Bluemicrosystem1 by ST Expansion SW Team

BlueMicrosystem application

This application is the mbed equivalent of ST BlueMicrosystem1 and provides an example of motion and environmental data exported via Bluetooth Low Energy to an Android or IOS device.
It runs on a ST NUCLEO-F401RE board connected with a X-NUCLEO-IKS01A1 and a X-NUCLEO-IDB04A1 expansion boards and is compatible with Android and iOS ST BlueMS smartphone applications (based on Android and iOS BlueST SDKs).
By default the application is not providing sensor fusion and activity recognition features. However sensor fusion can be enabled following the steps below:

  • Download and install osxMotionFX library on your PC.
  • Obtain the free license for your board following the instructions
  • Copy the correct license into Middlewares/ST/STM32_OSX_MotionFX_Library/osx_license.h of your mbed program folder
  • Copy Middlewares/ST/STM32_OSX_MotionFX_Library/Inc/osx_motion_fx.h file
  • Rename the provided .lib Keil binary library giving it a .ar extension, then copy it into Middlewares/ST/STM32_OSX_MotionFX_Library/Lib of your mbed program folder
  • Enable USE_SENSOR_FUSION_LIB macro into MotionFX_Manager.h file and recompile.
Committer:
mapellil
Date:
Wed Dec 23 11:13:08 2015 +0000
Revision:
9:2693f9ef8ff7
Parent:
8:b042fe719f51
Child:
11:ff82699c696e
Update BLE API and X-NUCLEO-IDB0XA1

Who changed what in which revision?

UserRevisionLine numberNew contents of line
mapellil 9:2693f9ef8ff7 1 /**
mapellil 9:2693f9ef8ff7 2 ******************************************************************************
mapellil 9:2693f9ef8ff7 3 * @file CustomSoftawareService.h
mapellil 9:2693f9ef8ff7 4 * @author Central Labs / AST
mapellil 9:2693f9ef8ff7 5 * @version V0.9.0
mapellil 9:2693f9ef8ff7 6 * @date 23-Dec-2015
mapellil 9:2693f9ef8ff7 7 * @brief BLE 9axis sensors fusion/quaternions service
mapellil 9:2693f9ef8ff7 8 ******************************************************************************
mapellil 9:2693f9ef8ff7 9 * @attention
mapellil 9:2693f9ef8ff7 10 *
mapellil 9:2693f9ef8ff7 11 * <h2><center>&copy; COPYRIGHT(c) 2015 STMicroelectronics</center></h2>
mapellil 9:2693f9ef8ff7 12 *
mapellil 9:2693f9ef8ff7 13 * Redistribution and use in source and binary forms, with or without modification,
mapellil 9:2693f9ef8ff7 14 * are permitted provided that the following conditions are met:
mapellil 9:2693f9ef8ff7 15 * 1. Redistributions of source code must retain the above copyright notice,
mapellil 9:2693f9ef8ff7 16 * this list of conditions and the following disclaimer.
mapellil 9:2693f9ef8ff7 17 * 2. Redistributions in binary form must reproduce the above copyright notice,
mapellil 9:2693f9ef8ff7 18 * this list of conditions and the following disclaimer in the documentation
mapellil 9:2693f9ef8ff7 19 * and/or other materials provided with the distribution.
mapellil 9:2693f9ef8ff7 20 * 3. Neither the name of STMicroelectronics nor the names of its contributors
mapellil 9:2693f9ef8ff7 21 * may be used to endorse or promote products derived from this software
mapellil 9:2693f9ef8ff7 22 * without specific prior written permission.
mapellil 9:2693f9ef8ff7 23 *
mapellil 9:2693f9ef8ff7 24 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
mapellil 9:2693f9ef8ff7 25 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
mapellil 9:2693f9ef8ff7 26 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
mapellil 9:2693f9ef8ff7 27 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
mapellil 9:2693f9ef8ff7 28 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
mapellil 9:2693f9ef8ff7 29 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
mapellil 9:2693f9ef8ff7 30 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
mapellil 9:2693f9ef8ff7 31 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
mapellil 9:2693f9ef8ff7 32 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
mapellil 9:2693f9ef8ff7 33 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
mapellil 9:2693f9ef8ff7 34 *
mapellil 9:2693f9ef8ff7 35 ******************************************************************************
mapellil 9:2693f9ef8ff7 36 */
mapellil 0:e93a11b4e044 37
mapellil 0:e93a11b4e044 38 #ifndef __CUSTOM_BLE_SOFTWARE_SERVICE_H__
mapellil 0:e93a11b4e044 39 #define __CUSTOM_BLE_SOFTWARE_SERVICE_H__
mapellil 0:e93a11b4e044 40 #include "BLE.h"
mapellil 0:e93a11b4e044 41
mapellil 0:e93a11b4e044 42 #define SEND_N_QUATERNIONS 3 // The number of quaternions to be sent per BLE update (could be 1,2,3)
mapellil 0:e93a11b4e044 43
mapellil 0:e93a11b4e044 44 #if SEND_N_QUATERNIONS == 1
mapellil 0:e93a11b4e044 45 #elif SEND_N_QUATERNIONS == 2
mapellil 0:e93a11b4e044 46 #elif SEND_N_QUATERNIONS == 3
mapellil 0:e93a11b4e044 47 #else
mapellil 0:e93a11b4e044 48 #error SEND_N_QUATERNIONS could be only 1,2,3
mapellil 0:e93a11b4e044 49 #endif
mapellil 0:e93a11b4e044 50
mapellil 0:e93a11b4e044 51 #define SIZEOF_QUAT 2+2*3*SEND_N_QUATERNIONS // timestamp+sizeof(quat)*xyz*nquat
mapellil 0:e93a11b4e044 52 #define SIZEOF_FLOAT_QUAT 2+4*3
mapellil 0:e93a11b4e044 53
mapellil 9:2693f9ef8ff7 54 const LongUUIDBytes_t SOFTWARE_SERVICE_UUID_128 = { 0x00,0x00,0x00,0x00,0x00,0x02,0x11,0xe1,0x9a,0xb4,0x00,0x02,0xa5,0xd5,0xc5,0x1b };
mapellil 9:2693f9ef8ff7 55 const LongUUIDBytes_t QUATERNIONS_CHAR_UUID_128 = { 0x00,0x00,0x01,0x00,0x00,0x01,0x11,0xe1,0xac,0x36,0x00,0x02,0xa5,0xd5,0xc5,0x1b};
mapellil 9:2693f9ef8ff7 56 const LongUUIDBytes_t QUATERNIONS_FLOAT_CHAR_UUID_128 = { 0x00,0x00,0x00,0x80,0x00,0x01,0x11,0xe1,0xac,0x36,0x00,0x02,0xa5,0xd5,0xc5,0x1b};
mapellil 0:e93a11b4e044 57
mapellil 0:e93a11b4e044 58 /* Custom Software Service */
mapellil 0:e93a11b4e044 59 class CustomSoftwareService {
mapellil 0:e93a11b4e044 60 public:
mapellil 9:2693f9ef8ff7 61 CustomSoftwareService(BLE &_ble) :
mapellil 0:e93a11b4e044 62 ble(_ble),
mapellil 0:e93a11b4e044 63 swQuaternionsCharacteristic(QUATERNIONS_CHAR_UUID_128, swQuaternions, SIZEOF_QUAT, SIZEOF_QUAT,
mapellil 0:e93a11b4e044 64 GattCharacteristic::BLE_GATT_CHAR_PROPERTIES_READ | GattCharacteristic::BLE_GATT_CHAR_PROPERTIES_NOTIFY),
mapellil 0:e93a11b4e044 65 swFloatQuaternionsCharacteristic(QUATERNIONS_FLOAT_CHAR_UUID_128, swFloatQuaternions, SIZEOF_FLOAT_QUAT, SIZEOF_FLOAT_QUAT,
mapellil 0:e93a11b4e044 66 GattCharacteristic::BLE_GATT_CHAR_PROPERTIES_READ | GattCharacteristic::BLE_GATT_CHAR_PROPERTIES_NOTIFY)
mapellil 0:e93a11b4e044 67 {
mapellil 0:e93a11b4e044 68
mapellil 0:e93a11b4e044 69 static bool serviceAdded = false; /* We should only ever need to add the heart rate service once. */
mapellil 0:e93a11b4e044 70 if (serviceAdded) {
mapellil 0:e93a11b4e044 71 return;
mapellil 0:e93a11b4e044 72 }
mapellil 0:e93a11b4e044 73
mapellil 0:e93a11b4e044 74 GattCharacteristic *charTable[] = {&swQuaternionsCharacteristic, &swFloatQuaternionsCharacteristic};
mapellil 0:e93a11b4e044 75
mapellil 0:e93a11b4e044 76 GattService quaternionsService(SOFTWARE_SERVICE_UUID_128, charTable, sizeof(charTable) / sizeof(GattCharacteristic *));
mapellil 0:e93a11b4e044 77
mapellil 0:e93a11b4e044 78 ble.gattServer().addService(quaternionsService);
mapellil 0:e93a11b4e044 79
mapellil 0:e93a11b4e044 80 isEnabledQuatNotify = false;
mapellil 0:e93a11b4e044 81 isEnabledFloatQuatnotify = false;
mapellil 0:e93a11b4e044 82
mapellil 0:e93a11b4e044 83 memset (swQuaternions, 0, SIZEOF_QUAT);
mapellil 0:e93a11b4e044 84 memset (swFloatQuaternions, 0, SIZEOF_FLOAT_QUAT);
mapellil 0:e93a11b4e044 85
mapellil 0:e93a11b4e044 86 serviceAdded = true;
mapellil 0:e93a11b4e044 87 }
mapellil 0:e93a11b4e044 88
mapellil 8:b042fe719f51 89 uint32_t updateQuaternions(AxesRaw_TypeDef *data, uint16_t TimeStamp) {
mapellil 9:2693f9ef8ff7 90 if (isEnabledQuatNotify) {
mapellil 8:b042fe719f51 91 STORE_LE_16(swQuaternions ,TimeStamp);
mapellil 0:e93a11b4e044 92 #if SEND_N_QUATERNIONS == 1
mapellil 8:b042fe719f51 93 STORE_LE_16(swQuaternions+2,data[0].AXIS_X);
mapellil 8:b042fe719f51 94 STORE_LE_16(swQuaternions+4,data[0].AXIS_Y);
mapellil 8:b042fe719f51 95 STORE_LE_16(swQuaternions+6,data[0].AXIS_Z);
mapellil 0:e93a11b4e044 96 #elif SEND_N_QUATERNIONS == 2
mapellil 8:b042fe719f51 97 STORE_LE_16(swQuaternions+2,data[0].AXIS_X);
mapellil 8:b042fe719f51 98 STORE_LE_16(swQuaternions+4,data[0].AXIS_Y);
mapellil 8:b042fe719f51 99 STORE_LE_16(swQuaternions+6,data[0].AXIS_Z);
mapellil 0:e93a11b4e044 100
mapellil 8:b042fe719f51 101 STORE_LE_16(swQuaternions+8 ,data[1].AXIS_X);
mapellil 8:b042fe719f51 102 STORE_LE_16(swQuaternions+10,data[1].AXIS_Y);
mapellil 8:b042fe719f51 103 STORE_LE_16(swQuaternions+12,data[1].AXIS_Z);
mapellil 0:e93a11b4e044 104 #elif SEND_N_QUATERNIONS == 3
mapellil 8:b042fe719f51 105 STORE_LE_16(swQuaternions+2,data[0].AXIS_X);
mapellil 8:b042fe719f51 106 STORE_LE_16(swQuaternions+4,data[0].AXIS_Y);
mapellil 8:b042fe719f51 107 STORE_LE_16(swQuaternions+6,data[0].AXIS_Z);
mapellil 0:e93a11b4e044 108
mapellil 8:b042fe719f51 109 STORE_LE_16(swQuaternions+8 ,data[1].AXIS_X);
mapellil 8:b042fe719f51 110 STORE_LE_16(swQuaternions+10,data[1].AXIS_Y);
mapellil 8:b042fe719f51 111 STORE_LE_16(swQuaternions+12,data[1].AXIS_Z);
mapellil 0:e93a11b4e044 112
mapellil 8:b042fe719f51 113 STORE_LE_16(swQuaternions+14,data[2].AXIS_X);
mapellil 8:b042fe719f51 114 STORE_LE_16(swQuaternions+16,data[2].AXIS_Y);
mapellil 8:b042fe719f51 115 STORE_LE_16(swQuaternions+18,data[2].AXIS_Z);
mapellil 0:e93a11b4e044 116 #else
mapellil 0:e93a11b4e044 117 #error SEND_N_QUATERNIONS could be only 1,2,3
mapellil 0:e93a11b4e044 118 #endif
mapellil 8:b042fe719f51 119 return ble.gattServer().write(swQuaternionsCharacteristic.getValueAttribute().getHandle(), swQuaternions, SIZEOF_QUAT,0);
mapellil 9:2693f9ef8ff7 120 }
mapellil 9:2693f9ef8ff7 121 return 0;
mapellil 0:e93a11b4e044 122 }
mapellil 0:e93a11b4e044 123
mapellil 8:b042fe719f51 124 uint32_t updateFloatQuaternions(float *QuatFloat, uint16_t TimeStamp) {
mapellil 9:2693f9ef8ff7 125 if (isEnabledFloatQuatnotify){
mapellil 8:b042fe719f51 126 STORE_LE_16(swFloatQuaternions ,TimeStamp);
mapellil 8:b042fe719f51 127 STORE_LE_32(swFloatQuaternions+2 ,((uint32_t*)(QuatFloat))[0]);
mapellil 8:b042fe719f51 128 STORE_LE_32(swFloatQuaternions+6 ,((uint32_t*)(QuatFloat))[1]);
mapellil 8:b042fe719f51 129 STORE_LE_32(swFloatQuaternions+10,((uint32_t*)(QuatFloat))[2]);
mapellil 0:e93a11b4e044 130
mapellil 8:b042fe719f51 131 return ble.gattServer().write(swFloatQuaternionsCharacteristic.getValueAttribute().getHandle(), swFloatQuaternions, SIZEOF_FLOAT_QUAT,0);
mapellil 9:2693f9ef8ff7 132 }
mapellil 9:2693f9ef8ff7 133 return 0;
mapellil 0:e93a11b4e044 134 }
mapellil 0:e93a11b4e044 135
mapellil 0:e93a11b4e044 136 void enNotify (Gap::Handle_t handle) {
mapellil 0:e93a11b4e044 137 if (isQuatHandle(handle)) { isEnabledQuatNotify = true; return; }
mapellil 0:e93a11b4e044 138 if (isFloatQuatHandle(handle)) { isEnabledFloatQuatnotify = true; return; }
mapellil 0:e93a11b4e044 139 }
mapellil 0:e93a11b4e044 140
mapellil 0:e93a11b4e044 141 void disNotify (Gap::Handle_t handle) {
mapellil 0:e93a11b4e044 142 if (isQuatHandle(handle)) { isEnabledQuatNotify = false; return; }
mapellil 0:e93a11b4e044 143 if (isFloatQuatHandle(handle)) { isEnabledFloatQuatnotify = false; return; }
mapellil 0:e93a11b4e044 144 }
mapellil 0:e93a11b4e044 145
mapellil 0:e93a11b4e044 146 bool isQuatHandle (Gap::Handle_t handle) {
mapellil 0:e93a11b4e044 147 if (handle == swQuaternionsCharacteristic.getValueAttribute().getHandle()) return true;
mapellil 0:e93a11b4e044 148 return false;
mapellil 0:e93a11b4e044 149 }
mapellil 0:e93a11b4e044 150
mapellil 0:e93a11b4e044 151 bool isFloatQuatHandle (Gap::Handle_t handle) {
mapellil 0:e93a11b4e044 152 if (handle == swFloatQuaternionsCharacteristic.getValueAttribute().getHandle()) return true;
mapellil 0:e93a11b4e044 153 return false;
mapellil 0:e93a11b4e044 154 }
mapellil 0:e93a11b4e044 155
mapellil 0:e93a11b4e044 156 void updateConnectionStatus(ConnectionStatus_t status) {
mapellil 0:e93a11b4e044 157 isEnabledQuatNotify = false;
mapellil 0:e93a11b4e044 158 isEnabledFloatQuatnotify = false;
mapellil 0:e93a11b4e044 159 memset (swQuaternions, 0, SIZEOF_QUAT);
mapellil 0:e93a11b4e044 160 memset (swFloatQuaternions, 0, SIZEOF_FLOAT_QUAT);
mapellil 0:e93a11b4e044 161 }
mapellil 0:e93a11b4e044 162
mapellil 0:e93a11b4e044 163 private:
mapellil 9:2693f9ef8ff7 164 BLE &ble;
mapellil 0:e93a11b4e044 165 GattCharacteristic swQuaternionsCharacteristic;
mapellil 0:e93a11b4e044 166 GattCharacteristic swFloatQuaternionsCharacteristic;
mapellil 8:b042fe719f51 167
mapellil 9:2693f9ef8ff7 168 uint8_t swQuaternions[SIZEOF_QUAT];
mapellil 9:2693f9ef8ff7 169 uint8_t swFloatQuaternions[SIZEOF_FLOAT_QUAT];
mapellil 8:b042fe719f51 170
mapellil 9:2693f9ef8ff7 171 bool isEnabledQuatNotify;
mapellil 9:2693f9ef8ff7 172 bool isEnabledFloatQuatnotify;
mapellil 8:b042fe719f51 173
mapellil 8:b042fe719f51 174 ConnectionStatus_t isBTLEConnected;
mapellil 0:e93a11b4e044 175 };
mapellil 0:e93a11b4e044 176
mapellil 0:e93a11b4e044 177 #endif /* #ifndef __CUSTOM_BLE_CONFIG_SERVICE_H__*/