Posts with «led» label

Optical pulse monitor with little electronics

In yesterday’s blog post, I talked mainly about what my son did with his time yesterday, to mention the small amount of debugging help I gave him.  Today I’ll post about what I did with most of my time yesterday.

This year, I am hoping to lead a 2-unit freshman design seminar for bioengineering students.  (Note: I did not say “teach” here, as I’m envisioning more of a mentoring role than a specific series of exercises.)  One thing I’m doing is trying to come up with design projects that freshmen with essentially no engineering skills can do as a team.  They may have to learn something new (I certainly hope they do!), but they should only spend a total of 60 hours on the course, including class time.  Since I want to spend some of class time on lab tours, lab safety, using the library resources, and how to work in a group effectively, there is not a lot of time left for the actual design and implementation.

One of the things I found very valuable in designing the Applied Circuits course was doing all the design labs myself, sometimes several times, in order to tweak the specs and anticipate where the students would have difficulty.  I expect to do some redesign of a couple of the circuits labs this year, but that course is scheduled for Spring (and finally got official approval this week), while the (not yet approved) freshman seminar is scheduled for Winter.  So I’m now experimenting with projects that I think may be suitable for the freshman design seminar.

These students cannot individually be expected to know anything useful, high school in California being what it is.  As a group, though, I think I can expect a fair amount of knowledge of biology, chemistry, and physics, with perhaps a sprinkling of math and computer programming.  I can’t expect any electronics knowledge, and we won’t have access to a machine shop—we may get permission for the students to use a laser cutter under supervision.  We can probably get some space in an electronics lab, but maybe not in a bio lab (the dean took away the department’s only teaching lab, with a “promise” to build a bigger one—but it is unlikely to be available for the freshmen by Winter quarter—I miss our first dean of engineering, as we seem to have had a series of incompetent deans since then).

So I’m looking for projects that can essentially be built at home with minimal tools and skills, but that are interesting enough to excite students to continue to higher levels in the program.  And I want them to be design projects, not kit-building or cookbook projects, with multiple possible solutions.

So far, there have been a couple of ideas suggested, both involving a small amount of electronics and some mechanical design:

  • An optical growth meter for continuously monitoring a liquid culture of bacteria or yeast. The electronics here is just a light source (LED or laser diode with current-limiting resistor), a phototransistor,  a current-to-voltage converter for the phototransistor (one resistor), and a data logger (like the Arduino Data Logger we use for the circuits course).  The hard part is coming up with a good way to get uniform sampling of the liquid culture while it is in an incubator on a shaker table.  There are lots of possible solutions: mounting stuff around flasks, immersed sensors, bending glass tubing so that the swirling culture is pumped through the tubes, external peristaltic pumps, … .  Design challenges include how the parts of the apparatus that touch the culture will be sterilized, how to keep things from falling apart when they are shaken for a couple of days, and so forth.   I’ve not even started trying to do a design here, though I probably should, as the mechanical design is almost all unfamiliar to me, and I’d be a good example of the cluelessness that the students would bring to the project.
  • An optical pulse sensor or pulse oximeter.  This is the project I decided to work on yesterday. The goal is to shine light through a finger and get a good pulse signal.  (I tried this last summer, making a very uncomfortable ear clip and doing a little testing before rejecting the project for the circuits course.)  If I can get good pulse signals from both red and IR light sources, I should be able to take differences or ratios and get an output proportional to blood oxygenation.

I decided yesterday to try to build a pulse monitor with almost no electronics.  In particular, I wanted to try building without an op amp or other amplifier, feeding the phototransistor signal directly into an Arduino analog in.  (I may switch to using the KL25Z for this project, as the higher resolution on the analog-to-digital converter means I could use smaller signals without amplification.)

A phototransistor is essentially a light-to-current converter.  The current through the phototransistor is essentially linear in the amount of light, over a pretty wide range. The Arduino analog inputs are voltage sensors, so we need to convert the current to a voltage.  The simplest way to do this is to put a series resistor to ground, and measure the voltage across the series resistor.  The voltage we see is then the current times the resistance.  Sizing the resistor is a design task—how big a current do we get with the intensity of light through the finger, and how much voltage do we need. The voltage needed can be estimated from the resolution of the analog-to-digital converter, but the amount of light is best measured empirically.

One problem that the pulse monitor faces is huge variations in ambient light.  Ideally the phototransistor gets light only from LED light shining through the finger, but that is a bit hard to set up while breadboarding.  Distinguishing the ambient light from the light through the finger can be difficult. Yesterday, I tried to reduce that problem by using “synchronous decoding”.  That is, I turned the LED on and off, and measured the difference between the phototransistor current with the LED on and with the LED off.  Using the Arduino to control the LED as well as to read the voltage is fairly easy—these are the sorts of tasks that are starter projects on the Arduino, so should be within the capabilities of the freshmen (with some learning on their part).

I also looked at the phototransistor output with my BitScope oscilloscope, so that I could see the waveform that the Arduino was sampling two points from.  Here is an example waveform:

The x-axis is 20ms/division, and the y-axis 1v/division, with the center line at 2v.
I put in a 50% duty cycle (20ms on, 20ms off).  The IR light is shining through my index finger.

For the above trace, I used a 680kΩ pulldown resistor to convert the current to voltage. I played a lot with different resistors yesterday, to get a feel for the tradeoffs.  Such a large resistor provides a large voltage swing for a small change in current, but the parasitic capacitance makes for rather slow RC charge/discharge curves.  Using larger resistors does not result in larger swings (unless the frequency of the input is reduced), because the RC time constant gets too large and the slowly changing signal does not have time to make a full swing.  I tried, as an experiment, adding a unity-gain buffer, so that the BitScope and Arduino inputs would not be loading the phototransistor.  This did not make much difference, so most of the parasitic capacitance is probably in the phototransistor itself.  One can get faster response for a fixed change in light only by decreasing the voltage swing, which would then require amplification to get a big enough signal to be read by the Arduino.  (It may be that the extra 6 bits of resolution on the KL25Z board would allow a resistor as low as 20kΩ and much faster response.)

Note that ambient light results in a DC shift of the waveform without a change in shape, until it gets bright enough that the current is more than 5v/680kΩ (about 7µA), at which point the signal gets clipped.  Unfortunately, ordinary room lighting is enough to saturate the sensor with this large a series resistor.  I was able to get fairly consistent readings by using the clothespin ear clip I made last summer, clamped open to make it the right size for my finger.  I did even better when I put the clip and my hand into a camera bag that kept out most of the ambient light.  Clearly, mechanical design for eliminating ambient light will be a big part of this design.

One might think that the 2v signal seen on the BitScope is easily big enough for pulse detection, but remember that this is not the signal we are interested in.  The peak-to-peak voltage is proportional to how transparent the finger is—we are interested in the variation of that amplitude with blood flow.  Here is an example plot of the sort of signal we are looking at:

(click to embiggen) The pulse here is quite visible, but is only about a 15–30 count change in the 300-count amplitude signal. Noise from discretization (and other sources) makes the signal hard to pick out auotmatically.  This signal was recorded with the Arduino data logger, but only after I had modified the data logger code to turn the IR emitter on and off and report differences in the readings rather than the readings themselves. Note the sharp downward transition (increased opacity due to more blood) at the beginning of each pulse.

To get a bigger, cleaner signal, I decided to do some very crude low-pass filtering on the Arduino. I used the simplest of infinite-impulse response (IIR) filters: . Because division is very slow on the Arduino, I limited myself to simple shifts for division: a= 1/2, 1/4, or 1/8. To avoid losing even more precision, I actually output then divided by 8 to get Y(t). I also used a 40msec sampling period, with the IR emitter on for 20ms, then off for 20msec (the waveform shown in the oscilloscope trace above).

(click to embiggen) With digital low-pass filtering, the pulse signal is much cleaner, but the sharp downward transition at the start of each pulse has been rounded off by the filter. This data was not captured with the Arduino Data Logger, but by cutting and pasting from the Arduino serial monitor, which involves simpler (hence more feasible for freshmen) programming of the Arduino.

I now have a very clean pulse signal, using just the Arduino, an IR emitter, a phototransistor, and two resistors. There is still a huge offset, as the signal is 200 counts out of 4600, and the offset fluctuates slowly.  To get a really good signal, I’d want to do a bandpass filter that passes 0.3Hz to 3Hz (20bpm–200bpm), but designing that digital filter would be beyond the scope of a freshman design seminar.  Even the simple IIR filter is pushing a bit here.

I’m not sure how to go from here to the pulse oximeter (using both an IR and a red LED) without fancy digital filtering.  Here is the circuit so far:

Although the 120Ω resistor allows up to 32mA, I didn’t believe that the Arduino outputs could actually sink that much current—20 mA is what the spec sheet allows. Checking with the BitScope, I see a 3840mV drop across the resistor, for 32mA. Note: I used pins D3 and D5 of the Arduino so that I could use pulse-width modulation (PWM) if I wanted to. (Schematic drawn with Digikey’s SchemeIt.)


Filed under: Circuits course, Data acquisition, freshman design seminar Tagged: Arduino, IR emitter, LED, phototransistor, pulse, pulse monitor, pulse oximeter

Optical pulse monitor with little electronics

In yesterday’s blog post, I talked mainly about what my son did with his time yesterday, to mention the small amount of debugging help I gave him.  Today I’ll post about what I did with most of my time yesterday.

This year, I am hoping to lead a 2-unit freshman design seminar for bioengineering students.  (Note: I did not say “teach” here, as I’m envisioning more of a mentoring role than a specific series of exercises.)  One thing I’m doing is trying to come up with design projects that freshmen with essentially no engineering skills can do as a team.  They may have to learn something new (I certainly hope they do!), but they should only spend a total of 60 hours on the course, including class time.  Since I want to spend some of class time on lab tours, lab safety, using the library resources, and how to work in a group effectively, there is not a lot of time left for the actual design and implementation.

One of the things I found very valuable in designing the Applied Circuits course was doing all the design labs myself, sometimes several times, in order to tweak the specs and anticipate where the students would have difficulty.  I expect to do some redesign of a couple of the circuits labs this year, but that course is scheduled for Spring (and finally got official approval this week), while the (not yet approved) freshman seminar is scheduled for Winter.  So I’m now experimenting with projects that I think may be suitable for the freshman design seminar.

