A few weeks ago I was asked about creating a musical-effect display with an RGB LED cube kit from Freetronics, and with a little work this was certainly possible using the MSGEQ7 spectrum analyser IC. In this project we’ll create a small add-on PCB containing the spectrum analyser circuit and show how it can drive the RGB LED cube kit.

You can get MSGEQ7 ICs from various sources, however they had varying results. We now recommend using the neat module from Tronixlabs.

The circuit

The LED cube already has an Arduino Leonardo-compatible built in to the main PCB, so all you need to do is build a small circuit that contains the spectrum analyzer which connects to the I/O pins on the cube PCB and also has audio input and output connections. First, consider the schematic:

For the purposes of this project our spectrum analyser will only display the results from one channel of audio – if you want stereo, you’ll need two! And note that the strobe, reset and DCOUT pins on the MSGEQ7 are labelled with the connections to the cube PCB. Furthermore the pinouts for the MSGEQ7 don’t match the physical reality – here are the pinouts from the MSGEQ7 data sheet (.pdf):

The circuit itself will be quite small and fit on a small amount of stripboard or veroboard. There is plenty of room underneath the cube to fit the circuit if so desired:

With a few moments you should be able to trace out your circuit to match the board type you have, remember to double-check before soldering. You will also need to connect the audio in point after the 1000 pF capacitor to a source of audio, and also pass it through so you can connect powered speakers, headphones, etc.

One method of doing so would be to cut up a male-female audio extension lead, and connect the shield to the GND of the circuit, and the signal line to the audio input on the circuit. Or if you have the parts handy and some shielded cable, just make your own input and output leads:

Be sure to test for shorts between the signal and shield before soldering to the circuit board. When finished, you should have something neat that you can hide under the cube or elsewhere:

Double-check your soldering for shorts and your board plan, then fit to the cube along with the audio source and speakers (etc).

Arduino Sketch

The sketch has two main functions – the first is to capture the levels from the MSGEQ7 and put the values for each frequency band into an array, and the second function is to turn on LEDs that represent the level for each band. If you’ve been paying attention you may be wondering how we can represent seven frequency bands with a 4x4x4 LED cube. Simple – by rotating the cube 45 degrees you can see seven vertical columns of LEDs:

So when looking from the angle as shown above, you have seven vertical columns, each with four levels of LEDs. Thus the strength of each frequency can be broken down into four levels, and then the appropriate LEDs turned on.

After this is done for each band, all the LEDs are turned off and the process repeats. For the sake of simplicity I’ve used the cube’s Arduino library to activate the LEDs, which also makes the sketch easier to fathom. The first example sketch only uses one colour:

Arduino

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

// Freetronics CUBE4: and MSGEQ7 spectrum analyser

// MSGEQ7 strobe on A4, reset on D5, signal into A0

#include "SPI.h"

#include "Cube.h"

Cubecube;

intres=5;// reset pins on D5

intleft[7];// store band values in these arrays

intband;

voidsetup()

{

pinMode(res,OUTPUT);// reset

pinMode(A4,OUTPUT);// strobe

digitalWrite(res,LOW);

digitalWrite(A4,HIGH);

cube.begin(-1,115200);

Serial.begin(9600);

}

voidreadMSGEQ7()

// Function to read 7 band equalizers

{

digitalWrite(res,HIGH);

digitalWrite(res,LOW);

for(band=0;band<7;band++)

{

digitalWrite(A4,LOW);// strobe pin on the shield - kicks the IC up to the next band

delayMicroseconds(30);//

left[band]=analogRead(0);// store band reading

digitalWrite(A4,HIGH);

}

}

voidloop()

