Light Show library for organic, calm, light display.

Dependencies:   BLE_API mbed nRF51822

Fork of mbed_blinky by Mbed

main.cpp

Committer:
nargetdev
Date:
2015-12-04
Revision:
19:fabe9521b0a1
Parent:
18:7c05ef6a639c
Child:
20:fa23847fbfef

File content as of revision 19:fabe9521b0a1:

#include "mbed.h" 
#include "BLE.h"
#include "ButtonService.h"
//#include "UARTService.h"
#include <string>

#define NEED_CONSOLE_OUTPUT 0 /* Set this if you need debug messages on the console;
                               * it will have an impact on code-size and power consumption. */

#if NEED_CONSOLE_OUTPUT
//#define DEBUG(...) { printf(__VA_ARGS__); }
#define DEBUG(STR) { if (uartServicePtr) uartServicePtr->write(STR, strlen(STR)); }
#else
#define DEBUG(...) /* nothing */
#endif /* #if NEED_CONSOLE_OUTPUT */

//#define NRFDK
#define MKIT

#define CALIBRATION_TIME 3

//#define HPI 1.571
//#define PI 3.1416
//#define HYSTERESIS_QUANTITY  PI/4
//
//#define RWAIT 0
//#define GWAIT PI/8
//#define BWAIT PI/4


//UARTService *uartServicePtr;
const static char     DEVICE_NAME[] = "Bathroom";
static const uint16_t uuid16_list[] = {ButtonService::BUTTON_SERVICE_UUID};

uint8_t motionState = 0;
ButtonService *buttonServicePtr;


unsigned long seed = 1151;

 typedef unsigned char byte;
 typedef unsigned int uint;
 
#ifdef NRFDK
InterruptIn motion(p20);
PwmOut red(p21);
PwmOut green(p22);
PwmOut blue(p23);
#endif

#ifdef MKIT
PwmOut red(p18);
PwmOut green(p19);
PwmOut blue(p20);
InterruptIn motion(p1);
#endif

// get some randomness
Timer t;

Serial pc(USBTX, USBRX); // tx, rx


BLEDevice  ble;

void disconnectionCallback(const Gap::DisconnectionCallbackParams_t *params)
{
    DEBUG("Disconnected!\n\r");
    DEBUG("Restarting the advertising process\n\r");
    ble.startAdvertising();
}



unsigned int hash(unsigned int x) {
    x = ((x >> 16) ^ x) * 0x45d9f3b;
    x = ((x >> 16) ^ x) * 0x45d9f3b;
    x = ((x >> 16) ^ x);
    seed*=2;
    seed+=17;
    return x%100;
}

void identify(unsigned int m){
    unsigned int hashable;
    float write_me;
    
    hashable = hash(m + seed);
    write_me = hashable/100.0;
    red.write(hashable >= 50);
    char* STR;
    sprintf(STR, "r, g, b: %f\t", write_me);
    DEBUG(STR);

    hashable = hash(m + seed);
    write_me = hashable/100.0;
    green.write(hashable >= 50);
    pc.printf("%f\t", write_me);
    
    hashable = hash(m + seed);
    write_me = hashable/100.0;
    blue.write(hashable >= 50);
    pc.printf("%f\n", write_me);
}
 
 void calibrate(){

  //give the sensor some time to calibrate
  pc.printf("calibrating sensor\n");
    for(int i = 0; i < CALIBRATION_TIME; i++){
      pc.printf(".");
      identify(CALIBRATION_TIME);
      wait(.5);
      }
    DEBUG(" done\n");
    DEBUG("SENSOR ACTIVE\n");
    wait(0.05);
}

void motionIRQ(){
    motionState = 1;
}

class Rgb {
private:
    // PI macros
    static const float INCREMENT = 0.00628;
    static const float HPI = 1.571;
    static const float PI = 3.1416;
    static const float HYSTERESIS_QUANTITY = PI/4;

    static const float RWAIT = 0;
    static const float GWAIT = PI/8;
    static const float BWAIT = PI/4;
    float WAIT [3];
    float SCALE [3];
    
//    static const float SCALE[3] = {
    
    // channel operators
    float rgb_c[3];
    float in;
    uint8_t rgb;
    float hysteresis;
    
    uint8_t i;
    bool mov;
    
    void random_init() {
        float rand_seed = t.read();
        pc.printf("%f\n", rand_seed);
        
        time_t seconds = time(NULL);
        printf("Time as seconds since January 1, 1970 = %d\n", seconds);
    }
    