These students cannot individually be expected to know anything useful, high school in California being what it is.  As a group, though, I think I can expect a fair amount of knowledge of biology, chemistry, and physics, with perhaps a sprinkling of math and computer programming.  I can’t expect any electronics knowledge, and we won’t have access to a machine shop—we may get permission for the students to use a laser cutter under supervision.  We can probably get some space in an electronics lab, but maybe not in a bio lab (the dean took away the department’s only teaching lab, with a “promise” to build a bigger one—but it is unlikely to be available for the freshmen by Winter quarter—I miss our first dean of engineering, as we seem to have had a series of incompetent deans since then).

So I’m looking for projects that can essentially be built at home with minimal tools and skills, but that are interesting enough to excite students to continue to higher levels in the program.  And I want them to be design projects, not kit-building or cookbook projects, with multiple possible solutions.

So far, there have been a couple of ideas suggested, both involving a small amount of electronics and some mechanical design:

  • An optical growth meter for continuously monitoring a liquid culture of bacteria or yeast. The electronics here is just a light source (LED or laser diode with current-limiting resistor), a phototransistor,  a current-to-voltage converter for the phototransistor (one resistor), and a data logger (like the Arduino Data Logger we use for the circuits course).  The hard part is coming up with a good way to get uniform sampling of the liquid culture while it is in an incubator on a shaker table.  There are lots of possible solutions: mounting stuff around flasks, immersed sensors, bending glass tubing so that the swirling culture is pumped through the tubes, external peristaltic pumps, … .  Design challenges include how the parts of the apparatus that touch the culture will be sterilized, how to keep things from falling apart when they are shaken for a couple of days, and so forth.   I’ve not even started trying to do a design here, though I probably should, as the mechanical design is almost all unfamiliar to me, and I’d be a good example of the cluelessness that the students would bring to the project.
  • An optical pulse sensor or pulse oximeter.  This is the project I decided to work on yesterday. The goal is to shine light through a finger and get a good pulse signal.  (I tried this last summer, making a very uncomfortable ear clip and doing a little testing before rejecting the project for the circuits course.)  If I can get good pulse signals from both red and IR light sources, I should be able to take differences or ratios and get an output proportional to blood oxygenation.

I decided yesterday to try to build a pulse monitor with almost no electronics.  In particular, I wanted to try building without an op amp or other amplifier, feeding the phototransistor signal directly into an Arduino analog in.  (I may switch to using the KL25Z for this project, as the higher resolution on the analog-to-digital converter means I could use smaller signals without amplification.)

A phototransistor is essentially a light-to-current converter.  The current through the phototransistor is essentially linear in the amount of light, over a pretty wide range. The Arduino analog inputs are voltage sensors, so we need to convert the current to a voltage.  The simplest way to do this is to put a series resistor to ground, and measure the voltage across the series resistor.  The voltage we see is then the current times the resistance.  Sizing the resistor is a design task—how big a current do we get with the intensity of light through the finger, and how much voltage do we need. The voltage needed can be estimated from the resolution of the analog-to-digital converter, but the amount of light is best measured empirically.

One problem that the pulse monitor faces is huge variations in ambient light.  Ideally the phototransistor gets light only from LED light shining through the finger, but that is a bit hard to set up while breadboarding.  Distinguishing the ambient light from the light through the finger can be difficult. Yesterday, I tried to reduce that problem by using “synchronous decoding”.  That is, I turned the LED on and off, and measured the difference between the phototransistor current with the LED on and with the LED off.  Using the Arduino to control the LED as well as to read the voltage is fairly easy—these are the sorts of tasks that are starter projects on the Arduino, so should be within the capabilities of the freshmen (with some learning on their part).

I also looked at the phototransistor output with my BitScope oscilloscope, so that I could see the waveform that the Arduino was sampling two points from.  Here is an example waveform:

The x-axis is 20ms/division, and the y-axis 1v/division, with the center line at 2v.
I put in a 50% duty cycle (20ms on, 20ms off).  The IR light is shining through my index finger.

For the above trace, I used a 680kΩ pulldown resistor to convert the current to voltage. I played a lot with different resistors yesterday, to get a feel for the tradeoffs.  Such a large resistor provides a large voltage swing for a small change in current, but the parasitic capacitance makes for rather slow RC charge/discharge curves.  Using larger resistors does not result in larger swings (unless the frequency of the input is reduced), because the RC time constant gets too large and the slowly changing signal does not have time to make a full swing.  I tried, as an experiment, adding a unity-gain buffer, so that the BitScope and Arduino inputs would not be loading the phototransistor.  This did not make much difference, so most of the parasitic capacitance is probably in the phototransistor itself.  One can get faster response for a fixed change in light only by decreasing the voltage swing, which would then require amplification to get a big enough signal to be read by the Arduino.  (It may be that the extra 6 bits of resolution on the KL25Z board would allow a resistor as low as 20kΩ and much faster response.)

Note that ambient light results in a DC shift of the waveform without a change in shape, until it gets bright enough that the current is more than 5v/680kΩ (about 7µA), at which point the signal gets clipped.  Unfortunately, ordinary room lighting is enough to saturate the sensor with this large a series resistor.  I was able to get fairly consistent readings by using the clothespin ear clip I made last summer, clamped open to make it the right size for my finger.  I did even better when I put the clip and my hand into a camera bag that kept out most of the ambient light.  Clearly, mechanical design for eliminating ambient light will be a big part of this design.

One might think that the 2v signal seen on the BitScope is easily big enough for pulse detection, but remember that this is not the signal we are interested in.  The peak-to-peak voltage is proportional to how transparent the finger is—we are interested in the variation of that amplitude with blood flow.  Here is an example plot of the sort of signal we are looking at:

(click to embiggen) The pulse here is quite visible, but is only about a 15–30 count change in the 300-count amplitude signal. Noise from discretization (and other sources) makes the signal hard to pick out auotmatically.  This signal was recorded with the Arduino data logger, but only after I had modified the data logger code to turn the IR emitter on and off and report differences in the readings rather than the readings themselves. Note the sharp downward transition (increased opacity due to more blood) at the beginning of each pulse.

To get a bigger, cleaner signal, I decided to do some very crude low-pass filtering on the Arduino. I used the simplest of infinite-impulse response (IIR) filters: . Because division is very slow on the Arduino, I limited myself to simple shifts for division: a= 1/2, 1/4, or 1/8. To avoid losing even more precision, I actually output then divided by 8 to get Y(t). I also used a 40msec sampling period, with the IR emitter on for 20ms, then off for 20msec (the waveform shown in the oscilloscope trace above).

(click to embiggen) With digital low-pass filtering, the pulse signal is much cleaner, but the sharp downward transition at the start of each pulse has been rounded off by the filter. This data was not captured with the Arduino Data Logger, but by cutting and pasting from the Arduino serial monitor, which involves simpler (hence more feasible for freshmen) programming of the Arduino.

I now have a very clean pulse signal, using just the Arduino, an IR emitter, a phototransistor, and two resistors. There is still a huge offset, as the signal is 200 counts out of 4600, and the offset fluctuates slowly.  To get a really good signal, I’d want to do a bandpass filter that passes 0.3Hz to 3Hz (20bpm–200bpm), but designing that digital filter would be beyond the scope of a freshman design seminar.  Even the simple IIR filter is pushing a bit here.

I’m not sure how to go from here to the pulse oximeter (using both an IR and a red LED) without fancy digital filtering.  Here is the circuit so far:

Although the 120Ω resistor allows up to 32mA, I didn’t believe that the Arduino outputs could actually sink that much current—20 mA is what the spec sheet allows. Checking with the BitScope, I see a 3840mV drop across the resistor, for 32mA. Note: I used pins D3 and D5 of the Arduino so that I could use pulse-width modulation (PWM) if I wanted to. (Schematic drawn with Digikey’s SchemeIt.)


Filed under: Circuits course, Data acquisition, freshman design seminar Tagged: Arduino, IR emitter, LED, phototransistor, pulse, pulse monitor, pulse oximeter

Tutorial – Arduino and MC14489 LED Display Driver

Learn how to use MC14489 LED display driver ICs with Arduino in chapter fifty-one of a series originally titled “Getting Started/Moving Forward with Arduino!” by John Boxall – A tutorial on the Arduino universe. The first chapter is here, the complete series is detailed here.

Updated 12/05/2013

Introduction

Recently we’ve been looking at alternatives to the MAX7219 LED display driver IC due to pricing and availability issues (stay tuned for that one) – and came across an old but still quite useful IC – the MC14489 from Motorola (now Freescale Semiconductor). The MC14489 can drive five seven-segment LED numbers with decimal point, or a combination of numbers and separate LEDs. You can also daisy-chain more than one to drive more digits, and it’s controlled with a simple serial data-clock method in the same way as a 74HC595 shift register. Sourcing the MC14489 isn’t too difficult – it’s available from element14, Newark, Digikey, and so on – or if you’re not in a hurry, try the usual suspects like Futurlec.

For the purpose of the tutorial we’ll show you how to send commands easily from your Arduino or compatible board to control a five-digit 7-segment LED display module – and the instructions are quite simple so they should translate easily to other platforms. Once you have mastered the single module, using more than one MC14489 will be just as easy. So let’s get started.

Hardware

Before moving forward, download the data sheet (pdf). You will need to refer to this as you build the circuit(s). And here’s our subject in real life:

For our demonstration display we’ll be using a vintage HP 5082-7415 LED display module. However you can use almost any 7-segment modules as long as they’re common-cathode – for example, Sparkfun part number COM-11405. If you’re using a four-digit module and want an extra digit, you can add another single digit display. If you want a ruler, the design files are here.

Connecting the MC14489 to an LED display isn’t complex at all. From the data sheet consider Figure 9:

Each of the anode control pins from the MC14489 connect to the matching anodes on your display module, and the BANK1~5 pins connect to the matching digit cathode pins on the display module. You can find the MC14489 pin assignments on page 1 of the data sheet. Seeing as this is chapter fifty-one  – by now you should be confident with finding such information on the data sheets, so I will be encouraging you to do a little more of the work.