{

readMSGEQ7();

for(band=0;band<7;band++)

{

// div each band strength into four layers, each band then one of the odd diagonals

// band one ~ 63 Hz

if(left[0]>=768){

cube.set(3,3,3,BLUE);

}

else

if(left[0]>=512){

cube.set(3,3,2,BLUE);

}

else

if(left[0]>=256){

cube.set(3,3,1,BLUE);

}

else

if(left[0]>=0){

cube.set(3,3,0,BLUE);

}

// band two ~ 160 Hz

if(left[1]>=768)

{

cube.set(3,2,3,BLUE);

cube.set(2,3,3,BLUE);

}

else

if(left[1]>=512)

{

cube.set(3,2,2,BLUE);

cube.set(2,3,2,BLUE);

}

else

if(left[1]>=256)

{

cube.set(3,2,1,BLUE);

cube.set(2,3,1,BLUE);

}

else

if(left[1]>=0)

{

cube.set(3,2,0,BLUE);

cube.set(2,3,0,BLUE);

}

// band three ~ 400 Hz

if(left[2]>=768)

{

cube.set(3,1,3,BLUE);

cube.set(2,2,3,BLUE);

cube.set(1,3,3,BLUE);

}

else

if(left[2]>=512)

{

cube.set(3,1,2,BLUE);

cube.set(2,2,2,BLUE);

cube.set(1,3,2,BLUE);

}

else

if(left[2]>=256)

{

cube.set(3,1,1,BLUE);

cube.set(2,2,1,BLUE);

cube.set(1,3,1,BLUE);

}

else

if(left[2]>=0)

{

cube.set(3,1,0,BLUE);

cube.set(2,2,0,BLUE);

cube.set(1,3,0,BLUE);

}

// band four ~ 1 kHz

if(left[3]>=768)

{

cube.set(3,0,3,BLUE);

cube.set(2,1,3,BLUE);

cube.set(1,2,3,BLUE);

cube.set(0,3,3,BLUE);

}

else

if(left[3]>=512)

{

cube.set(3,0,2,BLUE);

cube.set(2,1,2,BLUE);

cube.set(1,2,2,BLUE);

cube.set(0,3,2,BLUE);

}

else

if(left[3]>=256)

{

cube.set(3,0,1,BLUE);

cube.set(2,1,1,BLUE);

cube.set(1,2,1,BLUE);

cube.set(0,3,1,BLUE);

}

else

if(left[3]>=0)

{

cube.set(3,0,0,BLUE);

cube.set(2,1,0,BLUE);

cube.set(1,2,0,BLUE);

cube.set(0,3,0,BLUE);

}

// band five ~ 2.5 kHz

if(left[4]>=768)

{

cube.set(2,0,3,BLUE);

cube.set(1,1,3,BLUE);

cube.set(0,2,3,BLUE);

}

else

if(left[4]>=512)

{

cube.set(2,0,2,BLUE);

cube.set(1,1,2,BLUE);

cube.set(0,2,2,BLUE);

}

else

if(left[4]>=256)

{

cube.set(2,0,1,BLUE);

cube.set(1,1,1,BLUE);

cube.set(0,2,1,BLUE);

}

else

if(left[4]>=0)

{

cube.set(2,0,0,BLUE);

cube.set(1,1,0,BLUE);

cube.set(0,2,0,BLUE);

}

// band six ~ 6.25 kHz

if(left[5]>=768)

{

cube.set(1,0,3,BLUE);

cube.set(0,1,3,BLUE);

}

else

if(left[5]>=512)

{

cube.set(1,0,2,BLUE);

cube.set(0,1,2,BLUE);

}

else

if(left[5]>=256)

{

cube.set(1,0,1,BLUE);

cube.set(0,1,1,BLUE);

}

else

if(left[5]>=0)

{

cube.set(1,0,0,BLUE);

cube.set(0,1,0,BLUE);

}

// band seven ~ 16 kHz

if(left[6]>=768)

{

cube.set(0,0,3,BLUE);

}

else

if(left[6]>=512)

{

cube.set(0,0,2,BLUE);

}

else

if(left[6]>=256)

{

cube.set(0,0,1,BLUE);

}

else

if(left[6]>=0)

{

cube.set(0,0,0,BLUE);

}

}

// now clear the CUBE, or if that's too slow - repeat the process but turn LEDs off

cube.all(BLACK);

}