    void update_rgb_values () {
        for (i=0; i<3; i++){
            if (!(rgb & (0x1 << i) )){
                if ( i > WAIT[i]){
                    rgb_c[i] = -cos((in - WAIT[i])*i*WAIT[i]) + 1;
                }
                else {
                    rgb_c[i] = 0.0;
                }
            }
            else
                rgb_c[i] = 0.0;
            pc.printf("%f\t",rgb_c[i]);
        }
        pc.printf("\n");
    }

void write_rgb (){
    red.write(rgb_c[0]/2.0);
    green.write(rgb_c[1]/2.0);
    blue.write(rgb_c[2]/2.0);
}
    
public:
Rgb()
{
    WAIT[0] = 1.3;
    WAIT[1] = 0.8;
    WAIT[2] = 2.1;
}


void show() {
    random_init();
    for (in = 0; in < hysteresis || rgb != 0x7; in = in + INCREMENT){
        #ifdef MKIT
            bool mov = motion;
        #else
            bool mov = !motion;
        #endif
        if (mov){
            hysteresis = in + HYSTERESIS_QUANTITY;
            pc.printf("hyst ||");
        }
        
        // update rgb
        update_rgb_values();
        
        // write values
        write_rgb();
    
        
        if (in > hysteresis){
            if (rgb_c[0] < 0.01)
                rgb |= 0x1;
            if (rgb_c[1] < 0.01)
                rgb |= 0x2;
            if (rgb_c[2] < 0.01)
                rgb |= 0x4;
        }
        
        wait(0.0001f);
        }
    }
};
//void show(){
//  float in, rout, bout, gout;
//  bool tit = true;
//
//  unsigned int rgb = 0x0;
//    pc.printf("showing...\n");
//    
//    float hysteresis = 0;
//
//  for (in = -HPI; in < hysteresis || rgb != 0x7; in = in + 0.00628)
//  {
//#ifdef MKIT
//    bool i = motion;
//#else
//    bool i = !motion;
//#endif
//    if (i){
//        hysteresis = in + HYSTERESIS_QUANTITY;
//        pc.printf("hyst ||");
//    }
//    tit = !tit;
//    if (!(rgb & 0x1)){
//        if (in < RWAIT - HPI)
//            rout = 0.0f;
//        else
//            rout = sin(in + 2.88*(in + HPI - RWAIT))     + 1.0;
//    }
//    else
//        rout = 0.0f;
//    if (!(rgb & 0x2)){
//        if (in < GWAIT - HPI)
//            gout = 0.0f;
//        else
//            gout = sin(in + 2.61*(in+HPI - GWAIT) )    + 1.0;
//    }
//    else
//        gout = 0.0f;
//    if (!(rgb & 0x4)){
//        if (in < BWAIT - HPI)
//            bout = 0.0f;
//        else
//            bout = sin(in + 3.92*(in+HPI - BWAIT) )   + 1.0;
//    }
//    else
//        bout = 0.0f;
//        
//    pc.printf("%f\t%f\t%f\n",rout,gout, bout);
//
//
//    red.write(rout/2.0);
//    green.write(gout/2.0);
//    blue.write(bout/2.0);
//    
//    if (in > hysteresis){
//        if (rout < 0.01)
//            rgb |= 0x1;
//        if (gout < 0.01)
//            rgb |= 0x2;
//        if (bout < 0.01)
//            rgb |= 0x4;
//    }
//    wait(0.0001f);
//  }
//  pc.printf("\n%X\n", rgb);
//}

void channel_check(){
    
    red.write(1.0f);
    wait(.5);
    red.write(0.0f);
    
    green.write(1.0f);
    wait(.5);
    green.write(0.0f);
    
    blue.write(1.0f);
    wait(.5);
    blue.write(0.0f);
}


    
int main() {
    // Set RTC time to Wed, 28 Oct 2009 11:35:37
    set_time(1256729737);
    
    t.start();
    red.period(0.01f);
    green.period(0.01f);
    blue.period(0.01f);
    identify(CALIBRATION_TIME);

    ble.init();
    ble.gap().onDisconnection(disconnectionCallback);

    ButtonService buttonService(ble, false /* initial value for button pressed */);
    buttonServicePtr = &buttonService;

    /* setup advertising */
    ble.gap().accumulateAdvertisingPayload(GapAdvertisingData::BREDR_NOT_SUPPORTED | GapAdvertisingData::LE_GENERAL_DISCOVERABLE);
    ble.gap().accumulateAdvertisingPayload(GapAdvertisingData::COMPLETE_LIST_16BIT_SERVICE_IDS, (uint8_t *)uuid16_list, sizeof(uuid16_list));
    ble.gap().accumulateAdvertisingPayload(GapAdvertisingData::COMPLETE_LOCAL_NAME, (uint8_t *)DEVICE_NAME, sizeof(DEVICE_NAME));
    ble.gap().setAdvertisingType(GapAdvertisingParams::ADV_CONNECTABLE_UNDIRECTED);
    ble.gap().setAdvertisingInterval(1000); /* 1000ms. */
    ble.gap().startAdvertising();
    

    Rgb strip;
    while(1){
#ifdef MKIT
        motion.rise(&motionIRQ);
        if (motionState){
            buttonServicePtr->updateButtonState(motionState);
            strip.show();
            motionState = 0;
            buttonServicePtr->updateButtonState(motionState);
            red.write(0.0f);
            green.write(0.0f);
            blue.write(0.0f);
        }
#endif
#ifdef NRFDK
        motion.fall(&strip.show());
#endif
//        red.write(0.0f);
//        green.write(0.0f);
//        blue.write(0.0f);
        ble.waitForEvent();
    }
}