Interesting point – you don’t need current-limiting resistors. However you do need the resistor Rx – this controls the current flow to each LED segment. But which value to use? You need to find out the forward current of your LED display (for example 20 mA) then check Figure 7 on page 7 of the data sheet:

To be conservative I’m using a value of 2k0 for Rx, however you can choose your own based on the data sheet for your display and the graph above.  Next – connect the data, clock and enable pins of the MC14489 to three Arduino digital pints – for our example we’re using 5, 6 and 7 for data, clock and enable respectively. Then it’s just 5V and GND to Arduino 5V and GND – and put a 0.1uF capacitor between 5V and GND. Before moving on double-check the connections – especially between the MC14489 and the LED display.

Controlling the MC14489

To control the display we need to send data to two registers in the MC14489 – the configuration register  (one byte) and the display register (three bytes). See page 9 of the data sheet for the overview. The MC14489 will understand that if we send out one byte of data it is to send it the configuration register, and if it receives three bytes of data to send it to the display register. To keep things simple we’ll only worry about the first bit (C0) in the configuration register – this turns the display outputs on or off. To do this, use the following:

digitalWrite(enable, LOW);
shiftOut(data, clock, MSBFIRST, B00000001); // used binary for clarity, however you can use decimal or hexadecimal numbers
digitalWrite(enable, HIGH);
delay(10);

and to turn it off, send bit C0 as zero. The small delay is necessary after each command.

Once you have turned the display on – the next step is to send three bytes of data which represent the numbers to display and decimal points if necessary. Review the table on page 8 of the data sheet. See how they have the binary nibble values for the digits in the third column. Thankfully the nibble for each digit is the binary value for that digit. Furthermore you might want to set the decimal point – that is set using three bits in the first nibble of the three bytes (go back to page 9 and see the display register). Finally you can halve the brightness by setting the very first bit to zero (or one for full brightness).

As an example for that – if you want to display 5.4321 the three bytes of data to send in binary will be:

1101 0101 0100 0011 0010 0001

Let’s break that down. The first bit is 1 for full brightness, then the next three bits (101) turn on the decimal point for BANK5 (the left-most digit). Then you have five nibbles of data, one for each of the digits from left to right. So there’s binary for 5, then four, then three, then two, then one.

digitalWrite(enable, LOW); 
shiftOut(data, clock, MSBFIRST, B11010101); // D23~D16 
shiftOut(data, clock, MSBFIRST, B01000011); // D15~D8
shiftOut(data, clock, MSBFIRST, B00100001); // D7~D0
digitalWrite(enable, HIGH);
delay(10);

To demonstrate everything described so far, it’s been neatly packaged into our first example sketch:

// Example 51.1
// Motorola MC14489 with HP 5082-7415 5-digit, 7-segment LED display
// 2k0 resistor on MC14489 Rx pin
// John Boxall 2013 CC by-sa-nc
// define pins for data from Arduino to MC14489
// we treat it just like a 74HC595
int data = 5;
int clock = 6;
int enable = 7;
void setup()
{
 pinMode(data, OUTPUT);
 pinMode(enable, OUTPUT);
 pinMode(clock, OUTPUT);
 displayOn(); // display defaults to off at power-up
}
void displayTest1()
// displays 5.4321
{
 digitalWrite(enable, LOW); // send 3 bytes to display register. See data sheet page 9
 // you can also insert decimal or hexadecimal numbers in place of the binary numbers
 // we're using binary as you can easily match the nibbles (4-bits) against the table
 // in data sheet page 8
 shiftOut(data, clock, MSBFIRST, B11010101); // D23~D16
 shiftOut(data, clock, MSBFIRST, B01000011); // D15~D8
 shiftOut(data, clock, MSBFIRST, B00100001); // D7~D0
 digitalWrite(enable, HIGH);
 delay(10);
}
void displayTest2()
// displays ABCDE
{
 digitalWrite(enable, LOW); // send 3 bytes to display register. See data sheet page 9
 // you can also insert decimal or hexadecimal numbers in place of the binary numbers
 // we're using binary as you can easily match the nibbles (4-bits) against the table
 // in data sheet page 8
 shiftOut(data, clock, MSBFIRST, B10001010); // D23~D16
 shiftOut(data, clock, MSBFIRST, B10111100); // D15~D8
 shiftOut(data, clock, MSBFIRST, B11011110); // D7~D0
 digitalWrite(enable, HIGH);
 delay(10);
}
void displayOn()
// turns on display
{
 digitalWrite(enable, LOW);
 shiftOut(data, clock, MSBFIRST, B00000001);
 digitalWrite(enable, HIGH);
 delay(10);
}
void displayOff()
// turns off display
{
 digitalWrite(enable, LOW);
 shiftOut(data, clock, MSBFIRST, B00000000);
 digitalWrite(enable, HIGH);
 delay(10);
}
void loop()
{
 displayOn();
 displayTest1();
 delay(1000);
 displayTest2();
 delay(1000);
 displayOff();
 delay(500);
}

… with the results in the following video:


Now that we can display numbers and a few letters with binary, life would be easier if there was a way to take a number and just send it to the display.

So consider the following function that takes an integer between 0 and 99999, does the work and sends it to the display:

void displayIntLong(long x)
// takes a long between 0~99999 and sends it to the MC14489
{
 int numbers[5];
 byte a=0; 
 byte b=0; 
 byte c=0; // will hold the three bytes to send to the MC14489 

 // first split the incoming long into five separate digits
 numbers[0] = int ( x / 10000 ); // left-most digit (will be BANK5)
 x = x % 10000; 
 numbers[1] = int ( x / 1000 );
 x = x % 1000; 
 numbers[2] = int ( x / 100 );
 x = x % 100; 
 numbers[3] = int ( x / 10 );
 x = x % 10; 
 numbers[4] = x % 10; // right-most digit (will be BANK1)

 // now to create the three bytes to send to the MC14489
 // build byte c which holds digits 4 and 5
 c = numbers[3];
 c = c << 4; // move the nibble to the left
 c = c | numbers[4];
 // build byte b which holds digits 3 and 4
 b = numbers [1];
 b = b << 4;
 b = b | numbers[2];
 // build byte a which holds the brightness bit, decimal points and digit 1
 a = B10000000 | numbers[0]; // full brightness, no decimal points

 // now send the bytes to the MC14489
 digitalWrite(enable, LOW);
 shiftOut(data, clock, MSBFIRST, a);
 shiftOut(data, clock, MSBFIRST, b);
 shiftOut(data, clock, MSBFIRST, c); 
 digitalWrite(enable, HIGH);
 delay(10); 
}

So how does that work? First it splits the 5-digit number into separate digits and stores them in the array numbers[]. It then places the fourth digit into a byte, then moves the data four bits to the left – then we bitwise OR the fifth digit into the same byte. This leaves us with a byte of data containing the nibbles for the fourth and fifth digit. The process is repeated for digits 2 and 3. Finally the brightness bit and decimal point bits are assigned to another byte which then has the first digit’s nibble OR’d into it. Which leaves us with bytes a, b and c ready to send to the MC14489. Note that there isn’t any error-checking – however you could add a test to check that the number to be displayed was within the parameter, and if not either switch off the display (see example 51.1) or throw up all the decimal points or … whatever you want.

You can download the demonstration sketch for the function – Example 51.2, and view the results in the following video:

You can also display the letters A to F by sending the values 10 to 15 respectivel to each digit’s nibble. However that would be part of a larger application, which you can (hopefully) by now work out for yourself. Furthermore there’s some other characters that can be displayed – however trying to display the alphabet using 7-segment displays is somewhat passé. Instead, get some 16-segment LED modules or an LCD.

Finally, you can cascade more than one MC14489 to control more digits. Just run a connection from the data out pin on the first MC14889 to the data pin of the second one, and all the clock and enable lines together. Then send out more data – see page 11 of the data sheet. If you’re going to do that in volume other ICs may be a cheaper option and thus lead you back to the MAX7219.

Conclusion

For a chance find the MC14489 is a fun an inexpensive way to drive those LED digit displays. We haven’t covered every single possible option or feature of the part – however you will now have the core knowledge to go further with the MC14489 if you need to move further with it. And if you enjoy my tutorials, or want to introduce someone else to the interesting world of Arduino – check out my new book “Arduino Workshop” from No Starch Press.

In the meanwhile have fun and keep checking into tronixstuff.com. Why not follow things on twitterGoogle+, subscribe  for email updates or RSS using the links on the right-hand column? And join our friendly Google Group – dedicated to the projects and related items on this website. Sign up – it’s free, helpful to each other –  and we can all learn something.

The post Tutorial – Arduino and MC14489 LED Display Driver appeared first on tronixstuff.

Bluetooth Android Processing 3

PART THREE


If you happened to land on this page and missed PART ONE, and PART TWO, I would advise you go back and read those sections first.

This is what you'll find in partone:
  • Downloading and setting up the Android SDK
  • Downloading the Processing IDE
  • Setting up and preparing the Android device
  • Running through a couple of Processing/Android sketches on an Andoid phone.
This is what you will find in part two:

  • Introducing Toasts (display messages)
  • Looking out for BluetoothDevices using BroadcastReceivers
  • Getting useful information from a discovered Bluetooth device
  • Connecting to a Bluetooth Device
  • An Arduino Bluetooth Sketch that can be used in this tutorial


InputStream and OutputStream
We will now borrow some code from the Android developers site to help us to establish communication between the Android phone and the Bluetooth shield on the Arduino. By this stage we have already scanned and discovered the bluetooth device and made a successful connection. We now need to create an InputStream and OutputStream to handle the flow of communication between the devices. Let us start with the Android/Processing Side.
The Android Developers site suggests to create a new Thread to handle the incoming and outgoing bytes, because this task uses "blocking" calls. Blocking calls means that the application will appear to be frozen until the call completes. We will create a new Thread to receive bytes through the BluetoothSocket's InputStream, and will send bytes to the Arduino through the BluetoothSocket's OutputStream.
This Thread will continue to listen/send bytes for as long as needed, and will eventually close when we tell it to. We will also need a Handler() to act on any bytes received via the InputStream. The Handler is necessary to transfer information from the IO Thread to the main application thread. This is done by using a Message class. Here is a summary of relevant code that we will subsequently add to the ConnectBluetooth sketch (which was described in Part Two of this tutorial):

 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