… and a quick video demonstration:

For a second example, we’ve used various colours:

Arduino

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

// Freetronics CUBE4: and MSGEQ7 spectrum analyser

// MSGEQ7 strobe on A4, reset on D5, signal into A0

// now in colour!

#include "SPI.h"

#include "Cube.h"

Cubecube;

intres=5;// reset pins on D5

intleft[7];// store band values in these arrays

intband;

intadditional=0;

voidsetup()

{

pinMode(res,OUTPUT);// reset

pinMode(A4,OUTPUT);// strobe

digitalWrite(res,LOW);

digitalWrite(A4,HIGH);

cube.begin(-1,115200);

Serial.begin(9600);

}

voidreadMSGEQ7()

// Function to read 7 band equalizers

{

digitalWrite(res,HIGH);

digitalWrite(res,LOW);

for(band=0;band<7;band++)

{

digitalWrite(A4,LOW);// strobe pin on the shield - kicks the IC up to the next band

delayMicroseconds(30);//

left[band]=analogRead(0)+additional;// store band reading

digitalWrite(A4,HIGH);

}

}

voidloop()

{

readMSGEQ7();

for(band=0;band<7;band++)

{

// div each band strength into four layers, each band then one of the odd diagonals

// band one ~ 63 Hz

if(left[0]>=768){

cube.set(3,3,3,RED);

}

else

if(left[0]>=512){

cube.set(3,3,2,YELLOW);

}

else

if(left[0]>=256){

cube.set(3,3,1,YELLOW);

}

else

if(left[0]>=0){

cube.set(3,3,0,BLUE);

}

// band two ~ 160 Hz

if(left[1]>=768)

{

cube.set(3,2,3,RED);

cube.set(2,3,3,RED);

}

else

if(left[1]>=512)

{

cube.set(3,2,2,YELLOW);

cube.set(2,3,2,YELLOW);

}

else

if(left[1]>=256)

{

cube.set(3,2,1,YELLOW);

cube.set(2,3,1,YELLOW);

}

else

if(left[1]>=0)

{

cube.set(3,2,0,BLUE);

cube.set(2,3,0,BLUE);

}

// band three ~ 400 Hz

if(left[2]>=768)

{

cube.set(3,1,3,RED);

cube.set(2,2,3,RED);

cube.set(1,3,3,RED);

}

else

if(left[2]>=512)

{

cube.set(3,1,2,YELLOW);

cube.set(2,2,2,YELLOW);

cube.set(1,3,2,YELLOW);

}

else

if(left[2]>=256)

{

cube.set(3,1,1,YELLOW);

cube.set(2,2,1,YELLOW);

cube.set(1,3,1,YELLOW);

}

else

if(left[2]>=0)

{

cube.set(3,1,0,BLUE);

cube.set(2,2,0,BLUE);

cube.set(1,3,0,BLUE);

}

// band four ~ 1 kHz

if(left[3]>=768)

{

cube.set(3,0,3,RED);

cube.set(2,1,3,RED);

cube.set(1,2,3,RED);

cube.set(0,3,3,RED);

}

else

if(left[3]>=512)

{

cube.set(3,0,2,YELLOW);

cube.set(2,1,2,YELLOW);

cube.set(1,2,2,YELLOW);

cube.set(0,3,2,YELLOW);

}

else

if(left[3]>=256)

{

cube.set(3,0,1,YELLOW);

cube.set(2,1,1,YELLOW);

cube.set(1,2,1,YELLOW);

cube.set(0,3,1,YELLOW);

}

else

if(left[3]>=0)

{

cube.set(3,0,0,BLUE);

cube.set(2,1,0,BLUE);

cube.set(1,2,0,BLUE);

cube.set(0,3,0,BLUE);

}

// band five ~ 2.5 kHz

if(left[4]>=768)

{

cube.set(2,0,3,RED);

cube.set(1,1,3,RED);

cube.set(0,2,3,RED);

}

else

if(left[4]>=512)

{

cube.set(2,0,2,YELLOW);

cube.set(1,1,2,YELLOW);

cube.set(0,2,2,YELLOW);

}

else

if(left[4]>=256)

{

cube.set(2,0,1,YELLOW);

cube.set(1,1,1,YELLOW);

cube.set(0,2,1,YELLOW);

}

else

if(left[4]>=0)

{

cube.set(2,0,0,BLUE);

cube.set(1,1,0,BLUE);

cube.set(0,2,0,BLUE);

}

// band six ~ 6.25 kHz

if(left[5]>=768)

{

cube.set(1,0,3,RED);

cube.set(0,1,3,RED);

}

else

if(left[5]>=512)

{

cube.set(1,0,2,YELLOW);

cube.set(0,1,2,YELLOW);

}

else

if(left[5]>=256)

{

cube.set(1,0,1,YELLOW);

cube.set(0,1,1,YELLOW);

}

else

if(left[5]>=0)

{

cube.set(1,0,0,BLUE);

cube.set(0,1,0,BLUE);

}

// band seven ~ 16 kHz

if(left[6]>=768)

{

cube.set(0,0,3,RED);

}

else

if(left[6]>=512)

{

cube.set(0,0,2,YELLOW);

}

else

if(left[6]>=256)

{

cube.set(0,0,1,YELLOW);

}

else

if(left[6]>=0)

{

cube.set(0,0,0,BLUE);

}

}

// now clear the CUBE, or if that's too slow - repeat the process but turn LEDs off

cube.all(BLACK);

}

