Rotate the Cube Puck to invoke actions on your smartphone. Built on the Puck IOT platform.

Dependencies:   Puck MPU6050 mbed

The Cube Puck is an innovative bluetooth-enabled remote control device. It is a six-sided cube that can be rotated to any of its sides to invoke actions linked to that side. The cube puck is completely customizable and therefore also quite versatile.

A tutorial for the Cube Puck is available on GitHub.

Tutorials and in-depth documentation for the Puck platform is available at the project's GitHub page

Files at this revision

API Documentation at this revision

Comitter:
aleksanb
Date:
Thu Jul 03 11:25:12 2014 +0000
Child:
1:41b5460e2ee2
Commit message:
Initial commit.

Changed in this revision

BLE_API.lib Show annotated file Show diff for this revision Revisions of this file
MPU6050.lib Show annotated file Show diff for this revision Revisions of this file
gatt_service.cpp Show annotated file Show diff for this revision Revisions of this file
main.cpp Show annotated file Show diff for this revision Revisions of this file
mbed.bld Show annotated file Show diff for this revision Revisions of this file
nRF51822.lib Show annotated file Show diff for this revision Revisions of this file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/BLE_API.lib	Thu Jul 03 11:25:12 2014 +0000
@@ -0,0 +1,1 @@
+http://mbed.org/teams/Bluetooth-Low-Energy/code/BLE_API/#6f4c8e545d38
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/MPU6050.lib	Thu Jul 03 11:25:12 2014 +0000
@@ -0,0 +1,1 @@
+http://mbed.org/users/garfieldsg/code/MPU6050/#8162a54451b5
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/gatt_service.cpp	Thu Jul 03 11:25:12 2014 +0000
@@ -0,0 +1,22 @@
+#include "BLEDevice.h"
+
+uint8_t uuid_array_service[16]   = {'b', 'f', 't', 'j', ' ', 'c', 'u', 'b', 'e', ' ', ' ', ' ', ' ', ' ', ' ', ' ' };
+uint8_t uuid_array_direction[16] = {'b', 'f', 't', 'j', ' ', 'c', 'u', 'b', 'e', ' ', 'd', 'i', 'r', 'c', 't', 'n' };
+
+const UUID uuid_service = UUID(uuid_array_service);
+const UUID uuid_direction = UUID(uuid_array_direction);
+
+uint8_t direction_data[1] = {6};
+
+GattCharacteristic directionCharacteristic(
+        uuid_direction,
+        direction_data,
+        sizeof(direction_data),
+        sizeof(direction_data),
+        GattCharacteristic::BLE_GATT_CHAR_PROPERTIES_READ);
+        
+GattCharacteristic *characteristics[] = {&directionCharacteristic};
+GattService cube_service(uuid_service,
+        characteristics,
+        sizeof(characteristics) / sizeof(GattCharacteristic *));
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main.cpp	Thu Jul 03 11:25:12 2014 +0000
@@ -0,0 +1,182 @@
+#include "mbed.h"
+#include "BLEDevice.h"
+#include "nRF51822n.h"
+#include "MPU6050.h"
+#include <math.h> 
+
+#define DEBUG 1
+
+enum Direction {
+    UP,
+    DOWN,
+    LEFT,
+    RIGHT,
+    FRONT,
+    BACK,
+    UNDEFINED
+};
+
+Serial pc(USBTX, USBRX);
+
+BLEDevice ble;
+
+const static int16_t ACCELERATION_EXITATION_THRESHOLD = 15000;
+const static uint8_t beaconPayload[] = {
+    0x00, 0x4C, // Company identifier code (0x004C == Apple)
+    0x02,       // ID
+    0x15,       // length of the remaining payload
+    0xE2, 0x0A, 0x39, 0xF4, 0x73, 0xF5, 0x4B, 0xC4, // UUID
+    0xA1, 0x2F, 0x17, 0xD1, 0xAD, 0x07, 0xA9, 0x61,
+    0x13, 0x37, // the major value to differenciate a location
+    0xFA, 0xCE, // the minor value to differenciate a location
+    0xC8        // 2's complement of the Tx power (-56dB)
+};
+
+extern GattService cube_service;
+extern GattCharacteristic directionCharacteristic;
+extern uint8_t direction_data[1];
+
+MPU6050 mpu;
+
+int16_t ax, ay, az;
+int16_t gx, gy, gz;
+
+Direction direction = UNDEFINED;
+
+void log_direction(void)
+{
+    switch(direction)
+    {
+        case UP:
+            pc.printf("Direction UP\n");
+            break;
+            
+        case DOWN:
+            pc.printf("Direction DOWN\n");
+            break;
+            
+        case LEFT:
+            pc.printf("Direction LEFT\n");
+            break;
+            
+        case RIGHT:
+            pc.printf("Direction RIGHT\n");
+            break;
+            
+        case BACK:
+            pc.printf("Direction BACK\n");
+            break;
+            
+        case FRONT:
+            pc.printf("Direction FRONT\n");
+            break;
+            
+        default:
+            pc.printf("Direction UNSET\n");
+            break;
+    }
+}
+
+int16_t inline direction_if_exited(int16_t acceleration) {
+    if (acceleration > ACCELERATION_EXITATION_THRESHOLD) {
+        return 1;
+    } else if (acceleration < -ACCELERATION_EXITATION_THRESHOLD) {
+        return -1;
+    } else {
+        return 0;
+    }
+}
+
+void update_cube_direction(void)
+{
+    mpu.getMotion6(&ax, &ay, &az, &gx, &gy, &gz);
+    
+    int16_t x = direction_if_exited(ax);
+    int16_t y = direction_if_exited(ay);
+    int16_t z = direction_if_exited(az);
+    
+    int16_t sum = abs(x) + abs(y) + abs(z);
+    if (sum == 0 || sum != 1) {
+        return;
+    }
+    
+    if (z == 1) {
+        direction = UP;
+    } else if (z == -1) {
+        direction = DOWN;
+    } else if (y == 1) {
+        direction = LEFT;
+    } else if (y == -1) {
+        direction = RIGHT;
+    } else if (x == 1) {
+        direction = BACK;
+    } else if (x == -1) {
+        direction = FRONT;
+    }
+    
+#if DEBUG
+    log_direction();
+#endif
+}
+
+void update_direction_characteristic(void)
+{    
+    direction_data[0] = direction;
+    ble.updateCharacteristicValue(directionCharacteristic.getHandle(),
+            direction_data,
+            sizeof(direction_data));
+#if DEBUG
+    pc.printf("Updated gatt characteristic\n");
+#endif
+}
+
+void disconnectionCallback(void)
+{
+    pc.printf("Disconnected!\n");
+    pc.printf("Restarting the advertising process\n");
+    ble.startAdvertising();
+}
+
+void setup_ble(void)
+{
+    ble.init();
+    ble.onDisconnection(disconnectionCallback);
+
+    ble.accumulateAdvertisingPayload(GapAdvertisingData::BREDR_NOT_SUPPORTED);
+    ble.accumulateAdvertisingPayload(GapAdvertisingData::MANUFACTURER_SPECIFIC_DATA,
+                    beaconPayload, sizeof(beaconPayload));
+                    
+    ble.setAdvertisingType(GapAdvertisingParams::ADV_CONNECTABLE_UNDIRECTED);
+    ble.setAdvertisingInterval(160);
+
+    ble.startAdvertising();
+    
+    ble.addService(cube_service);
+    
+    pc.printf("BLE set up and running\n");
+}
+
+int main()
+{
+    setup_ble();
+    pc.printf("MPU6050 test startup:\n");
+
+    mpu.initialize();
+    pc.printf("TestConnection\n");
+    
+    if (mpu.testConnection())
+    {
+        pc.printf("MPU success\n");
+    }
+    else
+    {
+        pc.printf("MPU error\n");
+    }
+
+    while(1)
+    {
+        ble.waitForEvent();
+        update_cube_direction();
+        update_direction_characteristic();
+    }
+}
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/mbed.bld	Thu Jul 03 11:25:12 2014 +0000
@@ -0,0 +1,1 @@
+http://mbed.org/users/mbed_official/code/mbed/builds/024bf7f99721
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/nRF51822.lib	Thu Jul 03 11:25:12 2014 +0000
@@ -0,0 +1,1 @@
+http://mbed.org/teams/Nordic-Semiconductor/code/nRF51822/#7174913c9d67