import android.bluetooth.BluetoothSocket;
import java.io.InputStream;
import java.io.OutputStream;
import android.os.Handler;
import android.os.Message;
import android.util.Log;

// Message types used by the Handler
public static final int MESSAGE_WRITE = 1;
public static final int MESSAGE_READ = 2;

// The Handler that gets information back from the Socket
private final Handler mHandler = new Handler() {
@Override
public void handleMessage(Message msg) {
switch (msg.what) {
case MESSAGE_WRITE:
//Do something when writing
break;
case MESSAGE_READ:
//Get the bytes from the msg.obj
byte[] readBuf = (byte[]) msg.obj;
// construct a string from the valid bytes in the buffer
String readMessage = new String(readBuf, 0, msg.arg1);
break;
}
}
};



private class SendReceiveBytes implements Runnable {
private BluetoothSocket btSocket;
private InputStream btInputStream = null;
private OutputStream btOutputStream = null;
String TAG = "SendReceiveBytes";

public SendReceiveBytes(BluetoothSocket socket) {
btSocket = socket;
try {
btInputStream = btSocket.getInputStream();
btOutputStream = btSocket.getOutputStream();
}
catch (IOException streamError) {
Log.e(TAG, "Error when getting input or output Stream");
}
}

public void run() {
byte[] buffer = new byte[1024]; // buffer store for the stream
int bytes; // bytes returned from read()

// Keep listening to the InputStream until an exception occurs
while (true) {
try {
// Read from the InputStream
bytes = btInputStream.read(buffer);
// Send the obtained bytes to the UI activity
mHandler.obtainMessage(MESSAGE_READ, bytes, -1, buffer)
.sendToTarget();
}
catch (IOException e) {
Log.e(TAG, "Error reading from btInputStream");
break;
}
}
}

/* Call this from the main activity to send data to the remote device */
public void write(byte[] bytes) {
try {
btOutputStream.write(bytes);
}
catch (IOException e) {
Log.e(TAG, "Error when writing to btOutputStream");
}
}

/* Call this from the main activity to shutdown the connection */
public void cancel() {
try {
btSocket.close();
}
catch (IOException e) {
Log.e(TAG, "Error when closing the btSocket");
}
}
}

Notice that we place an endless loop in the run() method to continuously read bytes from the InputStream. This continuous process of reading bytes needs to be a different thread from the main application otherwise it would cause the program to "hang". This thread passes any read bytes to the main application by using the Handler's .sendToTarget() method.
You will also notice the use of Log.e(TAG, ".....") commands. This is useful for debugging Android problems, especially when you comae across errors that generate a "caused the application to close unexpectedly" dialog box to appear on your phone.  I personally created a shortcut of the adb.exe on my desktop and changed the target to
  • "c:\[INSERT FOLDER]\Android\android-sdk\platform-tools\adb.exe" logcat *:E
The adb.exe program comes with the Android-SDK downloaded in Part One . Once you find the adb.exe on your hard-drive, you just create a shortcut on your desktop. Right-click the shortcut, choose "Properties" and as indicated above, you change the last bit of the Target to
  • logcat *:E
So if you get an unexpected error on your android device, just go back to your laptop, and double-click on your new desktop adb.exe shortcut to get a better idea of where your program has gone wrong.

We will now incorporate the sketch above into our ConnectBluetooth Android/Processing App, however we will call this updated version "SendReceiveBytes"
Once we have created a successful connection, and created our Input/OutputStreams, we will send a single letter "r" to the Arduino via bluetooth, and if all goes well, we should see the light on the RGB Chainable LED turn Red (see further down for Arduino sketch).
I borrowed Byron's code snippet from this site: to convert a string ("r") to a byte array, which is used in the write() method. The relevant code can be found on lines 199-208 below. I have bolded the lines numbers to make it a little easier to see the changes I made (compared to the previous sketch).

Android/Processing Sketch 6: SendReceiveBytes
 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
/* SendReceiveBytes: Written by ScottC on 25 March 2013 using 
Processing version 2.0b8
Tested on a Samsung Galaxy SII, with Android version 2.3.4
Android ADK - API 10 SDK platform */

import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.widget.Toast;
import android.view.Gravity;
import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothDevice;

import java.util.UUID;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import android.os.Handler;
import android.os.Message;
import android.util.Log;

import android.bluetooth.BluetoothServerSocket;
import android.bluetooth.BluetoothSocket;
public BluetoothSocket scSocket;


boolean foundDevice=false; //When true, the screen turns green.
boolean BTisConnected=false; //When true, the screen turns purple.
String serverName = "ArduinoBasicsServer";

// Message types used by the Handler
public static final int MESSAGE_WRITE = 1;
public static final int MESSAGE_READ = 2;
String readMessage="";

//Get the default Bluetooth adapter
BluetoothAdapter bluetooth = BluetoothAdapter.getDefaultAdapter();

/*The startActivityForResult() within setup() launches an
Activity which is used to request the user to turn Bluetooth on.
The following onActivityResult() method is called when this
Activity exits. */
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
if (requestCode==0) {
if (resultCode == RESULT_OK) {
ToastMaster("Bluetooth has been switched ON");
}
else {
ToastMaster("You need to turn Bluetooth ON !!!");
}
}
}


/* Create a BroadcastReceiver that will later be used to
receive the names of Bluetooth devices in range. */
BroadcastReceiver myDiscoverer = new myOwnBroadcastReceiver();


/* Create a BroadcastReceiver that will later be used to
identify if the Bluetooth device is connected */
BroadcastReceiver checkIsConnected = new myOwnBroadcastReceiver();


// The Handler that gets information back from the Socket
private final Handler mHandler = new Handler() {
@Override
public void handleMessage(Message msg) {
switch (msg.what) {
case MESSAGE_WRITE:
//Do something when writing
break;
case MESSAGE_READ:
//Get the bytes from the msg.obj
byte[] readBuf = (byte[]) msg.obj;
// construct a string from the valid bytes in the buffer
readMessage = new String(readBuf, 0, msg.arg1);
break;
}
}
};


void setup() {
orientation(LANDSCAPE);
/*IF Bluetooth is NOT enabled, then ask user permission to enable it */
if (!bluetooth.isEnabled()) {
Intent requestBluetooth = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);
startActivityForResult(requestBluetooth, 0);
}


/*If Bluetooth is now enabled, then register a broadcastReceiver to report any
discovered Bluetooth devices, and then start discovering */
if (bluetooth.isEnabled()) {
registerReceiver(myDiscoverer, new IntentFilter(BluetoothDevice.ACTION_FOUND));
registerReceiver(checkIsConnected, new IntentFilter(BluetoothDevice.ACTION_ACL_CONNECTED));

//Start bluetooth discovery if it is not doing so already
if (!bluetooth.isDiscovering()) {
bluetooth.startDiscovery();
}
}
}


void draw() {
//Display a green screen if a device has been found,
//Display a purple screen when a connection is made to the device
if (foundDevice) {
if (BTisConnected) {
background(170, 50, 255); // purple screen
}
else {
background(10, 255, 10); // green screen
}
}

//Display anything received from Arduino
text(readMessage, 10, 10);
}


/* This BroadcastReceiver will display discovered Bluetooth devices */
public class myOwnBroadcastReceiver extends BroadcastReceiver {
ConnectToBluetooth connectBT;

@Override
public void onReceive(Context context, Intent intent) {
String action=intent.getAction();
ToastMaster("ACTION:" + action);

//Notification that BluetoothDevice is FOUND
if (BluetoothDevice.ACTION_FOUND.equals(action)) {
//Display the name of the discovered device
String discoveredDeviceName = intent.getStringExtra(BluetoothDevice.EXTRA_NAME);
ToastMaster("Discovered: " + discoveredDeviceName);

//Display more information about the discovered device
BluetoothDevice discoveredDevice = intent.getParcelableExtra(BluetoothDevice.EXTRA_DEVICE);
ToastMaster("getAddress() = " + discoveredDevice.getAddress());
ToastMaster("getName() = " + discoveredDevice.getName());

int bondyState=discoveredDevice.getBondState();
ToastMaster("getBondState() = " + bondyState);

String mybondState;
switch(bondyState) {
case 10:
mybondState="BOND_NONE";
break;
case 11:
mybondState="BOND_BONDING";
break;
case 12:
mybondState="BOND_BONDED";
break;
default:
mybondState="INVALID BOND STATE";
break;
}
ToastMaster("getBondState() = " + mybondState);

//Change foundDevice to true which will make the screen turn green
foundDevice=true;

//Connect to the discovered bluetooth device (SeeedBTSlave)
if (discoveredDeviceName.equals("SeeedBTSlave")) {
ToastMaster("Connecting you Now !!");
unregisterReceiver(myDiscoverer);
connectBT = new ConnectToBluetooth(discoveredDevice);
//Connect to the the device in a new thread
new Thread(connectBT).start();
}
}

//Notification if bluetooth device is connected
if (BluetoothDevice.ACTION_ACL_CONNECTED.equals(action)) {
ToastMaster("CONNECTED _ YAY");

while (scSocket==null) {
//do nothing
}
ToastMaster("scSocket" + scSocket);
BTisConnected=true; //turn screen purple
if (scSocket!=null) {
SendReceiveBytes sendReceiveBT = new SendReceiveBytes(scSocket);
new Thread(sendReceiveBT).start();
String red = "r";
byte[] myByte = stringToBytesUTFCustom(red);
sendReceiveBT.write(myByte);
}
}
}
}
public static byte[] stringToBytesUTFCustom(String str) {
char[] buffer = str.toCharArray();
byte[] b = new byte[buffer.length << 1];
for (int i = 0; i < buffer.length; i++) {
int bpos = i << 1;
b[bpos] = (byte) ((buffer[i]&0xFF00)>>8);
b[bpos + 1] = (byte) (buffer[i]&0x00FF);
}
return b;
}