… and the second video demonstration:

A little bit of noise comes through into the spectrum analyser, most likely due to the fact that the entire thing is unshielded. The previous prototype used the Arduino shield from the tutorial which didn’t have this problem, so if you’re keen perhaps make your own custom PCB for this project.

Have fun and keep checking into tronixstuff.com. Why not follow things on twitter, Google+, subscribe for email updates or RSS using the links on the right-hand column, or join our forum – dedicated to the projects and related items on this website.

In this tutorial you learn how to make a blinking clock with a difference!

Updated 18/03/2013

Followers of my website would realise that I tend to make too many clocks in those tutorials. Well, I like making clocks… so here is another one. However this time I have tried to make the most simple version possible. Usually projects will have many LEDs, or perhaps an LCD, buzzers, buttons, all sorts of things. Which looks great and will impress many. But the other day I thought to myself … “how few things do you need to show the time?”

So here is my answer to that question: Blinky the one-eyed clock …

It reminds me of the giant killer orb from The Prisoner… Using a minimal Arduino bootloader system, a DS1307 real time clock IC and an RGB diffused LED … we can make a clock that blinks the time, using the colours of the LED to note different numerical values. For example, if the time is 12:45, the clock will blink red 12 times, then show blue for a second (think of this as the colon on a digital clock) then blink four times in green (for forty minutes), then blink three times in red for the individual minutes. If there is a zero, blink blue quickly. Then the clock will not display anything for around forty seconds, then repeat the process. Here he (she, it?) is blinking the time:

Setting the clock is simple. It is set to start at 12:00 upon power up. So for the first use you have to wait until about five seconds before midday or midnight, then power it up. To save cost it doesn’t use a backup lithium battery on the real-time clock IC, but you could if you really wanted to. If you would like to follow my design process narrative, please read on. If you only want the sketch and schematic, 🙁 head to the bottom of this article.

Design process narrative…

So let’s get started!

