TinyDuino Bubble Level

BlueTiki TinyDuino Bubble Level
« on: May 15, 2014, 04:23:18 PM »
TinyBubble is a bubble level using the accelerometer and edge LED shields.

Code: [Select]
/*
* TinyBubble - Bubble Level
*
* Uses Accelerometer and 16 or 21-LED TinyShields
*
* Version 140515
*/

#include <Wire.h>
#include <math.h>

#define SENSITIVITY 15
#define CALIBRATION 0.0

#define BMA250_BW           0x08   // 7.81Hz

int N_LEDs;

void setup()
{
Wire.begin();

// Setup the filter bandwidth
Wire.write(0x10);
Wire.write(BMA250_BW);
Wire.endTransmission();

// Distinguish between 16 and 21 LED boards by detecting LED #21
pinMode(4, INPUT);
pinMode(9, OUTPUT);
bool led_21 = ((digitalWrite(9, HIGH), digitalRead(4)) &&
pinMode(9, INPUT);

N_LEDs = led_21 ? 21 : 16;
}

void loop()
{
static int led;
static int clock4;           // 4-bit clock
clock4 = (clock4 + 1) & 15;  // range: [0, 15]

// Read X and Y
Wire.write(0x02);
Wire.endTransmission();

int x_lsb = Wire.read();
int x_msb = Wire.read();
int y_lsb = Wire.read();
int y_msb = Wire.read();

int X = ((x_msb << 8) | x_lsb) >> 6;
int Y = ((y_msb << 8) | y_lsb) >> 6;

if (((long) X*X + (long) Y*Y) < SENSITIVITY) {
// Spin if board is level within sensitivity
if (++led > N_LEDs)
led = 1;
}
else {
// Compute angle
float angle = atan2(-X, -Y) * (10.5 / M_PI);  // range: [-10.5, 10.5]
float ramp = (clock4 - 7.5) * (1.0 / 18.75);  // range: [-0.4, 0.4]
led = angle + ramp + 19.5 + CALIBRATION;      // range: [8, 29]

if (led > 21)
led -= 21;
}

LED_on(led);
}

void LED_on(int n)
{
static uint8_t high_pin = {5, 6, 5, 7, 6, 7, 6, 8, 5, 8, 8, 7, 9, 7, 9, 8, 5, 9, 6, 9, 9};
static uint8_t low_pin  = {6, 5, 7, 5, 7, 6, 8, 6, 8, 5, 7, 8, 7, 9, 8, 9, 9, 5, 9, 6, 4};

for (int i = 4; i <= 9; i++)
pinMode(i, INPUT);

if (n >= 1 && n <= N_LEDs) {
digitalWrite(high_pin[n - 1], HIGH);
digitalWrite(low_pin [n - 1], LOW);

pinMode(high_pin[n - 1], OUTPUT);
pinMode(low_pin [n - 1], OUTPUT);
}
}

ChuckM Re: TinyDuino Bubble Level
« Reply #1 on: May 23, 2014, 12:56:33 AM »
Hi Blue, nice code! I was playing with this shield as well and noted that since the pin values are all between 4 and 9 for the LEDs you can store both the 'high' pin number and the 'low' pin number in a single byte, just store it as hex, so 0x95 is 'high' pin #9 and 'low' pin #5.  Cuts down a bit on RAM usage, which of course is unnecessary in a simple example but might come in handy if you are doing more computation or need more RAM.

--Chuck

Treverino Re: TinyDuino Bubble Level
« Reply #2 on: March 26, 2017, 12:11:55 PM »
Thank you! I really enjoyed this project.  It was only my second build with my new TinyDuino, and I have not done any programming since I took a course in PASCAL in 1981.  I had to go through and remove the "invisible characters" which were not UNICODE.  They all seemed to be embedded with the spaces in the code.  Then it worked like a charm.