public class ConnectToBluetooth implements Runnable {
private BluetoothDevice btShield;
private BluetoothSocket mySocket = null;
private UUID uuid = UUID.fromString("00001101-0000-1000-8000-00805F9B34FB");

public ConnectToBluetooth(BluetoothDevice bluetoothShield) {
btShield = bluetoothShield;
try {
mySocket = btShield.createRfcommSocketToServiceRecord(uuid);
}
catch(IOException createSocketException) {
//Problem with creating a socket
Log.e("ConnectToBluetooth", "Error with Socket");
}
}

@Override
public void run() {
/* Cancel discovery on Bluetooth Adapter to prevent slow connection */
bluetooth.cancelDiscovery();

try {
/*Connect to the bluetoothShield through the Socket. This will block
until it succeeds or throws an IOException */
mySocket.connect();
scSocket=mySocket;
}
catch (IOException connectException) {
Log.e("ConnectToBluetooth", "Error with Socket Connection");
try {
mySocket.close(); //try to close the socket
}
catch(IOException closeException) {
}
return;
}
}

/* Will cancel an in-progress connection, and close the socket */
public void cancel() {
try {
mySocket.close();
}
catch (IOException e) {
}
}
}


private class SendReceiveBytes implements Runnable {
private BluetoothSocket btSocket;
private InputStream btInputStream = null;
private OutputStream btOutputStream = null;
String TAG = "SendReceiveBytes";

public SendReceiveBytes(BluetoothSocket socket) {
btSocket = socket;
try {
btInputStream = btSocket.getInputStream();
btOutputStream = btSocket.getOutputStream();
}
catch (IOException streamError) {
Log.e(TAG, "Error when getting input or output Stream");
}
}


public void run() {
byte[] buffer = new byte[1024]; // buffer store for the stream
int bytes; // bytes returned from read()

// Keep listening to the InputStream until an exception occurs
while (true) {
try {
// Read from the InputStream
bytes = btInputStream.read(buffer);
// Send the obtained bytes to the UI activity
mHandler.obtainMessage(MESSAGE_READ, bytes, -1, buffer)
.sendToTarget();
}
catch (IOException e) {
Log.e(TAG, "Error reading from btInputStream");
break;
}
}
}


/* Call this from the main activity to send data to the remote device */
public void write(byte[] bytes) {
try {
btOutputStream.write(bytes);
}
catch (IOException e) {
Log.e(TAG, "Error when writing to btOutputStream");
}
}


/* Call this from the main activity to shutdown the connection */
public void cancel() {
try {
btSocket.close();
}
catch (IOException e) {
Log.e(TAG, "Error when closing the btSocket");
}
}
}



/* My ToastMaster function to display a messageBox on the screen */
void ToastMaster(String textToDisplay) {
Toast myMessage = Toast.makeText(getApplicationContext(),
textToDisplay,
Toast.LENGTH_SHORT);
myMessage.setGravity(Gravity.CENTER, 0, 0);
myMessage.show();
}


Arduino Sketch: Testing the Input/OutputStream
We will borrow the Arduino Sketch from my previous blog post (here). Which should change the RGB LED to red when it receives an "r" through the bluetooth serial port.
You should also be able to send text to the Android phone by opening up the Serial Monitor on the Arduino IDE (although found this to be somewhat unreliable/unpredictable. I may need to investigate a better way of doing this, but it should work to some capacity (I sometimes find that a couple of letters go missing on transmision).
In this sketch I am using a Bluetooth shield like this one,  and have connected a Grove Chainable RGB LED to it using a Grove Universal 4 Pin Cable.



Arduino Sketch 2: Bluetooth RGB Colour Changer

 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
/* This project combines the code from a few different sources.
This project was put together by ScottC on the 15/01/2013
http://arduinobasics.blogspot.com/

Bluetooth slave code by Steve Chang - downloaded from :
http://www.seeedstudio.com/wiki/index.php?title=Bluetooth_Shield

Grove Chainable RGB code can be found here :
http://www.seeedstudio.com/wiki/Grove_-_Chainable_RGB_LED#Introduction

*/

#include <SoftwareSerial.h> //Software Serial Port
#define uint8 unsigned char
#define uint16 unsigned int
#define uint32 unsigned long int

#define RxD 6 // This is the pin that the Bluetooth (BT_TX) will transmit to the Arduino (RxD)
#define TxD 7 // This is the pin that the Bluetooth (BT_RX) will receive from the Arduino (TxD)

#define DEBUG_ENABLED 1

int Clkpin = 9; //RGB LED Clock Pin (Digital 9)
int Datapin = 8; //RGB LED Data Pin (Digital 8)

SoftwareSerial blueToothSerial(RxD,TxD);
/*----------------------SETUP----------------------------*/ void setup() {
Serial.begin(9600); // Allow Serial communication via USB cable to computer (if required)
pinMode(RxD, INPUT); // Setup the Arduino to receive INPUT from the bluetooth shield on Digital Pin 6
pinMode(TxD, OUTPUT); // Setup the Arduino to send data (OUTPUT) to the bluetooth shield on Digital Pin 7
pinMode(13,OUTPUT); // Use onboard LED if required.
setupBlueToothConnection(); //Used to initialise the Bluetooth shield

pinMode(Datapin, OUTPUT); // Setup the RGB LED Data Pin
pinMode(Clkpin, OUTPUT); // Setup the RGB LED Clock pin

}
/*----------------------LOOP----------------------------*/ void loop() {
digitalWrite(13,LOW); //Turn off the onboard Arduino LED
char recvChar;
while(1){
if(blueToothSerial.available()){//check if there's any data sent from the remote bluetooth shield
recvChar = blueToothSerial.read();
Serial.print(recvChar); // Print the character received to the Serial Monitor (if required)

//If the character received = 'r' , then change the RGB led to display a RED colour
if(recvChar=='r'){
Send32Zero(); // begin
DataDealWithAndSend(255, 0, 0); // first node data
Send32Zero(); // send to update data
}

//If the character received = 'g' , then change the RGB led to display a GREEN colour
if(recvChar=='g'){
Send32Zero(); // begin
DataDealWithAndSend(0, 255, 0); // first node data
Send32Zero(); // send to update data
}

//If the character received = 'b' , then change the RGB led to display a BLUE colour
if(recvChar=='b'){
Send32Zero(); // begin
DataDealWithAndSend(0, 0, 255); // first node data
Send32Zero(); // send to update data
}
}

//You can use the following code to deal with any information coming from the Computer (serial monitor)
if(Serial.available()){
recvChar = Serial.read();

//This will send value obtained (recvChar) to the phone. The value will be displayed on the phone.
blueToothSerial.print(recvChar);
}
}
}

//The following code is necessary to setup the bluetooth shield ------copy and paste----------------
void setupBlueToothConnection()
{
blueToothSerial.begin(38400); //Set BluetoothBee BaudRate to default baud rate 38400
blueToothSerial.print("\r\n+STWMOD=0\r\n"); //set the bluetooth work in slave mode
blueToothSerial.print("\r\n+STNA=SeeedBTSlave\r\n"); //set the bluetooth name as "SeeedBTSlave"
blueToothSerial.print("\r\n+STOAUT=1\r\n"); // Permit Paired device to connect me
blueToothSerial.print("\r\n+STAUTO=0\r\n"); // Auto-connection should be forbidden here
delay(2000); // This delay is required.
blueToothSerial.print("\r\n+INQ=1\r\n"); //make the slave bluetooth inquirable
Serial.println("The slave bluetooth is inquirable!");
delay(2000); // This delay is required.
blueToothSerial.flush();
}

//The following code snippets are used update the colour of the RGB LED-----copy and paste------------
void ClkProduce(void){
digitalWrite(Clkpin, LOW);
delayMicroseconds(20);
digitalWrite(Clkpin, HIGH);
delayMicroseconds(20);
}
void Send32Zero(void){
unsigned char i;
for (i=0; i<32; i++){
digitalWrite(Datapin, LOW);
ClkProduce();
}
}

uint8 TakeAntiCode(uint8 dat){
uint8 tmp = 0;
if ((dat & 0x80) == 0){
tmp |= 0x02;
}

if ((dat & 0x40) == 0){
tmp |= 0x01;
}

return tmp;
}
// gray data
void DatSend(uint32 dx){
uint8 i;
for (i=0; i<32; i++){
if ((dx & 0x80000000) != 0){
digitalWrite(Datapin, HIGH);
} else {
digitalWrite(Datapin, LOW);
}

dx <<= 1;
ClkProduce();
}
}
// data processing
void DataDealWithAndSend(uint8 r, uint8 g, uint8 b){
uint32 dx = 0;

dx |= (uint32)0x03 << 30; // highest two bits 1,flag bits
dx |= (uint32)TakeAntiCode(b) << 28;
dx |= (uint32)TakeAntiCode(g) << 26;
dx |= (uint32)TakeAntiCode(r) << 24;

dx |= (uint32)b << 16;
dx |= (uint32)g << 8;
dx |= r;

DatSend(dx);
}



Some GUI Buttons

My aim is to somewhat recreate the experience from a similar project I blogged about (here). However I wanted to have much more control over the GUI. I will start by creating a few buttons, but will later look at making a much more fun/interactive design (hopefully). The following simple Android/Processing sketch will be totally independant of the sketch above, it will be a simple App that will have a few buttons which will change the colour of the background on the phone. Once we get the hang of this, we will incorporate it into our Bluetooth Sketch.
To start off with, we will need to download an Android/Processing library which will allow us to create the buttons that we will use in our App.
Unzip the apwidgets_r44.zip file and put the apwidgets folder into your default Processing sketch "libraries" folder. For more information about installing contributed libraries into you Processing IDE - have a look at this site.
You will need to reboot your Processing IDE before being able to see the "apwidgets" item appear in the Processing IDE's menu,
  • Sketch > Import Library :  Under the "Contributed" list item.
If you cannot see this menu item, then you will need to try again. Make sure you are putting it into the default sketch libraries folder, which may not be in the same folder as the processing IDE. To find out the default sketch location - look here:
  • File > Preferences > Sketchbook location
Ok, now that you have the APWidgets library installed in your Processing IDE, make sure you are still in Andorid Mode, and copy the following sketch into the IDE, and run the program on your device. This sketch borrows heavily from the APWidgets Button example, which can be found here.

Android/Processing Sketch 7: Button Presser
 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
import apwidgets.*;

APWidgetContainer widgetContainer;
APButton redButton, greenButton, blueButton, offButton;
String buttonText="";
int buttonWidth=0;
int buttonHeight=0;
int n=4; //number of buttons
int gap=10; //gap between buttons


void setup() {
buttonWidth=((width/n)-(n*gap));
buttonHeight=(height/2);
widgetContainer = new APWidgetContainer(this); //create new container for widgets
redButton =new APButton((buttonWidth*(n-4)+(gap*1)), gap, buttonWidth, buttonHeight, "RED"); //Create a RED button
greenButton = new APButton((buttonWidth*(n-3)+(gap*2)), gap, buttonWidth, buttonHeight, "GREEN"); //Create a GREEN button
blueButton = new APButton((buttonWidth*(n-2)+(gap*3)), gap, buttonWidth, buttonHeight, "BLUE"); //Create a BLUE button
offButton = new APButton((buttonWidth*(n-1)+(gap*4)), gap, buttonWidth, buttonHeight, "OFF"); //Create a OFF button
widgetContainer.addWidget(redButton); //place red button in container
widgetContainer.addWidget(greenButton); //place green button in container
widgetContainer.addWidget(blueButton);//place blue button in container
widgetContainer.addWidget(offButton);//place off button in container
background(0); //Start with a black background
}



void draw() {
//Change the text based on the button being pressed.
text(buttonText, 10, buttonHeight+(buttonHeight/2));
}



//onClickWidget is called when a widget is clicked/touched
void onClickWidget(APWidget widget) {

if (widget == redButton) { //if the red button was clicked
buttonText="RED";
background(255, 0, 0);
}
else if (widget == greenButton) { //if the green button was clicked
buttonText="GREEN";
background(0, 255, 0);
}
else if (widget == blueButton) { //if the blue button was clicked
buttonText="BLUE";
background(0, 0, 255);
}
else if (widget == offButton) { //if the off button was clicked
buttonText="OFF";
background(0);
}
}

The sketch creates 4 buttons, one for Red, Green, Blue and Off. In this example, we use the onClickWidget() method to deal with button_click events, which we use to change the colour of the background.  I forgot to include the following line in the setup() method:
  • orientation(LANDSCAPE);
This will force the application to go into landscape mode, which is what I intended.


Bluetooth Buttons : Adding Buttons to the Bluetooth project

We will now incorporate the Buttons sketch into our Bluetooth project so that when we press a button, it will send a letter to the Arduino via Bluetooth. The letter will be used by the Arduino to decide what colour to display on the Chainable RGB LED. We will still keep the previous functionality of changing the LED to RED when a successful Input/OutputStream is created, because this will be the signal to suggest that it is now ok to press the buttons (and we should see it work).

Here is the updated Android/Processing sketch

Android/Processing Sketch 8: Bluetooth App1

 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
/* BluetoothApp1: Written by ScottC on 25 March 2013 using 
Processing version 2.0b8
Tested on a Samsung Galaxy SII, with Android version 2.3.4
Android ADK - API 10 SDK platform
Apwidgets version: r44 */

import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.widget.Toast;
import android.view.Gravity;
import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothDevice;

import java.util.UUID;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import android.os.Handler;
import android.os.Message;
import android.util.Log;

import android.bluetooth.BluetoothServerSocket;
import android.bluetooth.BluetoothSocket;
import apwidgets.*;
public BluetoothSocket scSocket;


//Used for the GUI**************************************
APWidgetContainer widgetContainer;
APButton redButton, greenButton, blueButton, offButton;
String buttonText="";
int buttonWidth=0;
int buttonHeight=0;
int n=4; //number of buttons
int gap=10; //gap between buttons

boolean foundDevice=false; //When true, the screen turns green.
boolean BTisConnected=false; //When true, the screen turns purple.
String serverName = "ArduinoBasicsServer";

// Message types used by the Handler
public static final int MESSAGE_WRITE = 1;
public static final int MESSAGE_READ = 2;
String readMessage="";

//Used to send bytes to the Arduino
SendReceiveBytes sendReceiveBT=null;

//Get the default Bluetooth adapter
BluetoothAdapter bluetooth = BluetoothAdapter.getDefaultAdapter();

/*The startActivityForResult() within setup() launches an
Activity which is used to request the user to turn Bluetooth on.
The following onActivityResult() method is called when this
Activity exits. */
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
if (requestCode==0) {
if (resultCode == RESULT_OK) {
ToastMaster("Bluetooth has been switched ON");
}
else {
ToastMaster("You need to turn Bluetooth ON !!!");
}
}
}