The first thing to do was test the RGB LED for brightness levels, so I just connected it to the digital output pins of my Eleven via suitable current-limiting resistors. Each LED is going to be different, so to ensure maximum brightness without causing any damage you need to calculate the appropriate resistor values. This is quite easy, the formula is: resistor (ohms) = voltage drop / LED current So if you have a 5 V supply, and LED that needs only 2 volts, and draws 20 milliamps (0.2 amps) , the calculation will be: resistor = (5-2)/0.02 = 150 ohms. To be safe I used a 180 ohm resistor. The LED was tested with this simple sketch:

Arduino

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

/*

blinky LED test

*/

intred=2;

intgreen=3;

intblue=4;

intd=300;

voidsetup()

{

pinMode(red,OUTPUT);

pinMode(green,OUTPUT);

pinMode(blue,OUTPUT);

}

voidloop()

{

digitalWrite(red,HIGH);

delay(d);

digitalWrite(red,LOW);

delay(d);

digitalWrite(green,HIGH);

delay(d);

digitalWrite(green,LOW);

delay(d);

digitalWrite(blue,HIGH);

delay(d);

digitalWrite(blue,LOW);

delay(d);

}

It was interesting to alter the value of d, the delay variable, to get an idea for an appropriate blinking speed. Originally the plan was to have the LED in a photo frame, but it was decided to mount a ping-pong ball over the LED for a retro-style look. Here is a short video of the result of the test:

If you are going to use a ping-pong ball, please be careful when cutting into it with a knife, initially it may require a lot of force, but once the knife cuts through it does so very quickly:

Now it was time to develop the sketch to convert time into blinks. The sketch itself is quite simple. Read the hours and minutes from the DS1307 timer IC; convert the hours to 12 hour time; then blink an LED for the number of hours, display another colour for the colon; divide the minutes by ten and blink that in another colour; then the modulus of minutes and ten to find the individual minutes, and blink those out. Here is the first sketch I came up with. Finally, the code was tested using the Eleven board and my DS1307 real time clock shield. It is best to use existing hardware while testing, before committing to purchasing new hardware and so on. So here it is on the breadboard:

And telling the time! In this example, the time is 3:45…

But perhaps that was a little bland. By using analogWrite() we can control the brightness of the LED segments. So now there are two more functions, whiteGlow() and blueGlow(); whose purpose is to make the display “glow” by increasing then decreasing the brightness. And scale back the amount of blinking, to increase battery life and make blinky less obvious. So now the display will glow white to announce the forthcoming display of time, wait a second, blink the time (with a blue glowing colon) then stay dark for ten seconds before repeating the process. Here is a quick demonstration of this display style:

Here is the sketch for the above demonstration, and the final one I will use with the hardware prototype. Once happy with the sketch, I put a fresh ATmega328 with Arduino bootloader in the board and programmed it with the blinky sketch, to be used in the final product.

Next was to build my own hardware. My last hardware unknown is the amount of current the circuit draws. Once I know this the correct voltage regulator and power supply can be decided upon. I had a fair idea it would be less than 100 milliamps, so I put a 6V battery onto supply duty via a 78L05 5V regulator (data sheet), and recorded the result:

So it varies, between 20.5 and 46 mA. As it only reaches 46 mA for a short time, we could consider the constant draw to be averaged out at 30 mA. I really want this to be able to run from a battery, but without having an external lead-acid battery lurking around, it will need a plug-pack with an output voltage greater than 7V DC. Another alternative would be to run it from a USB socket, a nice source of 5V. If doing so, there wouldn’t be a need for the 78L05 regulator. Which brings us to the circuit diagram, which includes the power regulator:

It does not allow for programming in the circuit, so you will need to program the microcontroller on another Arduino or compatible board, then transfer it to the blinky circuit board as described above. At this stage I tested it again, but using a solderless breadboard. In doing so you can make final hardware checks, and generally make sure everything works as it should. This is also a good stage to double-check you are happy with the display behaviour, default time and so on.