/* Create a BroadcastReceiver that will later be used to
receive the names of Bluetooth devices in range. */
BroadcastReceiver myDiscoverer = new myOwnBroadcastReceiver();


/* Create a BroadcastReceiver that will later be used to
identify if the Bluetooth device is connected */
BroadcastReceiver checkIsConnected = new myOwnBroadcastReceiver();



// The Handler that gets information back from the Socket
private final Handler mHandler = new Handler() {
@Override
public void handleMessage(Message msg) {
switch (msg.what) {
case MESSAGE_WRITE:
//Do something when writing
break;
case MESSAGE_READ:
//Get the bytes from the msg.obj
byte[] readBuf = (byte[]) msg.obj;
// construct a string from the valid bytes in the buffer
readMessage = new String(readBuf, 0, msg.arg1);
break;
}
}
};



void setup() {
orientation(LANDSCAPE);

//Setup GUI********************************
buttonWidth=((width/n)-(n*gap));
buttonHeight=(height/2);
widgetContainer = new APWidgetContainer(this); //create new container for widgets
redButton =new APButton((buttonWidth*(n-4)+(gap*1)), gap, buttonWidth, buttonHeight, "RED"); //Create a RED button
greenButton = new APButton((buttonWidth*(n-3)+(gap*2)), gap, buttonWidth, buttonHeight, "GREEN"); //Create a GREEN button
blueButton = new APButton((buttonWidth*(n-2)+(gap*3)), gap, buttonWidth, buttonHeight, "BLUE"); //Create a BLUE button
offButton = new APButton((buttonWidth*(n-1)+(gap*4)), gap, buttonWidth, buttonHeight, "OFF"); //Create a OFF button
widgetContainer.addWidget(redButton); //place red button in container
widgetContainer.addWidget(greenButton); //place green button in container
widgetContainer.addWidget(blueButton);//place blue button in container
widgetContainer.addWidget(offButton);//place off button in container
background(0); //Start with a black background

/*IF Bluetooth is NOT enabled, then ask user permission to enable it */
if (!bluetooth.isEnabled()) {
Intent requestBluetooth = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);
startActivityForResult(requestBluetooth, 0);
}

/*If Bluetooth is now enabled, then register a broadcastReceiver to report any
discovered Bluetooth devices, and then start discovering */
if (bluetooth.isEnabled()) {
registerReceiver(myDiscoverer, new IntentFilter(BluetoothDevice.ACTION_FOUND));
registerReceiver(checkIsConnected, new IntentFilter(BluetoothDevice.ACTION_ACL_CONNECTED));

//Start bluetooth discovery if it is not doing so already
if (!bluetooth.isDiscovering()) {
bluetooth.startDiscovery();
}
}
}


void draw() {
//Display a green screen if a device has been found,
//Display a purple screen when a connection is made to the device
if (foundDevice) {
if (BTisConnected) {
background(170, 50, 255); // purple screen
}
else {
background(10, 255, 10); // green screen
}
}


//Change the text based on the button being pressed.
text(buttonText, 10, buttonHeight+(buttonHeight/2));

//Display anything received from Arduino
text(readMessage, 10, buttonHeight+(buttonHeight/2)+30);
}



/* This BroadcastReceiver will display discovered Bluetooth devices */
public class myOwnBroadcastReceiver extends BroadcastReceiver {
ConnectToBluetooth connectBT;

@Override
public void onReceive(Context context, Intent intent) {
String action=intent.getAction();
ToastMaster("ACTION:" + action);

//Notification that BluetoothDevice is FOUND
if (BluetoothDevice.ACTION_FOUND.equals(action)) {
//Display the name of the discovered device
String discoveredDeviceName = intent.getStringExtra(BluetoothDevice.EXTRA_NAME);
ToastMaster("Discovered: " + discoveredDeviceName);

//Display more information about the discovered device
BluetoothDevice discoveredDevice = intent.getParcelableExtra(BluetoothDevice.EXTRA_DEVICE);
ToastMaster("getAddress() = " + discoveredDevice.getAddress());
ToastMaster("getName() = " + discoveredDevice.getName());

int bondyState=discoveredDevice.getBondState();
ToastMaster("getBondState() = " + bondyState);

String mybondState;
switch(bondyState) {
case 10:
mybondState="BOND_NONE";
break;
case 11:
mybondState="BOND_BONDING";
break;
case 12:
mybondState="BOND_BONDED";
break;
default:
mybondState="INVALID BOND STATE";
break;
}
ToastMaster("getBondState() = " + mybondState);

//Change foundDevice to true which will make the screen turn green
foundDevice=true;

//Connect to the discovered bluetooth device (SeeedBTSlave)
if (discoveredDeviceName.equals("SeeedBTSlave")) {
ToastMaster("Connecting you Now !!");
unregisterReceiver(myDiscoverer);
connectBT = new ConnectToBluetooth(discoveredDevice);
//Connect to the the device in a new thread
new Thread(connectBT).start();
}
}

//Notification if bluetooth device is connected
if (BluetoothDevice.ACTION_ACL_CONNECTED.equals(action)) {
ToastMaster("CONNECTED _ YAY");
int counter=0;
while (scSocket==null) {
//do nothing
}
ToastMaster("scSocket" + scSocket);
BTisConnected=true; //turn screen purple
if (scSocket!=null) {
sendReceiveBT = new SendReceiveBytes(scSocket);
new Thread(sendReceiveBT).start();
String red = "r";
byte[] myByte = stringToBytesUTFCustom(red);
sendReceiveBT.write(myByte);
}
}
}
}

public static byte[] stringToBytesUTFCustom(String str) {
char[] buffer = str.toCharArray();
byte[] b = new byte[buffer.length << 1];
for (int i = 0; i < buffer.length; i++) {
int bpos = i << 1;
b[bpos] = (byte) ((buffer[i]&0xFF00)>>8);
b[bpos + 1] = (byte) (buffer[i]&0x00FF);
}
return b;
}