Time to solder up the circuit on some stripboard. Blank stripboard varies, but luckily I found this and a nice box to hold it in:

Stripboard does vary between retailers and so on, so you will need to work out the layout with your own board. In doing so, please double-check your work – follow the layout against the schematic and so on. Have a break, then check it again. There is nothing worse than soldering away to realise you are one strip too far over or something. My hand-eye coordination is not the best, therefore my soldering isn’t pretty, but it works:

One would say that there is a good argument for making your own PCBs… and I would start to agree with that. The LED is soldered to some short leads to give it a bit of play, and some heatshrink over the legs to keep them isolated:

And finally, to add a DC socket to feed blinky some power…

The last thing was to check the soldering once more under natural light, to check for bridges or shorts, then have a cup of tea. Upon my return I drilled out a hole in the enclosure lid for the LED, and one one the side for the DC socket, and fitted the lot together… and success! It worked 🙂

So there you have it. The journey from a daydream to a finished product… well a prototype anyway. But it works, and that is the best feeling of all. You can download the schematic from here. And here is the Arduino sketch:

Arduino

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

/*

"blinky" the one-eyed clock

Version beta 2.1

John Boxall 04 August 2010

http://tronixstuff.com/projects > blinky

Creative Commons Attribution-Share Alike 2.5 Australia

DS1307/i2c timekeeping based on code by Maurice Ribble

17-4-2008 - http://www.glacialwanderer.com/hobbyrobotics

*/

#include "Wire.h"

#define DS1307_I2C_ADDRESS 0x68

intred=9;// LEDs connected to these pins as you might want to PWM them to alter brightness

setDateDs1307(second,minute,hour,dayOfWeek,dayOfMonth,month,year);// every time blinky has new batteries, it will start from midnight/midday

pinMode(red,OUTPUT);

pinMode(green,OUTPUT);

pinMode(blue,OUTPUT);

}

voidloop()

{

whiteGlow(1,10);// glow white - announces that the time will now be shown

delay(1000);// give people a second to focus on blinky

blinkTime();

delay(50000);// wait 50 seconds

}

I hope you enjoyed reading this post and hopefully felt inspired enough to make your own.

In the meanwhile have fun and keep checking into tronixstuff.com. Why not follow things on twitter, Google+, 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.

I hope you have been enjoying your new-found skills with the Arduino system, and enjoying Massimo’s book. There are many interesting tasks for you to complete in this instalment: finish chapter four and five of the book, which contains some vital information about electricity; we’ll look at a new command or two for your sketches that will save you time and a lot of sketch memory; take a look at pulse width modulation (huh?); go random!; receive inputs from analogue sources; make some decisions; and finally – complete a project as an exercise for you to test your new knowledge.

First of all, please continue on from page 38 until the end of chapter four. This contains excellent instuctions on how to deal with “switch-bounce”, which is vital for future use. See you soon!

Hello again.

Recall from the previous instalment that your exercise involved a lot of repeated commands to light each LED in sequence – for example:

Arduino

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

digitalWrite(2,HIGH);// turn on LED on pin 2

delay(del);// wait (length determined by value of ‘del’)

digitalWrite(2,LOW);// turn it off

digitalWrite(3,HIGH);// turn on LED on pin 3

delay(del);// wait

digitalWrite(3,LOW);// turn it off

digitalWrite(4,HIGH);// turn on LED on pin 4

delay(del);// wait

digitalWrite(4,LOW);// turn it off

digitalWrite(5,HIGH);// turn on LED on pin 5

delay(del);// wait

digitalWrite(5,LOW);// turn it off

digitalWrite(6,HIGH);// turn on LED on pin 6

delay(del);// wait

digitalWrite(6,LOW);// turn it off

digitalWrite(7,HIGH);// turn on LED on pin 7

delay(del);// wait

digitalWrite(7,LOW);// turn it off