public class ConnectToBluetooth implements Runnable {
private BluetoothDevice btShield;
private BluetoothSocket mySocket = null;
private UUID uuid = UUID.fromString("00001101-0000-1000-8000-00805F9B34FB");

public ConnectToBluetooth(BluetoothDevice bluetoothShield) {
btShield = bluetoothShield;
try {
mySocket = btShield.createRfcommSocketToServiceRecord(uuid);
}
catch(IOException createSocketException) {
//Problem with creating a socket
Log.e("ConnectToBluetooth", "Error with Socket");
}
}

@Override
public void run() {
/* Cancel discovery on Bluetooth Adapter to prevent slow connection */
bluetooth.cancelDiscovery();

try {
/*Connect to the bluetoothShield through the Socket. This will block
until it succeeds or throws an IOException */
mySocket.connect();
scSocket=mySocket;
}
catch (IOException connectException) {
Log.e("ConnectToBluetooth", "Error with Socket Connection");
try {
mySocket.close(); //try to close the socket
}
catch(IOException closeException) {
}
return;
}
}

// Will allow you to get the socket from this class
public BluetoothSocket getSocket() {
return mySocket;
}

/* Will cancel an in-progress connection, and close the socket */
public void cancel() {
try {
mySocket.close();
}
catch (IOException e) {
}
}
}



private class SendReceiveBytes implements Runnable {
private BluetoothSocket btSocket;
private InputStream btInputStream = null;
;
private OutputStream btOutputStream = null;
String TAG = "SendReceiveBytes";

public SendReceiveBytes(BluetoothSocket socket) {
btSocket = socket;
try {
btInputStream = btSocket.getInputStream();
btOutputStream = btSocket.getOutputStream();
}
catch (IOException streamError) {
Log.e(TAG, "Error when getting input or output Stream");
}
}

public void run() {
byte[] buffer = new byte[1024]; // buffer store for the stream
int bytes; // bytes returned from read()

// Keep listening to the InputStream until an exception occurs
while (true) {
try {
// Read from the InputStream
bytes = btInputStream.read(buffer);
// Send the obtained bytes to the UI activity
mHandler.obtainMessage(MESSAGE_READ, bytes, -1, buffer)
.sendToTarget();
}
catch (IOException e) {
Log.e(TAG, "Error reading from btInputStream");
break;
}
}
}

/* Call this from the main activity to send data to the remote device */
public void write(byte[] bytes) {
try {
btOutputStream.write(bytes);
}
catch (IOException e) {
Log.e(TAG, "Error when writing to btOutputStream");
}
}

/* Call this from the main activity to shutdown the connection */
public void cancel() {
try {
btSocket.close();
}
catch (IOException e) {
Log.e(TAG, "Error when closing the btSocket");
}
}
}



/* My ToastMaster function to display a messageBox on the screen */
void ToastMaster(String textToDisplay) {
Toast myMessage = Toast.makeText(getApplicationContext(),
textToDisplay,
Toast.LENGTH_SHORT);
myMessage.setGravity(Gravity.CENTER, 0, 0);
myMessage.show();
}




//onClickWidget is called when a widget is clicked/touched
void onClickWidget(APWidget widget) {
String sendLetter = "";

//Disable the previous Background colour changers
foundDevice=false;
BTisConnected=false;

if (widget == redButton) { //if the red button was clicked
buttonText="RED";
background(255, 0, 0);
sendLetter = "r";
}
else if (widget == greenButton) { //if the green button was clicked
buttonText="GREEN";
background(0, 255, 0);
sendLetter = "g";
}
else if (widget == blueButton) { //if the blue button was clicked
buttonText="BLUE";
background(0, 0, 255);
sendLetter = "b";
}
else if (widget == offButton) { //if the off button was clicked
buttonText="OFF";
background(0);
sendLetter = "x";
}

byte[] myByte = stringToBytesUTFCustom(sendLetter);
sendReceiveBT.write(myByte);
}
The sketch above has been thrown together without much planning or consideration for code efficiency. It was deliberately done this way so that you could see and follow the incremental approach used to create this Android/Processing Bluetooth App. I will do my best to rewrite and simplify some of the code, however, I don't anticipate the final sketch will be a short script.
You should have noticed that I included a fourth button called an "off" button. This will turn off the RGB led. However, the Arduino code in its current format does not know what to do with an 'x'. So we will update the sketch as follows:

Arduino Sketch 3: Bluetooth RGB Colour Changer (with OFF option)

 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
/* This project combines the code from a few different sources.
This project was put together by ScottC on the 15/01/2013
http://arduinobasics.blogspot.com/

Bluetooth slave code by Steve Chang - downloaded from :
http://www.seeedstudio.com/wiki/index.php?title=Bluetooth_Shield

Grove Chainable RGB code can be found here :
http://www.seeedstudio.com/wiki/Grove_-_Chainable_RGB_LED#Introduction

Updated on 25 March 2013: Receive 'x' to turn off RGB LED.

*/

#include <SoftwareSerial.h> //Software Serial Port

#define uint8 unsigned char
#define uint16 unsigned int
#define uint32 unsigned long int

#define RxD 6 // This is the pin that the Bluetooth (BT_TX) will transmit to the Arduino (RxD)
#define TxD 7 // This is the pin that the Bluetooth (BT_RX) will receive from the Arduino (TxD)

#define DEBUG_ENABLED 1

int Clkpin = 9; //RGB LED Clock Pin (Digital 9)
int Datapin = 8; //RGB LED Data Pin (Digital 8)

SoftwareSerial blueToothSerial(RxD, TxD);


/*----------------------SETUP----------------------------*/
void setup() {
Serial.begin(9600); // Allow Serial communication via USB cable to computer (if required)
pinMode(RxD, INPUT); // Setup the Arduino to receive INPUT from the bluetooth shield on Digital Pin 6
pinMode(TxD, OUTPUT); // Setup the Arduino to send data (OUTPUT) to the bluetooth shield on Digital Pin 7
pinMode(13, OUTPUT); // Use onboard LED if required.
setupBlueToothConnection(); //Used to initialise the Bluetooth shield

pinMode(Datapin, OUTPUT); // Setup the RGB LED Data Pin
pinMode(Clkpin, OUTPUT); // Setup the RGB LED Clock pin
}


/*----------------------LOOP----------------------------*/
void loop() {
digitalWrite(13, LOW); //Turn off the onboard Arduino LED
char recvChar;
while (1) {
if (blueToothSerial.available()) {//check if there's any data sent from the remote bluetooth shield
recvChar = blueToothSerial.read();
Serial.print(recvChar); // Print the character received to the Serial Monitor (if required)

//If the character received = 'r' , then change the RGB led to display a RED colour
if (recvChar=='r') {
Send32Zero(); // begin
DataDealWithAndSend(255, 0, 0); // first node data
Send32Zero(); // send to update data
}

//If the character received = 'g' , then change the RGB led to display a GREEN colour
if (recvChar=='g') {
Send32Zero(); // begin
DataDealWithAndSend(0, 255, 0); // first node data
Send32Zero(); // send to update data
}

//If the character received = 'b' , then change the RGB led to display a BLUE colour
if (recvChar=='b') {
Send32Zero(); // begin
DataDealWithAndSend(0, 0, 255); // first node data
Send32Zero(); // send to update data
}

//If the character received = 'x' , then turn RGB led OFF
if (recvChar=='x') {
Send32Zero(); // begin
DataDealWithAndSend(0, 0, 0); // first node data
Send32Zero(); // send to update data
}
}

//You can use the following code to deal with any information coming from the Computer (serial monitor)
if (Serial.available()) {
recvChar = Serial.read();

//This will send value obtained (recvChar) to the phone. The value will be displayed on the phone.
blueToothSerial.print(recvChar);
}
}
}



//The following code is necessary to setup the bluetooth shield ------copy and paste----------------
void setupBlueToothConnection()
{
blueToothSerial.begin(38400); //Set BluetoothBee BaudRate to default baud rate 38400
blueToothSerial.print("\r\n+STWMOD=0\r\n"); //set the bluetooth work in slave mode
blueToothSerial.print("\r\n+STNA=SeeedBTSlave\r\n"); //set the bluetooth name as "SeeedBTSlave"
blueToothSerial.print("\r\n+STOAUT=1\r\n"); // Permit Paired device to connect me
blueToothSerial.print("\r\n+STAUTO=0\r\n"); // Auto-connection should be forbidden here
delay(2000); // This delay is required.
blueToothSerial.print("\r\n+INQ=1\r\n"); //make the slave bluetooth inquirable
Serial.println("The slave bluetooth is inquirable!");
delay(2000); // This delay is required.
blueToothSerial.flush();
}


//The following code snippets are used update the colour of the RGB LED-----copy and paste------------
void ClkProduce(void) {
digitalWrite(Clkpin, LOW);
delayMicroseconds(20);
digitalWrite(Clkpin, HIGH);
delayMicroseconds(20);
}
void Send32Zero(void) {
unsigned char i;
for (i=0; i<32; i++) {
digitalWrite(Datapin, LOW);
ClkProduce();
}
}



uint8 TakeAntiCode(uint8 dat) {
uint8 tmp = 0;
if ((dat & 0x80) == 0) {
tmp |= 0x02;
}

if ((dat & 0x40) == 0) {
tmp |= 0x01;
}
return tmp;
}


// gray data
void DatSend(uint32 dx) {
uint8 i;
for (i=0; i<32; i++) {
if ((dx & 0x80000000) != 0) {
digitalWrite(Datapin, HIGH);
}
else {
digitalWrite(Datapin, LOW);
}
dx <<= 1;
ClkProduce();
}
}

// data processing
void DataDealWithAndSend(uint8 r, uint8 g, uint8 b) {
uint32 dx = 0;

dx |= (uint32)0x03 << 30; // highest two bits 1,flag bits
dx |= (uint32)TakeAntiCode(b) << 28;
dx |= (uint32)TakeAntiCode(g) << 26;
dx |= (uint32)TakeAntiCode(r) << 24;

dx |= (uint32)b << 16;
dx |= (uint32)g << 8;
dx |= r;

DatSend(dx);
}



Well that concludes part 3.
Part 4 is a summary of the finished project with videos, screenshots, parts used etc.
I hope you found this tutorial useful. I would love to receive any advice on how I could improve these tutorials (please put your recommendations in comments below).

Reason for this Project:
While there are quite a few people creating Android/Arduino projects, I have not been able to find many that show how these are being accomplished using the Android/Processing IDE, and even less on how they are using Bluetooth in their Android/Processing projects. I hope my piecing of information will spark some creative Bluetooth projects of your own.



PART 4: Navigate here.





Pics captured during programming RGB LED...

Thats an interesting an captivating slideshow of some pics captured during programming a RGB LED to glow in different shades through Arduino...
Let's Make Robots 06 Feb 14:04

Glowing RGB LED... My 1st Arduino Program...

7 different shades of RGB LED.. Enjoy watching it..

Arduino based RGB LED

The RGB led glows in 7 colors and at 2 different rates. Hope you like it......Cheers......

LED cloud lamp in any color you can image

This lamp which [Bablondeemu] built will add a little whimsy to your home decor. The project started as coursework for a Digital Art and Installations class. But the remote controlled color changing cloud ended up being a pretty neat gift for his little brother.

The prototype uses an Arduino, breadboard, and a collection of LEDs to perform its tasks. [Bablondeemu] admits the next revision should have a standalone circuit board. The electronics are housed in a clear plastic container which was then adorned with Polyfill stuffing which would commonly be found inside a decorative pillow. The polyester fibers do a great job or filtering and diffusing the light. But they don’t seem to interfere with the incoming IR signals from the remote control.

If you like the idea of creatively shaped diffusers you should take a look at this giant LED lamp. It’s molded to look like a through-hole package with the leads hiding the power cord.


Filed under: led hacks
Hack a Day 17 Jan 18:01
arduino  cloud  led  led hacks  rgb  

Bluetooth Tutorial 1


Introduction:
The bluetooth shield used in this project is a great way to detach the Arduino from your computer. What is even better, is that the shield allows you to control your arduino from your mobile phone or other bluetooth enabled device through simple Serial commands. In this tutorial we will connect a Grove Chainable RGB LED to the bluetooth shield directly, and send simple commands using the Bluetooth SPP app on a Samsung Galaxy S2 to change the colour of the LED (Red , Green and Blue)



Parts Required:
Freetronics Eleven or any compatible Arduino.
Bluetooth shield
Grove Chainable RGB LED
Grove Wire connectors




The Video:





The Arduino Sketch:








Arduino Code:
You can download the Arduino IDE from this site.


 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
/* This project combines the code from a few different sources.
This project was put together by ScottC on the 15/01/2013
http://arduinobasics.blogspot.com/

Bluetooth slave code by Steve Chang - downloaded from :
http://www.seeedstudio.com/wiki/index.php?title=Bluetooth_Shield

Grove Chainable RGB code can be found here :
http://www.seeedstudio.com/wiki/Grove_-_Chainable_RGB_LED#Introduction

*/

#include <SoftwareSerial.h> //Software Serial Port

#define uint8 unsigned char
#define uint16 unsigned int
#define uint32 unsigned long int

#define RxD 6 // This is the pin that the Bluetooth (BT_TX) will transmit to the Arduino (RxD)
#define TxD 7 // This is the pin that the Bluetooth (BT_RX) will receive from the Arduino (TxD)

#define DEBUG_ENABLED 1


int Clkpin = 9; //RGB LED Clock Pin (Digital 9)
int Datapin = 8; //RGB LED Data Pin (Digital 8)

SoftwareSerial blueToothSerial(RxD,TxD);

/*----------------------SETUP----------------------------*/
void setup() {
Serial.begin(9600); // Allow Serial communication via USB cable to computer (if required)
pinMode(RxD, INPUT); // Setup the Arduino to receive INPUT from the bluetooth shield on Digital Pin 6
pinMode(TxD, OUTPUT); // Setup the Arduino to send data (OUTPUT) to the bluetooth shield on Digital Pin 7
pinMode(13,OUTPUT); // Use onboard LED if required.
setupBlueToothConnection(); //Used to initialise the Bluetooth shield

pinMode(Datapin, OUTPUT); // Setup the RGB LED Data Pin
pinMode(Clkpin, OUTPUT); // Setup the RGB LED Clock pin

}

/*----------------------LOOP----------------------------*/
void loop() {
digitalWrite(13,LOW); //Turn off the onboard Arduino LED
char recvChar;
while(1){
if(blueToothSerial.available()){//check if there's any data sent from the remote bluetooth shield
recvChar = blueToothSerial.read();
Serial.print(recvChar); // Print the character received to the Serial Monitor (if required)

//If the character received = 'r' , then change the RGB led to display a RED colour
if(recvChar=='r'){
Send32Zero(); // begin
DataDealWithAndSend(255, 0, 0); // first node data
Send32Zero(); // send to update data
}

//If the character received = 'g' , then change the RGB led to display a GREEN colour
if(recvChar=='g'){
Send32Zero(); // begin
DataDealWithAndSend(0, 255, 0); // first node data
Send32Zero(); // send to update data
}

//If the character received = 'b' , then change the RGB led to display a BLUE colour
if(recvChar=='b'){
Send32Zero(); // begin
DataDealWithAndSend(0, 0, 255); // first node data
Send32Zero(); // send to update data
}
}

//You can use the following code to deal with any information coming from the Computer (serial monitor)
if(Serial.available()){
recvChar = Serial.read();

//This will send value obtained (recvChar) to the phone. The value will be displayed on the phone.
blueToothSerial.print(recvChar);
}
}
}


//The following code is necessary to setup the bluetooth shield ------copy and paste----------------
void setupBlueToothConnection()
{
blueToothSerial.begin(38400); //Set BluetoothBee BaudRate to default baud rate 38400
blueToothSerial.print("\r\n+STWMOD=0\r\n"); //set the bluetooth work in slave mode
blueToothSerial.print("\r\n+STNA=SeeedBTSlave\r\n"); //set the bluetooth name as "SeeedBTSlave"
blueToothSerial.print("\r\n+STOAUT=1\r\n"); // Permit Paired device to connect me
blueToothSerial.print("\r\n+STAUTO=0\r\n"); // Auto-connection should be forbidden here
delay(2000); // This delay is required.
blueToothSerial.print("\r\n+INQ=1\r\n"); //make the slave bluetooth inquirable
Serial.println("The slave bluetooth is inquirable!");
delay(2000); // This delay is required.
blueToothSerial.flush();
}


//The following code snippets are used update the colour of the RGB LED-----copy and paste------------
void ClkProduce(void){
digitalWrite(Clkpin, LOW);
delayMicroseconds(20);
digitalWrite(Clkpin, HIGH);
delayMicroseconds(20);
}

void Send32Zero(void){
unsigned char i;
for (i=0; i<32; i++){
digitalWrite(Datapin, LOW);
ClkProduce();
}
}

uint8 TakeAntiCode(uint8 dat){
uint8 tmp = 0;
if ((dat & 0x80) == 0){
tmp |= 0x02;
}

if ((dat & 0x40) == 0){
tmp |= 0x01;
}

return tmp;
}

// gray data
void DatSend(uint32 dx){
uint8 i;
for (i=0; i<32; i++){
if ((dx & 0x80000000) != 0){
digitalWrite(Datapin, HIGH);
} else {
digitalWrite(Datapin, LOW);
}

dx <<= 1;
ClkProduce();
}
}

// data processing
void DataDealWithAndSend(uint8 r, uint8 g, uint8 b){
uint32 dx = 0;

dx |= (uint32)0x03 << 30; // highest two bits 1,flag bits
dx |= (uint32)TakeAntiCode(b) << 28;
dx |= (uint32)TakeAntiCode(g) << 26;
dx |= (uint32)TakeAntiCode(r) << 24;

dx |= (uint32)b << 16;
dx |= (uint32)g << 8;
dx |= r;

DatSend(dx);
}

The code above was formatted using hilite.me

Notes:
You don't need to download a library to get this project running. But if you plan to use bluetooth shields to get 2 Arduinos to communicate to each other, then I would advise that you download the library files (which are just examples) from the Seeedstudio site : here.

Visit this site to setup your phone or laptop for bluetooth communication to the shield - here

The app used on my Samsung Galaxy S2 phone was "Bluetooth SPP"

You will initially need to enter a pin of '0000' to establish a connection to the Bluetooth shield - which will appear as "SeeedBTSlave" or whatever text you place on line 90 of the Arduino code above.





Warning !

Not all phones are compatible with the bluetooth shield.
If you have used this shield before - please let me know what phone you used - so that we can build a list and inform others whether their phone is likely to work with this project or not. Obviously - those phones that do not have bluetooth within - will not work :).
And I have not tried any other apps either

I got it to work very easily with my Samsung Galaxy S2 using the free Bluetooth SPP app from the google play store.

This was fun, but I want to make my own app !
Have a look at my latest 4-part tutorial which takes you step-by-step through the process of building your own app using the Processing/Android IDE.
You can build your own GUI interface on your Android Phone and get it to communicate via Bluetooth to your Arduino/Bluetooth Shield. Click on the links below for more information:




 
 



If you like this page, please do me a favour and show your appreciation :

 
Visit my ArduinoBasics Google + page.
Follow me on Twitter by looking for ScottC @ArduinoBasics.
Have a look at my videos on my YouTube channel.


 
 

 
 
 



However, if you do not have a google profile...
Feel free to share this page with your friends in any way you see fit.

An Arduino-controlled RGB lamp

On his blog, Miguel presents one of his latest projects:

This project shows the operation of an RGB lamp using a digital LED strip. After activating the bluetooth connection, the user can open the GUI on the PC to control the lamp. The program shows a hue palette divided into 30 rods, one for each LED of the strip.
By clicking & dragging the mouse cursor it is possible to make your own patterns,. To remove a color, the user can simply click on a rod while pressing the spacebar, which switches off the selected LED.

Part list: wooden support, RGB digitally-addressable LED strip, microcontroller (Arduino Pro Mini, for example), Bluetooth or USB wire.

More information on this project can be found on Miguel’s blog, while a brief video about its operation can be found here; the code of the project can be found on Github. The project’s page on Thingiverse can be found here.

[Via: Miguel's blog]

 

Arduino Blog 12 Jan 09:20