digitalWrite(8,HIGH);// turn on LED on pin 8

delay(del);// wait

digitalWrite(8,LOW);// turn it off

digitalWrite(9,HIGH);// turn on LED on pin 9

delay(del);// wait

digitalWrite(9,LOW);// turn it off

That seemed repetitive and time consuming – the nemesis to the reasoning for the existence of Arduino! However the solution can be found by using the for command. The purpose of the for command is to repeat a section of your sketch a number of times (of course this number is an integer – you cannot repeat a loop 3.141 times!).

the code checks to ensure “wow” is less than or equal to five, then increments “wow” by one

You can also use “wow–” to subtract one from the value of wow, or another variable. Anyway, if wow <=5 the looping continues; and if wow>5 it stops and the sketch moves on.

Hopefully by this stage you have recognised how this can simplify the code for exercise 0.1 from the last instalment. No? Let’s try that now. So instead of that huge block of code to light the LEDS in order up and down, rewrite it to use two loops – one for the up direction, and one for the down.

Well, wasn’t that better? Those for loops saved us a lot of time, and the use of variables also allows for sketch modifications to be much easier that hunting for each value to change within the sketch.

Groovy. Time for a quickie:

Hey, do you need a random integer? Easy!

random(x) returns a random integer between 0 and x-1. For example, if you need a random number between 0 and 255, use random(256). However, using random() is not entirely random, you need to seed the random number generator inside your Arduino chip. Use randomSeed(analogRead(0)); or another open analogue pin. You can also specify a range, for example random(10,20) will produce a random number between 10 and 19 (the minimum of the range is inclusive, the maximum exclusive – that is why the range is 10~19.

Next on the agenda is pulse-width modulation. Instead of reinventing the wheel, you will now work through chapter five of the book until the end of page 62.

Now that you have emulated a popular cult’s computer, it’s time to have some real fun with PWM and colours. Massimo mentioned about using red, green and blue LEDs to make any colour in the spectrum. This can be done quite easily (like most things) with your Arduino! When you were in school in art classes, you may remember that red + yellow = orange, red + green = blue, and so on. You can achieve the same effect using LEDs, and also vary the brightness between them to create the entire colour spectrum.

First, let’s look at how the primary colours can be used to create all sorts of colours. This example demonstrates briefly the possibilities of experimenting with red, green and blue.

You will need:

Your standard Arduino setup (computer, cable, Uno or compatible)

A diffused (not clear plastic) common-cathode RGB light emitting diode. A diffused LED will shine like a light bulb, where a clear one will just look like a 5mm dot.

2 50 ohm 0.25 W resistors. They are to reduce the current to protect the green and blue LED section

1 150 ohm 0.25W resistor. This is to reduce the current to the red LED section

a breadboard and some connecting wire

a camera (optional) – to document your success!

The circuit is quite simple, however the pins of the LED can be tricky. Here is the explanation of their layout:

The resistors are between the PWM output pins and the colour anode of the LED. See the board layout below:

analogWrite(red,random(255));// set red at random brightness between 0 and 254

delay(random(10,31));// wait for a random duration between 10 and 30 milliseconds

analogWrite(green,random(255));

delay(random(10,31));

analogWrite(blue,random(255));

delay(random(10,31));

}

}

And here it is in action! Mesmerising…

Wasn’t that fun? I hope you enjoyed that as much as I did writing about it for you. Don’t stare at the LED for too long though… we’re moving on to analogue sensors! Follow the book until the end of page 69. Now for something completely different. It is time to learn about a new command: if…else.

More often than not your sketch will need to make a decision. Is a switch on? Or is it off? If the variable ph equals 8657309 I will send that number to the GSM module to dial the number! Once again, with Arduino – it’s simple.

Example: if the value of temperature is greater than 100, turn off pin 13, otherwise turn it on.

Arduino

1

2

3

4

5

6

7

8

if(temperature>100)

{

digitalWrite(13,LOW);// turn off kettle

}

else

{

digitalWrite(13,HIGH);// leave kettle on

}

You can also extend this with else if…

Example: if the value of temperature is greater than 100, turn off pin 13; otherwise if value of humidity > 80, turn on pin 7.

Arduino

1

2

3

4

5

6

7

8

if(temperature>100)

{

digitalWrite(13,LOW);// turn off kettle

}

elseif(humidity>80)

{

digitalWrite(7,HIGH);// turn on pin 7

}

With the if…else statement you have a choice of six operators:

== equals

> greater than

< less than

>= greater than or equal to

<= less than or equal to

!= not equal to

At this point go and have a break and some fresh air. Because after that, it’s time for…

Exercise 1.1

Now we want to put together all the things learned so far and make something that has analogue inputs, digital outputs, and lots of LEDs… a voltmeter! Imagine a bar graph of ten LEDs, each one represents a voltage range. The range of the voltmeter will be between 0 and 10 volts DC – ideal for testing batteries and cells before they head to the garbage bin.

That sounds like a lot of work (the sketch, not throwing away batteries), but it isn’t when you break it down into smaller tasks. Let’s have a think about it…

We know that analogRead() can measure between 0 and 5 volts, and return an integer between 0 and 1023 relative to the measurement. Ah, but we want to measure up to 10 volts. Easy – use a voltage divider. Use two small resistors of equal value (e.g. 560 ohm 0.25 watt).

Next, how to convert that analogRead() value to represent a voltage we relate to an LED. We know that it will return a value between 0 and 1023, in our case that relates to 0~10 volts. So each LED will relate to one-tenth of the maximum reading. So the first LED will need to be illuminated if the analogRead() returns between 0 and 102.3 (actually 102 as it returns integers, not real numbers). The second LED will need to be illuminated if analogRead() returns between 103 and 205. Etcetera.

Now the rest should be easy… use your new sketch decision-making skills to decide which LED to light up (and don’t forget to turn it off as well) and you’re away…

You will need:

Your standard Arduino setup

ten LEDs of your choice. Standard ones are fine, or perhaps a mixture of colours?

3 x 560 ohm 0.25 W resistors. One to reduce the current to protect the LED indicator in use, and two for the voltage divider

1 x 10k ohm 0.25 W resistor. For use with the analogue input

a breadboard and some connecting wire

a camera (optional) – to document your success!

So here is our layout diagram:

And here it is in real life:

… and the action movie! We connected a variable power output to the voltmeter for the sake of the demonstration …

… however due to resistor tolerance and other analogue electrical problems caused by using a breadboard, our voltmeter was a little overenthusiastic. So like any quality piece of test equipment, it required some calibration. There are two ways this could be achieved:

put a variable resistor in the voltage divider. Then feed a known source, such as 5V from an LM7805 regulator, then adjust the variable resistor until LED 5 was constantly on;

put another voltmeter (e.g. a multimeter) over the voltage input to measure the voltage being measured by our voltmeter; use the serial.begin and serial.println() functions (from page 69) to send the value of voltage to the screen. Adjust the voltage being measured until you hit 1, 2, … 10V – noting the serial output. Then substitute these values into the if…then decision tree for the LEDs.

The second method is more accurate and easier to accomplish, so I have inserted the serial code into the example sketch below.

Here is a clip showing the results of the second calibration option:

So how did you go? Did it work first time? It’s ok if it didn’t, as you learn by doing and fixing your mistakes. Remember – if you have any questions, leave a comment at the bottom of this post and I will get back to you. But to save you time, here is the sketch. So there you have it. Today you have learned many more useful things to help you on your Arduino journey. And now for Chapter Two.

Have fun and keep checking into tronixstuff.com. Why not follow things on twitter, Google+, subscribe for email updates or RSS using the links on the right-hand column, or join our 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.