0% found this document useful (0 votes)
11 views

Arduino Compilation

Arduino

Uploaded by

MaxiNaki
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
11 views

Arduino Compilation

Arduino

Uploaded by

MaxiNaki
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 233

BEST-OF SERIES

ARDUINO COMPILATION
ALL ARTICLES FROM ELEKTOR ● 233 PAGES

SELECT LEARN DESIGN SHARE

N ● SHARE ● LEARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ●
ARE ● LEARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ●
EARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ●
GN ● SHARE ● LEARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ●
HARE ● LEARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ● LEARN ● DESIGN ● SHARE ●

Personal Download for Petar Crnojevic | copyright Elektor


Table of Contents
Page Article title Edition Pages
3 Arduino Software Development with Atmel Studio 12/2014 4
7 C Modules 11/2014 11
18 Extremely Low Frequency (ELF) Receiver 10/2014 8
26 16 Bit Data Logger 9/2014 6
32 Arduino is a Tool 7/2014 1
33 My first Shield :-) 7/2014 5
38 Lathe Tachometer 6/2014 4
42 3D Pad: Touchles Gesture Control Interface 5/2014 10
52 Microcontroller Bootcamp (1) 4/2014 7
59 Microcontroller Bootcamp (2) 4/2014 8
67 Microcontroller Bootcamp (3) 4/2014 10
77 Microcontroller Bootcamp (4) 4/2014 8
85 Microcontroller Bootcamp (5) 4/2014 10
95 Microcontroller Bootcamp (6) 4/2014 10
105 Microcontroller Bootcamp (7) 4/2014 12
117 Intel Galileo-Arduino 3/2014 2
119 Arduino Yún 1/2014 5
124 Numitron Clock and Thermometer 10/2013 5
129 Spot the Difference 7/2013 2
131 Off to the EF Library 6/2013 2
133 Motion-Detector Camera Trigger using Arduino 4/2014 5
138 Arduino AC Grid Analyser 12/2012 8
146 Thou Shalt Communicate 10/2012 6
152 Laser Projection with Arduino 7/2012 2
154 AVR multitool 7/2012 4
158 Arduino on course (1a) 7/2012 5
163 Arduino on course (1b) 7/2012 5
168 Arduino on course (2) 7/2012 5
173 Arduino on course (3a) 7/25/2012 6
179 Arduino on course (3b) 7/24/2012 6
185 Arduino on course (4) 7/23/2012 7
192 Arduino on course (5) 7/22/2012 6
198 Arduino on course (7) 7/21/2012 5
203 Android Switch Interface 3/1/2012 6
209 Arduino Shields 7/1/2011 1
210 Arduino Nano Robot Controller 7/1/2011 1
211 Support Board for Arduino Nano 1/1/2011 1
212 Wireless Instrumentation Network 11/1/2010 5
217 A voltage booster using Arduino 4/1/2010 1
218 Arduino + Theremin = Theremino 11/1/2009 4
222 Touch LEDs for Arduino 10/1/2009 6
228 Microcontrollers for Dummies 2/1/2009 5

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Arduino Software
Development
with Atmel Studio
By Wolfram Pioch
(Germany)
Debugging applications on the Arduino Due

If you normally use Atmel Studio to develop


software for microcontrollers in the AT(X)mega
family and are familiar with the advantages of work-
ing with a debugger, you will sorely miss the convenience
of these tools when you switch to the Arduino IDE to develop
sketches for the Arduino Due board. This article describes a suitable remedy.

Although it’s nice that you can get useful results


quickly with the many ready-to-run Arduino sam-
Figure 1. ple sketches already available, when you start
The actual Arduino version, developing serious software for an Arduino board
board and programming
with an ARM processor you are confronted with
interface are selected on the
the following significant shortcomings:
toolbar.

• Compiling the program in the Arduino IDE


takes too long.
• Loading the program takes too long.
• No genuine hardware debugger is available.

To remedy this situation, the author has devised


a suitable alternative.
One reason for switching to a 32-bit microcon-
Figure 2. troller is faster access to the hardware, especially
The location of the Arduino the I/O pins. Accordingly, a good way to test the
IDE folder can be entered in processing power of a microcontroller is to write
the configuration window. a sample program (Arduino sketch) that gener-

3
46 | December 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Arduino & Atmel Studio

ates a pulse waveform with the shortest possible


pulse width and measure the pulse width of the
output signal. In this article we describe how you
can program a test sketch for this purpose using
Atmel Studio 6.2 [1].

Arduino compatibility
The procedure described here assumes you have
Atmel Studio 6.2 (or later) installed under Win-
dows. To make the Atmel IDE compatible with
Figure 3.
Arduino, you also have to install a free add-in
The Micro Explorer window
called Visual Micro [2], which is an Arduino IDE
of Visual Micro.
for Microsoft’s Visual Studio and Atmel Studio.
Visual Micro is directly available in Atmel Studio tion Explorer window in Atmel Studio. There the
after it has been installed. Arduino references are shown as links on the
Reference tab. A click on one of the entries takes
The USB-based Arduino debugger available from you to the corresponding website in the config-
[2], which is not free, is not necessary because ured browser. The Examples tab holds a list of
debugging with the Atmel ICE is significantly more examples (including library examples) from the
convenient. The latter tool is available in vari- Arduino IDE, grouped by topic.
ous webstores at prices in the 100 dollar range
(see the review in the October 2014 issue of Sketches in Atmel Studio
Elektor [3]). The expenditure is worthwhile if A major benefit of the Atmel Studio IDE is the
you use Atmel microcontrollers more than just code completion function, which you now have
occasionally. available for Arduino sketches as well. For this
With this debugger you can set real breakpoints you have to enable Visual Assist X via VAssistX
without recompiling the program, observe vari- Ž Enable/Disable. With this enabled, all possi-
ables in the Watch window, and examine or ble completion options are listed each time you
Figure 4.
change memory contents. What’s more, you can type a character in the Code window. For exam-
The Atmel Studio editor
inspect the numerous I/O registers and alter them ple, if you type “S” at the start of a new line in
helps you avoid typos
with a mouse click. a sketch, the terms Serial, Server, SPI and so on
by suggesting function
After you install Visual Micro, a new toolbar are suggested. You can then select the appro- names and options for
appears in Atmel Studio. On this toolbar you priate term directly, with no risk of typos. Even autocompletion.
can select the current Arduino version (1.5.x), better, after you type a dot, for example after the
the board (Arduino Due) and the programming term “Serial”, the existing attributes and methods
interface (programming port) as illustrated in of this class are listed for selection (Figure 4).
Figure 1. After this you have to configure the
appropriate virtual serial interface, which you At this point you could create or open a sketch
can find by looking in the Device Manager win- in the Arduino IDE in the usual manner and then
dow when the Arduino Due is connected to the import it into Atmel Studio. However, you now
PC with a USB cable. As in the Arduino IDE, the
serial monitor button is located to the right of
these settings. Adapter for SAM ICE +3V3

If the settings do not appear automatically, for This adapter is necessary for using
JTAG
example because the Arduino IDE software is the SAM ICE debugger/programmer SAM-ICE
2 1
not located in the default directory, you have to with the Arduino Due. 4 3
+3V3

select “Configuration Manager”. That opens the 6


8
5
7
JTAG_TDI
JTAG_TMS
JTAG
Arduino Due

window shown in Figure 2. There you have to It connects the 10-pin JTAG 10 9 2 1
12 11 JTAG_TCK 4 3
enter the correct folder location manually, since pinheader with 50 mil (0.05”; 14 13 JTAG_TDO 6 5
16 15 JTAG_RESET 8 7
no selection dialog is available. 1.27 mm) pin pitch on the Due board 18 17 10 9
20 19
Clicking the question mark on the menu bar in to the 20-pin JTAG connector on the
Figure 1 opens the Micro Explorer window (Fig- SAM ICE device. 130392 - 66

ure 3), which is the counterpart of the Solu-

4
www.elektor-magazine.com | December 2014 | 47

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

trollers. According to Figure 6 the AVR platform


is active, but the “Make file Name” location is
correct for the SAM toolchain of the Arduino IDE.
As usual with Atmel Studio, pressing the F7 key
compiles the project and pressing the F5 key (or
clicking the solid green arrow) downloads the
program to the board via the boot loader. You
have to select “Clean Solution” on the Build tab
(Figure 7), since that is the only way to ensure
that all files are compiled the same way as in
Figure 5.
The Solution Explorer
the Arduino IDE.
window of Atmel Studio. As previously mentioned, one of the main advan-
tages of Atmel Studio over a pure Arduino IDE
is shorter compilation time, which significantly
accelerates the iterative process of compiling,
testing and modifying program code. That’s
because the Arduino IDE always compiles all of
the program files, while Atmel Studio only com-
piles the files that have been modified. In most
cases this means that only the .ino file, which
Figure 6. contains the sketch code, is compiled. On the
The wrong platform is author’s PC the first compiler run for the Speed-
shown here, but everything Test sketch took 3.7 seconds, but the second run
still works fine. after a change was finished in just 0.23 second.

Debugging with the Atmel ICE


A real hardware debugger such as the Atmel ICE
makes software development a lot easier. All you
need to connect the Atmel ICE to the Arduino
Figure 7. Due is the basic cable that comes with the device.
Compiler run with the Clean The Arduino Due can be powered from the USB
Solution option. port or by an external AC adapter. The Atmel ICE
only needs the USB port.
have the option of creating new Arduino sketches There are two options for plugging in the debug
directly in Atmel Studio. After you create and cable. The SAM port is the right choice for the
save the SpeedTest sketch (see inset) in either of Arduino Due, with the other end of the cable
these two ways, the structure shown in Figure 5 plugged into the JTAG connector on the board.
appears in the Solution Explorer window. Now The current version of Atmel Studio (6.2) does not
you can open the sketch and edit it in the cus- support editing of Arduino sketches on an Atmel
tomary manner in Atmel Studio. From this point ARM platform, but there is a way to get around
on you don’t actually need to run the Arduino this. To use the Atmel ICE for debugging, simply
IDE. However, you should not delete it because launch a second instance of Atmel Studio. Then
it has to remain available on the PC. select Open -> Open Object File For Debugging.
It’s a bit confusing that the platform is shown as The compiled files generated by Atmel Studio are
“Active AVR” in the project properties (right-click located in the following folder under Windows 7:
SpeedTest: Properties Ž Build), at least in the
current version of Atmel Studio (6.2). Unfortu- C:\Users\xxxx\AppData\Local\
nately there’s nothing you can do about this. The VMicro\Arduino\Builds\SpeedTest\
platform is also shown as “AVR” under “Toolchain” arduino_due_x_dbg\
and “Device”. Nevertheless, everything works as
Figure 8. it should. When you select “Arduino Due” as the There you will find the file SpeedTest.elf. Now
Output files in the Solution board, the project is compiled in the same way as let’s open it for debugging.
Explorer window. with the SAM platform for Atmel ARM microcon- If the sketch was compiled and saved with the

5
48 | December 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Arduino & Atmel Studio

Arduino IDE, a copy of this file is also located in The actual structure of the downloaded Arduino
the debug folder for the sketch. It can be seen program can be seen in the Solution Explorer win-
in the Solution Explorer window of the code gen- dow, where the main.ccp file is selected and the
eration instance of Atmel Studio under “Output cursor is positioned on the first line of this routine
Files” (Figure 8).

Using the browse function, find and select the out-


put file SpeedTest.elf. You should see a window
like the one shown in Figure 9. You can specify
your own project name and storage location for
the debug project folder. Your settings will be
saved and used automatically the next time you
Figure 9.
open the debug project.
Dialog for selecting the
generated output file.
Next you see a window for selecting the device
family and target microcontroller (Figure 10). For
the Arduino Due you should select “SAM3, 32 bit”
for the device family and “ATSAM3X8E” for the
microcontroller type.

Now the file SpeedTest.ccp appears in the Solu-


tion Explorer window. This is simply the program Figure 10.
file of the sketch, which originally had the exten- Dialog for selecting the
sion .ino. Right-click the project name “Speed- device family and device
Test_Debug” to open the Properties window. type.

When the Atmel ICE is connected to the PC over


USB, the debugger can be selected under Tool ->
Selected debugger/programmer. Here you must
specify “SWD” as the interface instead of “JTAG”.

Now the Atmel ICE is ready. You can also use it


as a programmer. To open the programming win-
dow, press Ctrl-Shift-P or click the chip symbol
with the lightning flash. The desired functions
are available after you click Apply. You can set
the maximum SWD clock rate (2 MHz) on the
Interface Settings tab. On the Memory tab, you
can download the SpeedText.elf file directly
to the flash memory of the microcontroller. The
program starts running automatically after the
programming process completes.
Figure 11.
The true complexity of an
However, it is more efficient to use the Debug Arduino project can be seen
Ž Start Debugging and Break or the Start With- in the Solution Explorer
out Debugging command (or the corresponding window.
icon: the blue arrow with the vertical blue bar or
the solid green arrow) to download a program
for debugging or running, instead of the device
Figure 12.
programming function. When this error message
Downloading the complete program to the micro- appears after you modify a
controller takes roughly 1 second with the Atmel file, simply click “Reload” to
ICE, which is quite fast. dismiss the message.

6
www.elektor-magazine.com | December 2014 | 49

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

(Figure 11). As you can see, the SpeedTest.ccp


file is only a small part of the overall program,
which is why a full compilation takes so long.
The debugger gives you access to all the debug
functions of Atmel Studio, such as single-stepping
with F11, setting breakpoints with F9, defining
breakpoint conditions in the Breakpoint window,
and so on.
If you edit and recompile the SpeedTest.ino file
Figure 13.
in the first instance of Atmel Studio, the mes-
Oscilloscope screenshot
of the 150-kHz pulse sage shown in Figure 12 appears in the second
waveform. instance (the debug environment). Press “Reload”
to close the debug message and load the mod-
ified program into the microcontroller. Now the
cursor is again positioned on the first line of the
program code and the program can be run again.

If you have previously worked with 8-bit AVR


microcontrollers in the Atmel Studio environment,
you will not have any problems working with
32-bit ARM microcontrollers because the user
interface is nearly the same. Incidentally, clearing
and rewriting the flash memory with the Atmel
ICE does not affect the boot loader because it
is located in the ROM of the microcontroller and
therefore cannot be deleted or overwritten. Con-
sequently simply downloading a program over the
USB interface still works the same way.

SpeedTest
Only the following two instructions are executed
in the main loop of the example sketch (see the
SpeedTest listing):

digitalWrite(TP1,1); //On
digitalWrite(TP1,0); //Off
Figure 14.
Microcontroller PIO register. With an oscilloscope, you can see a pulse wave-
form on this pin while the program is running,
with a pulsewidth of 2.35 µs and a period of
6.6 µs (Figure 13), which corresponds to a fre-
quency of about 150 kHz. That is not very high,
and you could hardly be blamed for thinking that
there’s no reason to use an ARM controller clocked
at 84 MHz for this when a simple 8-bit AVR micro-
controller can do it better.

The reason for this poor performance is that the


Arduino instruction digitalWrite is a cover name
Figure 15.
Oscilloscope screenshot of
for a bunch of C routines, as you can see by exe-
the 12-MHz pulse waveform cuting the program in single-step mode with the
generated by version 2.0 of debugger (F11 key). To actually achieve high
the program. processing speed, you have to avoid this over-

7
50 | December 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Advertisement
head. Fortunately, the Arduino programming language is not
a separate language, but instead a form of C with a GNU
compiler in a special Arduino configuration.
This means that a pin configured as an output can be
addressed directly by setting or clearing a bit in the PIO
register. The instruction

const int TP1 = 7; //Test pin

selects Arduino pin 7 as the test pin. According to the Arduino


pin mapping, this corresponds to pin PC23 of the microcontrol-
ler or bit 23 in the parallel input/output (PIO) register. With
the program stopped you can go to the I/O View window of
the debugger (Figure 14) and click bit 23 of the PIO_ODSR YOU DESIGN IT – WE MACHINE IT
(set) register to set the pin high. To reset the pin, click the

Professional quality front panels


www.schaeffer-ag.de
same bit in the PIO_CODR (clear) register. In the main loop
you can simply use the instruction
From one piece and at a fair price! Simply
PIOC->PIO_SODR = 1<<23;
download our free Front Panel Designer at
to set the pin without any fuss or bother. www.schaeffer-ag.de, design your front
panel and order it directly.
To test this, and at the same time check whether conditional
compilation works properly, the author generated a new ver-
sion of the sketch (see the SpeedTest 2.0 listing). If the
expression Direct is defined in the code, the code segment
after #ifdef Direct is compiled, and otherwise the previ-
ous version with the slow digitalWrite instruction is com-
piled. Naturally, this change would also work in the normal
Arduino IDE.

Listing 1. Speed-Test.

//*******************************
//Speed-Test with Arduino Due
//*******************************

const int TP1 = 7; //Testpin

void setup()
{
/* add setup code here */
// set the digital pin as output:
pinMode(TP1, OUTPUT);
}

void loop() {
// put your main code here, to run repeatedly:

digitalWrite(TP1,1); //On
digitalWrite(TP1,0); //Aus
}

8
www.elektor-magazine.com | December 2014 | 51

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

The result of this code optimization, as shown


Listing 2. Speed-Test 2.0.
in Figure 15, is stunning: the pulse waveform
//********************************* now has a pulse width of 23.2 ns and a period
//Speed-Test 2.0 with Arduino Due of 83.3 ns. This corresponds to 12 MHz – about
//********************************* 80 times faster than before. From that we can
conclude that using an ARM microcontroller isn’t
#include „arduino.h“
such a bad idea.
//
// Summary
const int LED1 = 13; Working with Atmel Studio accelerates Arduino
int LED2 = 12; sketch development to a completely new level
int LED3 = 11; thanks to shorter turn-around times, since only
int TP1 = 7; //Testpin
modified code is recompiled. Atmel Studio and
the tools that can be used with it, such as the
Atmel ICE as a debugger and programmer, are
#define Direct
worthwhile when you work with Atmel microcon-
trollers because they offer professional debugging
void setup() features and because downloading programs to
{ the microcontroller memory is significantly faster.
/* add setup code here */
Incidentally, you can also use Atmel’s SAM ICE
// set the digital pin as output:
instead of the Atmel ICE for ARM projects. With
pinMode(LED1, OUTPUT);
the SAM ICE hardware debugger and program-
pinMode(LED2, OUTPUT); mer, microcontroller programming speed can be
pinMode(LED3, OUTPUT); boosted by a factor of 4 because it can operate
pinMode(TP1, OUTPUT); at 8 MHz instead of 2 MHz. For this you need
// set output low the adapter described in the inset. If you are a
professional software developer, the expenditure
digitalWrite(LED1,0);
quickly pays for itself even if the device can only
digitalWrite(LED2,0);
be used with the AT91xx microcontroller family.
digitalWrite(LED3,0); (130392-I)
digitalWrite(TP1,0);
}
Web Links

void loop() { [1] Atmel Studio 6.2:


www.atmel.com/microsite/atmel_studio6
// put your main code here, to run repeatedly:
[2] Arduino IDE for Visual Studio:
#ifdef Direct
www.visualmicro.com
//x= state of PIO_SODR with bit 23 = 1
[3] Atmel ICE:
int x = PIOC->PIO_SODR | 1<<23;
www.atmel.com/tools/atatmel-ice.aspx
Review: www.elektor-magazine.com/140275
while (1){ //Only for testpurposes, don‘t exit this loop
[4] SAM ICE:
PIOC->PIO_SODR = x; www.atmel.com/tools/atmelsam-ice.aspx
PIOC->PIO_CODR = x;
}

#else
digitalWrite(TP1,1);
digitalWrite(TP1,0);
#endif
}

9
52 | December 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

C Modules
Software for Elektor Extension Shield,
Relay Board and more
By Jens Nickel (Elektor Germany)

Modular hardware enables us to create


plug-and-play prototypes rapidly; all we
ExtensionEFL_ECC_RS485.c need do is assemble predesigned build-
ing blocks. Exactly the same principle
can be applied to software, and the C
programming language is well suited
to this approach. This article showcas-
es some compatible software modules
BoardEFL_ArduinoUnoCore.c and demo applications for our Elektor
Extension Shield and three expansion
boards.

Elektor’s 2014 Project Generator double edi-


ExtensionEFL_Arduino_ tion introduced a compact plug-in board for
ElektorExtensionShield.c the Arduino Uno that contained a Display, two
user-definable LEDs, two pushbuttons and a
potentiometer or ‘pot’ [1]. Using this board, new-
comers can get cracking immediately and make
their first steps in programming microcontrol-
lers, for example adding digital outputs (LEDs)
and digital inputs (pushbuttons). More advanced
users will make use of two additional expansion
ExtensionEFL_
connectors on the board. The 10-pin Embedded
Communication Connector (ECC) provides TX/
EEC_Relay8.c
RX UART signals and two GPIO pins. Using a
flatcable you can hook up an RS-485 module for
example, enabling you to send and receive bytes
down longer c cables. Already developed is an
NFC gateway, enabling simple ASCII commands
to read and characterize NFC cards or communi-
cate with NFC-ready smartphones. Further ECC
modules are planned as well.

The 14-pin Embedded Extension Connector


(EEC) is also known as a Gnublin connector, as
it enables you to link up with the Gnublin mod-
ules from Benedikt Sauter and his team. Benedikt
has also defined the specifics of the connector,

10
56 | November 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


C Modules

although we should point out that the Elektor


Extension Shield employs only four of the 14 New file structure
pins (namely 3.3 V, GND and the two I2C lines). The EFL is now adapted additionally for larger modular projects, in which
However, most Gnublin boards [2] use only the several expansion boards are connected to (or chained in series with)
I2C pins, for example the Port Expander Board, a Controller board. For this purpose the Library needs to be extended
the Temperature Sensor Board, a board with eight somewhat and restructured compared with its previous state [5].
relays [3] and the ADC Board from the Septem-
ber 2014 edition [4]. • The hierarchical system of the Includes has been disentangled. Only
Header files from the Common folder are now integrated throughout.
Software modules These files are identical in all EFL projects, regardless of which boards
In the BASCOM-oriented Microcontroller Boot- and Controllers are used.
Camp course that concludes in this edition vet- • To this end a new Header file is placed in the Common folder
eran author Burkhard Kainka has developed some (ControllerDefinesEFL.h). It now includes all Function definitions
interesting applications for the Elektor Extension of the Controller API, which of course are always identical. The
Shield. More of these will appear in Elektor from Controller-specific Header file (previously ControllerEFL.h) now
time to time. includes only Controller-specific definitions, such as those for the
Register.
One thing that was lacking till now was soft- • Instead of ControllerEFL.h/.c and/or BoardEFL.h/.c we now
ware support for C. This language is particularly provide meaningful names for the Controller and board-specific code
well suited for modular software projects. Once files. The file that implements the Controller API for the ATmega328,
developed and tested (either by yourself or by is now called ControllerEFL_ATmega328. The file extracted
third parties), software modules can be used from the wiring connection to the Arduino Uno board is called
again and again in your homebrew projects. This BoardEFL_ArduinoUnoCore.
shortens development time enormously and in • We can now integrate several extension boards into our project,
extreme cases you can achieve a major, func- since the relevant code files all have differing names instead of
tioning application in minutes. And should those ExtensionEFL.c/.h . For instance:
project requirements alter, for instance if an addi- -- ExtensionEFL_Arduino_ElektorExtensionShield.c/.h
tional RS-485 interface becomes necessary, you -- ExtensionEFL_ECC_RS-485.c/.h
can create a compatible software solution just -- ExtensionEFL_EEC_Relay8.c/.h
as rapidly. The type of expansion connector is always shown between the
underscore symbols.
Hardware-wise we can now devise a functioning
• The Board-Init Functions that incorporate the onboard wiring
system from modules that need merely plug-
connection in the Tables and make ready the Peripheral units are also
ging together. Once you have stacked the Elektor
given more specific names, for example ExtensionEFL_Arduino_
Extension Shield onto an Arduino Uno board, you
ElektorExtensionShield_Init(0) in place of ExtensionEFL_
can plug in your choice out of an RS-485 mod-
Init(). To make this consistent, the Controller-Init Function is
ule, a relay card or an ADC board. We shall now
now, for example, ControllerEFL_ATmega328_Init() instead of
apply the same modular principle to the software;
ControllerEFL_Init().
for an application with defined requirements we
An initialization of the Controllers and all boards could now look like
need simply assemble the corresponding code
this for example:
modules into a software project. Ideally each
-- ControllerEFL_ATmega328_Init();
hardware module will have its associated soft-
-- BoardEFL_ArduinoUnoCore_Init();
ware module that can be used without alteration,
-- ExtensionEFL_Arduino_ElektorExtensionShield_Init(0);
regardless of in which particular set-up the hard-
-- ExtensionEFL_ECC_RS-485_Init(2);
ware interacts. Take for example the code for the
-- ExtensionEFL_EEC_Relay8_Init(3);
Relay Expansion Board; it remains unchanged
• The Init Functions of the Expansion boards are now augmented
regardless of whether we hook up the relays to
with the consecutive Block number of the expansion connector to
the Elektor Extension Shield, the Xmega Board
which they are attached. In this way the wiring connection (from
or the Elektor Linux Board.
the Controller pins through to the furthest Peripheral) is represented
correctly in the EFL-internal Tables. It is now also possible to ‘chain’
Pretty close to perfection
Expansion boards in series as in the present case (for this see also
Using the programming language C and the
Embedded Firmware Library (EFL) described in the main article and Figure 1).

11
www.elektor-magazine.com | November 2014 | 57

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

RELAIS
ing to the Arduino-Uno board has the name
ARDUINO BoardEFL_ArduinoUnoCore.
#0
RS485
#2 #2 #3 #3
• We can now use several extension boards in
our project, since each of the corresponding
code files has a different name, for example:

#1
ExtensionEFL_Arduino_
SHIELD
ElektorExtensionShield.c/.h
140328 - 17 ExtensionEFL_ECC_RS-485.c/.h
ExtensionEFL_EEC_Relay8.c/.h

Figure 1. Elektor [5] we can get extremely close to the


Chaining expansion boards: ideal just described, as we shall now show. Up • The Init Functions called up initially are also
the Extension Shield is till now you could use the EFL only for a Duo named specifically. This is the initialization of
plugged into two connector equipped with a Controller Board and an Exten- the Controller and all the boards for the first
strips on the Arduino Uno
sion Board. So that other expansion boards can be sample application discussed next:
(#0 = digital pins, #1 =
used in a project, the Library had to be extended
analog pins). Connectors
#2 (ECC) and #3 (EEC) are and restructured somewhat. To avoid boring the ControllerEFL_ATmega328_Init();
still available for use, being hands-on practitioners among our readers with BoardEFL_ArduinoUnoCore_Init();
linked through and repeated all the details, we have placed the full explana- ExtensionEFL_Arduino_
on the Shield. tion in a separate text box. Here in brief are just ElektorExtensionShield_Init(0);
the most important alterations:
ExtensionEFL_ECC_RS-485_Init(2);
ExtensionEFL_EEC_Relay8_Init(3);
• Previously a file pair by the name of Con-
trollerEFL.h/.c contained Controller-spe- The number of the first expansion Port connected
cific source code that made standard- is given together with the Init Functions of the
ized Functions available for activating the expansion board; this number is incremented
inputs and outputs of each Controller, for during the initialization of the board (Figure 1).
example IO_SetPinLevel(…). A file pair, The Extension Shield is installed on the Arduino
always called BoardEFL.h/.c, displayed the Uno, which defines two expansion Ports; these are
onboard wiring connections (which the appli- assigned the numbers #0 (digital pins) and #1
Figure 2. cation developer no longer needs to know). (analog pins). The Extension Shield is connected
Application 1: Eight relays Instead of the uniform designations these to #0 and #1 and has onboard two additional
can be operated either files now have meaningful names. The file expansion Ports, #2 (ECC) and #3 (EEC). To the
locally via a user interface responsible for the ATmega328 is now called first of these we connect the RS-485 module and
or remotely via RS-485. ControllerEFL_ATmega328. The file belong- to the second the relay module.

(Remote) Control of relays


We have prepared three demo projects for Atmel
Studio 6 that you can find in the download data
for this article [6]. Incidentally a Configurator for
the PC is already in development; this automati-
cally assembles and integrates the files necessary
for an EFL project in Atmel Studio. This leaves
you only the task of indicating which boards you
plan to use in the project.

Let’s begin with the first project, a small control


application. Eight relays can be switched locally
using a user interface; they can also be controlled
remotely by a PC using a Terminal program. An
Elektor Extension Shield is plugged on top of an

12
58 | November 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


C Modules

Arduino Uno; the Gnublin PCB with eight relays


is connected to this with some flat cable (Fig-
ure 2). The RS-485 ECC module is an optional
extra, also connected to the Shield; the con-
nection then goes over RS-485 (two wires plus
ground) to an RS-485-to-USB converter and the
PC. The application will also work if you link the
Arduino Uno direct to a PC using USB.

The software can be found in the download pack-


age in the ElektorShieldRelay folder. After click-
ing on ElektorShieldRelay.atsln the project
opens in Atmel Studio (Figure 3). On the right, in
Solution Explorer, you can see the integrated files.
In all cases you should be able to see a folder
called Hardware. As well as the files mentioned
above for the Controller, the Controller board
and the expansion board you will also find the
new BlockEFL files with the Low Level Functions
for the RS-485 driver, the digital outputs and
inputs and the Display (see box-out ‘BlockEFL
files’). Advanced users should check out the code
in the file ExtensionEFL_Arduino_ElektorEx- verted into the character strings in Block Protocol Figure 3.
tensionShield.c (Figure 3). This code records format [7] that are received via the UART. The Relay control operation in
the peripheral Blocks located on the Shield in the Function ADCSimple_GetRawValue(0, 0) returns Atmel Studio 6. The code
indicates the initialization of
EFL-internal Block Table (Figure 4). From now the value of the ADC input 0 in ADC Block #0 (the
the Extension Shield.
on the buttons on the board respond to the Block pot is connected here). The value can amount to
number #0 and the LEDs to Block number #1, as 0...1023 (10 bits); we can reduce this to 7 bits
there is already an LED mounted directly on the by shifting them to the right, in order to obtain
Arduino board (addressed using Block number a figure between 0 and 7. This enables us to
#0). For the pot an ADC Block #0 is provided, select one of the eight relays from the setting
then comes the Display with the number #0. of the pot. The selected value is shown in line 0
Finally the wiring to the ECC and EEC connectors of the Display.
is displayed, with two new Blocks provided for
the connectors (#2, #3). The entries are then The Function ButtonEventCallback(…) contains
used once more by the code of the ECC and EEC code that is carried out when a pushbutton is
modules. Last of all, check out each peripheral pressed. Which of the two buttons was pressed
Figure 4.
unit in the Table to see which Controller pin it is is determined using the variable ButtonPosition
All peripherals can be
connected to. (0 or 1). If the left-hand button (0) is pressed,
addressed conveniently and
we deactivate the selected relay, whilst pressing uniformly using their Block
Let’s now examine the main program in the file the right-hand button (1) activates the relay. As numbers.
ElektorShieldRelay.c. The routine Appli-
cationSetup() contains all the initializations
RELAIS
from the Controller via the boards as far as the ARDUINO
RELAY#0
Libraries. Assuming your hardware setup does
CONN#0
not change, you can leave the whole bunch RS485
LED#0 LED#1
BUTT#0
UART#0 CONN#2 CONN#3
untouched.
DISP#0

Short code
The application itself can be viewed in Listing 1. CONN#1
ADC#0

In the Function ApplicationLoop() you will see SHIELD

all the commands that need to be reiterated each


140328 - 12
time. First the pressbuttons are polled, then con-

13
www.elektor-magazine.com | November 2014 | 59

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

BlockEFL files
Up till now BoardEFL and ExtensionEFL files have still included the so-called Low Level/Block Functions, such as for example
the Function

void Display_SendByte(uint8 DisplayBlockIndex, uint8 ByteToSend, uint8 DATABYTE_COMMANDBYTE)

which is based on the wiring interconnection between the


Controller and Display (4-bit or SPI as appropriate). A Display APPLICATION
Library such as DisplayEFL then needs only to ensure that
the correct bytes are sent to the Display. The code there is LED
DISPLAY UART LIBRARIES
BUTTON

COMMON
independent of which particular route the bytes take to reach
the Display. This Block Function must be defined once in the BOARD BLOCK BLOCK BLOCK
DISPLAY IO UART
project if a Display is provided on any of the boards. HARDWARE
LAYER
Logically we therefore provide a dedicated file pair in the CONTROLLER
Hardware folder for the Low Level/Block Functions required
by the Display. If a Display is used anywhere in a project, HARDWARE
you need to integrate BlockEFL_Display.h/.c in addition. A 140328 - 14

different BlockEFL file is responsible for the RS-485 Functions.


Block Functions for digital outputs and inputs, such as for
instance SwitchDigitalOutput(uint8 BlockIndex, uint8 Position, uint8 ON_OFF) are also extracted from the
BoardEFL file and relocated into a new file BlockEFL_IO.
The Board files now contain normally only the Init Functions that define wiring and integrated Peripheral/Blocks like, for
example, making the Display ready. For this purpose the Function

void Display_BoardSetup(uint8 DisplayBlockIndex);

is called up there, now located in BlockEFL_Display.h/.c.


Overall, you now have to deal with a greater number of files but the modularity of the EFL has been further improved.
Already in development is a Project Configurator, which assembles and integrates the files necessary for a project
automatically.

the Function SwitchRelay(…) directly demands a


0 = OFF or a 1 = ON as its third parameter, the
code turns out agreeably short and to the point.
Info on these and the other EFL Functions is in
the Doxygen documentation (click on Index.htm
in the download).

Using the Block Protocol [7] you can control the


relays remotely from a Terminal program. The
command R 0 2 + <CR> activates the third
relay in Relay Block #0 (as always we count up
from zero, 0, 1, 2…). R 0 2 - <CR> deactivates
it again. With L 0 0 + <CR> we can switch on

Figure 5.
You can display the EFL Tables using a Terminal program.
The Blocks are set out centrally.

14
60 | November 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


C Modules

the LED located directly on the Arduino. L 1 0


Listing 1. Relay (remote) control.
+ <CR> and L 1 1 + <CR> are the correspond-
ing commands for the LEDs on the Extension uint8 RelayPosition;
Shield. Do also try the command x <CR>; you
will then have on your screen the content of the void ApplicationLoop()
EFL Table. At the centre you will see all the rel- {
evant Blocks (Figure 5). ButtonPoll(0);
BlockProtocol_Engine();
Precise measurement
For our second application we remove the relay
RelayPosition = ADCSimple_GetRawValue(0, 0) >> 7;
board and substitute the 16-bit ADC board that
Display_WriteNumber(0, 0, RelayPosition);
we featured in the September issue [4]. As men-
tioned in that article, we link the output A3 on }
the lower Arduino connector strip (replicated on
the Shield) using a flying lead to the input AIN0
of the ADC board (Figure 6). Our task now is void ButtonEventCallback(uint8 BlockType, uint8
to digitize the setting of the pot also using the ButtonBlockNumber, uint8 ButtonPosition, uint8 Event)
accurate external ADC. {
if (Event == EVENT_BUTTON_PRESSED)
Double clicking on ElektorShieldADC.atsln {
reveals the source code. As seen in Solution
ToggleLED(1, 0);
Explorer, instead of the two files ExtensionEFL_
SwitchRelay(0, RelayPosition, ButtonPosition);
EEC_Relay8.c/.h we now have two files Exten-
}
sionEFL_EEC_ADCModule16bit.c/.h in the proj-
}
ect. In addition the files ADC_ADS1x1xEFL.c and
BlockEFL_DeviceRegister16.c have appeared
now. BlockEFL_DeviceRegister16.c in the
Hardware folder contains Low Level Functions good multimeter you will discover the external
for addressing an I2C chip, featuring 16-bit reg- ADC measures to a high level of accuracy.
isters. ADC_ADS1x1xEFL.c takes care of the cor-
rect compilation of the bytes, which are written This application also provides remote access Figure 6.
Application 2: External
in these registers (the Library of my colleague using the Block Protocol. The command A 0 0
16-bit ADC on the Arduino
Clemens Valens is adapted to the EFL here [4]). # <CR> causes the Arduino to return the value
Uno. The voltage on the pot
just sampled by the internal ADC in hex charac- is returned across the cable,
Application developers don’t have to be concerned ters. A 1 0 # <CR> returns the last value of the enabling the readings of the
with all this. The only thing they need to know is external ADC. The indications are quite different internal and external ADCs
that after initialization of the boards a further ADC because we are now dealing with raw values and can be compared.
Block with the number #1 is created (Figure 7).
You can now access the external ADC exactly as
you would the internal ADC of the Controller. The
application library ADCSimpleEFL.c for instance
makes available the Function ADCSimple_GetMil-
livoltValue(..), which can provide you with
the voltage in millivolts on an analog input of a
particular ADC Block.

The actual application code is located in the file


ElektorShieldADC.c, the critical function being
printed in Listing 2. Next up we need to find
out what the application actually does: the volt-
age on pin A3 of the Arduino is digitized by both
the internal and external ADCs and displayed
on-screen. If you check out the voltage with a

15
www.elektor-magazine.com | November 2014 | 61

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Virtualization
Port expanders and external A-to-D converters are two The concept of ‘Virtualization’ is now broadened to analog
sample applications for chips that extend the capabilities of inputs. In our case the external ADC is located on the
a Controller. Frequently these chips are addressed via an EEC/Gnublin ADC Expansion board, so the code in file
I2C Bus or some other serial interface. ExtensionEFL_EEC_ADCModule16bit.c must take over
the activation of its ADC. When the board is initialized with
A modular prototyping library should, as far as possible, the Function ExtensionEFL_EEC_ADCModule16bit_Init(…)
be based on the hardware used. For someone developing the external ADC is integrated into the EFL Tables like
an application (or a Library that activates Peripherals) an internal ADC (in our case with the Block number #1),
it should be immaterial how the wiring tracks run on where, however, it is assigned to the virtual Port 0x40. In
the board or to which Controller pins the Peripheral is addition the I2C interface is made ready. Furthermore the
connected. Ideally the developer should also not need to Function Virtual_ADC_GetValue(…) is notified to the
know whether an input or output is connected to a genuine Controller code.
Controller pin or merely to a Port expansion chip. We
can solve that problem by assigning to the Controller in Using the Function ADCSimple_GetRawValue(uint8
addition to its Ports 0, 1, … etc. some extra ‘virtual’ Ports ADCBlockNumber, uint8 ADCPosition) users now have
that begin with the number 0x40 = 64, so as to be able to access to an ADC pin in a specific ADC Block, independent
differentiate these from ‘real’ Ports. of the connection to the Controller. The Function directly
If for example you wish to activate a relay connected to a calls up the Controller Function ADC_GetValue(…). The
Port expansion device, then access to the relay from the Controller refers to the EFL Tables and on account of the
RelayEFL Library will be forwarded perfectly normally to high Port number recognizes that an internal ADC is not
the Function SwitchDigitalOutput(…), located in the file intended but instead it should call up the Function Virtual_
BlockEFL_IO.c. This Function refers in the EFL Tables which ADC_GetValue(…), located in the code file of the Expansion
Controller Port and pin the relay belongs and calls up the board. This results in giving access to the external ADC over
Function IO_SetPinLevel(…) in the Controller file. In the I2C.
Tables a Port 0x50 is recorded for the relay and normally
this would be the end of it, as the Controller is unaware As well as the Function ADC_GetValue(…) our application
of any Port 0x50. However, for such situations when the also virtualizes the Function ADC_GetParameter(…), with
relay board is initialized, a special Function of the relay which the resolution and voltage range of an ADC can
board code is passed to the Controller code that is called be read off. In this way ADC values can be calculated in
up in cases like this. This same Function then sends the millivolts.
corresponding I2C commands to set the output pins of the
Port expansion unit located on the board.

not numbers of millivolts. To avoid inflating the Mini Protocol


Block Protocol library unduly, we have foregone Given that we can already calculate the millivolt
having a Function for converting ADC values into readings in the application, couldn’t we simply
millivolts. call them up using the UART?
Absolutely! We just need to concoct a dedicated
mini Protocol. It we transmit 0 <CR>, then we
ARDUINO receive back the value of the internal ADC in
CONN#0
millivolts. Typing 1 <CR> should arrange that
LED#0 LED#1 ADC-BOARD
RS485 BUTT#0
UART#0 CONN#2 CONN#3 ADC#1

DISP#0

ADC#0
Figure 7.
CONN#1
Internal and external ADCs can be addressed using the
SHIELD 140328 - 13 same Functions, with the Block numbers #0 and #1 used
for differentiation.

16
62 | November 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


C Modules

the Arduino send back the value of the external


Listing 2. Measurement using internal and external ADCs.
ADC. Now we can compare both values directly
in the Terminal program. void ApplicationLoop()
{
Listing 3 shows the relevant code (project Elek- ButtonPoll(0);
torShieldADCMiniProtocol.atsln in the down-
BlockProtocol_Engine();
load). ReceiveRingbuffer contains the address
of the receive ring-buffer, where the characters
uint16 ADCValue1 = ADCSimple_GetMillivoltValue(0, 0);
are written. These then reach the Arduino via
Display_WriteNumber(0, 0, ADCValue1);
the UART (UART Block #0).
The millivolt value is converted into hex digits in
uint16 ADCValue2 = ADCSimple_GetMillivoltValue(1, 0);
the application routine SendMillivolt(…) and
Display_WriteNumber(0, 1, ADCValue2);
sent forward via the UART #0.
}

In an upcoming issue we will introduce the Con-


figurator, with which you can generate an EFL
project yourself. We’ll also provide simple instruc- Listing 3. Reading values with a mini Protocol.
tions for writing your own board file. Stay tuned! void ApplicationLoop()
(140328) {
ButtonPoll(0);
//BlockProtocol_Engine();

uint16 ADCValue1 = ADCSimple_GetMillivoltValue(0, 0);


Display_WriteNumber(0, 0, ADCValue1);

uint16 ADCValue2 = ADCSimple_GetMillivoltValue(1, 0);


Display_WriteNumber(0, 1, ADCValue2);

while (Ringbuffer_IsEmpty(ReceiveRingbuffer) == FALSE)


{
uint8 ReceivedChar =
Ringbuffer_GetByte(ReceiveRingbuffer);
if (ReceivedChar == ‘1’)
{
SendADCValueOverUART(ADCValue2);
}
if (ReceivedChar == ‘0’)
{
SendADCValueOverUART(ADCValue1);
}
}
}

Web Links void SendADCValueOverUART(uint16 ADCValue)


[1] www.elektor-magazine.com/140009 {
uint8 sd[3];
[2] www.elektor.com/development/gnublin/
[3] www.elektor-magazine.com/130157 sd[0] = (ADCValue & 0xFF00) >> 8;
[4] www.elektor-magazine.com/130485 sd[1] = ADCValue & 0x00FF;
sd[2] = 13;
[5] www.elektor-magazine.com/120668
[6] www.elektor-magazine.com/140328 UARTInterface_Send(0, sd, 3);
[7] www.elektor-magazine.com/130154 }

17
www.elektor-magazine.com | November 2014 | 63

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Extremely Low Frequency


(ELF) Receiver
Arduino + ADC = ELF

By Kurt Diedrich If you Google


(Germany)
the terms ELF,
ULF, or VLF it
transpires that the
lowest frequencies of all electro-
magnetic interference (EMI) signals
are generated by electrified railways and not a lot more
beyond this. Wrong! You can in fact receive some extremely interest-
ing signals between 0 Hz and the ‘railway’ frequency of 162/3 Hz. Using the receiv-
er described here with an ADC module described in a separate article and some
free PC software it is possible to receive and make recordings of these signals.

It had always fascinated me what I might hear—or ten in Europe where the AC supply frequency is
rather see on an oscilloscope—if I could connect 50 Hz but exactly the same methods will work
a pick-up coil, with a couple of hundred turns on in territories where the line frequency is 60 Hz.
it, to an extremely sensitive amplifier. A dozen Please read ‘60’ wherever you see ‘50’ from now
or so years ago I decided to turn this supposition on, if you live in a 60 Hz country. Ed.]
into fact using modern electronics. Eventually, after I submitted my received data to
The first circuit I constructed for this purpose FFT-versus-Time analysis, it became very clear to
differed from the version presented here only me that that this ‘wriggling about’ on the screen
by having a cruder filter and a somewhat old- was the result of recurring signals of typical struc-
er-fashioned method of analog to digital con- tures, which could be resolved only if they could
version. To my surprise there appeared on the be compressed over prolonged periods of time.
monitor screen more than the power frequency They were also audible if played back at higher
hum that I was expecting but unfortunately the speed, sometimes reminiscent of animal sounds
confused serrations of the complex time signals or teletype transmissions on the short waves. In
did not allow me to draw any conclusions from any case, all this was sufficiently interesting to
about their composition. [this article was writ- keep me occupied with it ever since. Readers who

18
8 | October 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


ELF Receiver

are interested will find further detailed informa- be connected to other recording devices, all the
tion at the blog vlf.it [3], which is a platform for time keeping in mind that signals below 16 Hz
enthusiasts involved with receiving and experi- will be attenuated heavily by PC sound cards.
menting in the ELF and VLF bands. I have pub- The circuit is made up from a combination of a
lished a number of articles there on this theme highly sensitive voltage amplifier and a steep
along with many screen shots. (36 dB per octave) Sallen Key low-pass filter with
Among other things, we need to understand that a cut-off frequency of approximately 21 Hz. The
supply transformers in residential areas radiate receiver has the task of amplifying extremely
extremely weak magnetic waves between around weak magnetic waves in the frequency range
0.3 Hz and 25 Hz. These are up to 1,000 times from 21 Hz down to (almost) 0 Hz and filtering
weaker than the interference fields produced by out line hum interference in the process. Figure 1
the 50 Hz AC supply. To receive the desired fre- shows the schematic for this receiver, which is
quencies without interference, we need to filter made up from the functional groups that follow.
out the 50 Hz (60 Hz) supply hum as early as
possible ahead of the main amplifier in order to Linearizer and preamp
avoid over-driving the receiver. The extremely weak (in the microvolt region) AC
signals of interest here are picked up with a coil
The circuit and once processed and optimized in a combi-
The receiver described here operates in conjunc- nation of preamplifier and low-pass filter (IC1),
tion with the ADC module described in a separate they are directed to the Sallen Key low-pass filter
article, an Arduino Uno and some free—that goes that follows. This simple upstream low-pass filter
without saying—recorder software for the PC. This (a pre-filter so to speak) is necessary specifically
combination makes it possible to detect, display for attenuating any 50 Hz line frequency interfer- Figure 1.
and log weak alternating currents and/or alter- ence in relation to the wanted signal to prevent Schematic of the ELF
nating magnetic fields at frequencies down to less overloading that might generate a square-wave Receiver (without Data
than 1 Hertz. The receiver output can additionally signal between the maximum output voltages Logger).

R7
56k K2(S1)
1 2
R6
C1 3 4
120k TP1
5 6
R5 IC3 = TL074
10n 390k
R2 C6
10M R4 C4
9
470k C2 1u TP2
K1 6 8
IC1
8

R1 330n R12 R13 IC3C


2 2 7 10
IC2
8

100k R3 220n R10 R11 IC3B 18k 150k


1

6 2 1 5
OP07 10k R8 R9 IC3A 18k 220k
1

3 6 3
Coil OP07 22k 180k C7 TP3
3 C5
C3 22n
47n
68n
IC4
IFX25001TS V50 +5V
S2 L1 L2 +12V R16 P1
1 3
47k
100u 1 6 100u
+VIN +VOUT C22 C20 C18 1M
C8 C9 R15
13 K3
2

BT1 MOD1 10u 100n 47u L4 100k


C28 C27 C26 C25 C24 C17 C16 14
5 63V 25V 47u 47u IC3D
6V COM 25V 25V 12
R14
100u 100n 1000u 100u 2u2 C23 C21 C19 100n 100n
25V 16V 25V TMA0512D 2 x 47u
100k

2 4 0Ω6
-VIN -VOUT 10u 100n 47u 900mA
63V L3 25V

100u -12V
+12V +12V +12V +5V

R17
C10 C12 C14
1k5

7 7 4
100n 100n 100n
IC1 IC2 IC3 D1
C11 C13 C15
4 4 11

100n 100n 100n Power


140035 - 11
-12V -12V -12V

19
www.elektor-magazine.com | October 2014 | 9

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

of the op-amp. This could occur were the coil The stage built around IC2 is a well-known ‘stan-
to be placed close to a power cable in which a dard’ circuit involving an inverting amplifier. The
heavy current was flowing. The circuitry associ- gain factor can be varied by selecting one of sev-
ated with IC1 has a second function: the char- eral feedback resistors. This feature is absolutely
acteristics of the coil at the input of the circuit necessary since completely different intensities
mean that low frequencies are attenuated appre- of the received signal may arise, according to
ciably, so that the amplitude of received signals the position of the receiver. R4 is not a built-in
in the region of zero Hz is weakened increasingly. part of the selector switch, ensuring that there is
We can compensate or ‘linearize’ this to a large always some degree of negative feedback, even
extent using the effect of capacitor C1 in paral- when the switch settings are open-circuit. This
lel with R2. Figure 2 shows the amplification at has the advantage that at the moment of swi-
the output of IC1. tchover, when the switch contact ‘hangs in mid-
air’ for a very brief timespan, no interference
pulses appear on the receiver output.
The gain or amplification of the inverting ampli-
Audio Precision
+24 fier arises from the quotient negative feedback
+23
resistance divided by the upstream resistor:
+22

+21

+20
V = Rg/Rv
d +19
B
r +18

A +17 By switching from R7 down to R4 alone we have


successively (approximate) gain settings of 5,
+16

+15

+14 10, 21 and 47, the last of these values being


Figure 2.
+13
when the three switches or jumper links are all
+12

Amplifier flatness at the


10 12 15 20
Hz
22 25 30 32 35
140035 - 54
open-circuit.
output of IC1.
Filter
The remaining four op-amps are combined in a
+10
Audio Precision
single IC, the TL074. IC2A to IC2C together form
+0
a Sallen Key Filter with fast roll-off providing 36
-10

-20 dB per octave in total. The elevated level of the


-30

-40
50 Hz signal relative to the desired signal makes
d
B
-50 this filter extremely necessary, to prevent over-
r -60

A -70
loads. To learn more about Sallen Key Filters you
-80
can find the desired background information in
-90

-100 the technical literature and on the Internet [2].


The cut-off frequency of the filter is, precisely
-110

-120
Figure 3. -130
stated, 21.5 Hz, which is far enough removed
10 20 50 100 200 500 1k
Filter IC3 achieves a slope of Hz 140035 - 55

from the interfering 50 Hz and is still outside the


around 36 dB per octave!
desired reception range.
You should stick to the values given for the capac-
Audio Precision itors and resistors as closely as possible, as the
required transfer characteristic cannot be guar-
+0

-10

-20

-30
anteed. Figure 3 shows how steep the flanks of
-40
the resulting filter are (measured at the output
-50

d
-60 of IC3C).
B -70
r
-80
A
-90

-100
High-pass and final stage
-110 At high levels of gain (according to the setting
-120

Figure 4. -130 of P1 up to about 50,000) it’s possible that even


The common-mode choke
-140

-150
quite small offset voltages could nevertheless
6 10 20 50 100 200 500 1k 2k

reduces interfering noise by Hz 140035 - 56 be sufficiently large to shift the output signal by
up to 40 dB. several volts into the positive or negative regions

20
10 | October 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


ELF Receiver

and become an undesirable disruption. To avoid


this, a high-pass filter (C8+C9/R14) is provided
between the filter output (IC3C) and the input to
the amplifier stage IC3D following, with a cut-off
frequency arranged to lie well below the target
range. In this way the filter does not affect the
frequency response of the received signals. The
voltage at the the output of IC3D is thus always
symmetrical around zero. Trimpot P4 is used to
adjust the total gain of IC3D between 0.5 and
about 10.5. In conjunction with the switchable
pre-filter stage this should suffice for well-nigh
all user situations.

Powering the circuit


Power connections are provided for 6 V recharge-
able (or plain) battery operation. Initially the
voltage is reduced to 5 V and stabilized in IC4,
to suit the needs of the TMA0512D converter that
follows. This converter changes the input voltage
of 5 V into two complementary output voltages
of 12 V, used for powering the op-amps. Do not so thin that it would snap instantly if handled Figure 5.
omit any of the chokes and capacitors shown in roughly. The author’s home-made
the schematic of the power supply section, as During signal reception the coil must lie flat on coil winding machine.
these are absolutely necessary to reduce interfer- a non-metallic surface, as far away as possible Smaller versions will suffice
ence from electrical noise. Figure 4 shows, for from any AC power cables with current flow- for practical applications.
example, the beneficial effect of using the com- ing through them. Important: on account of the
mon-mode choke L4; this suppresses noise in the Earth’s magnetic field, the receiver should be
relevant frequency range by around 30–40 dB! operated only when the coil is not subjected to
If you prefer to power the receiver using an AC any movement or agitation.
adapter rather than batteries you can connect As an alternative to the pickup coil, the receiver
a 6-V wall wart power adaptor of the necessary can also be used with electrodes, consisting of
amps rating. metal probe spikes about 8 inches (20 cm) long,
pushed into the ground at a distance about 7 feer
Coil and electrodes (2 m) apart. In this way you can detect alternat-
To detect weak magnetic fields a sensitive receiv- ing currents in the prescribed frequency range
ing antenna is necessary, so we should connect a present in the Earth’s surface.
coil with around 2,000 to 4,000 turns of as large
a diameter as possible. This does not have to be Safety warning: If you are working with ground
as full-blown an affair as the one shown in Fig- electrodes bear in mind the risk of rogue AC
ure 5; a diameter of 12 to 20 inches (30 – 50 cm) power voltages in the soil. For this reason it is
will be perfectly adequate (to begin with). The vital to use a 1:1 microphone transformer (iso-
sensitivity of the coil (not to be confused with lating transformer) on the input of the receiver
its inductance!) increases linearly with the area whenever the receiver (or any other device con-
enclosed by the coil former and the number of nected to it) is powered from the AC supply. I
turns. The coil should be ring-shaped and if you have experimented with an example made by
buy the wire from a specialist supplier coiled in a the firm Jensen that has proved to be absolutely
roll [3], you can create your coil rapidly and eas- ideal (type JT-11P-1). A variety of suitable types
ily using a coil-winding machine made at home are shown on this American firm’s website [4].
from an old Erector or Meccano outfit. Use unscreened cable to connect the ground
Enameled copper ‘magnet’ wire of 30 AWG spikes to the transformer, the secondary side
(0.25 mm) diameter turned out to be a partic- of which is hooked up to the receiver input in
ularly good choice for making the coil. It is not place of the coil.

21
www.elektor-magazine.com | October 2014 | 11

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

The author’s prototype can be seen in Figure 6,


with Figure 7 showing the test build made with
stripboard in Elektor Labs.
Once you have finished the construction and test-
ing, the alignment of the receiver with the oscil-
loscope can begin. Hook the coil up to the input,
arm yourself with a strong magnet (such as one
from a loudspeaker) and investigate each of the
outputs of the op-amps in succession. At the out-
put of IC2 the line hum (so far only pre-filtered
and receivable everywhere) should not exceed
the 50 % overload limit. If the options available
at K2/S1 are insufficient for this, then the value
of R3 should be increased.
As you investigate each successive IC output,
the 50 Hz (60 Hz) sinewave components should
become ever weaker. Now set the oscilloscope
to 1 V/Div and move the magnet to and fro by
hand at a distance of two meters from the coil,
once or twice a second. You should now be able
to observe clear deflections up to the clipping
limit. It should also be possible to detect a slight
ripple even without moving the magnet, result-
ing from ambient signals (unless your home is
Figure 6. Alignment, connection and testing in the middle of a forest). Next adjust P1 so that
The author’s first prototype. A printed circuit board layout is not provided for the peak values of this ripple amount to no more
The Arduino data logger is the circuit of the ELF receiver, so readers inter- than ±1 V and lie within the optimum range of
also visible in the case.
ested in replicating it must resort to self-help or the A-to-D converter. The output signal should
simply assemble the small number of compo- be free of any offset voltages whatsoever. Also
nents involved on a piece of perf-board or strip the line frequency sinewave oscillations should be
board (Vectorboard; Veroboard). Programs like barely detectable now. At output K3 you should
Figure 7.
Test build signed off by LochMaster from Abacom or the free Blackboard now have a pure AC signal for downstream pro-
Elektor Labs. [5] will be of assistance for laying out the board. cessing by the ADC.

Installation and
operation of the recorder
Now connect the ELF receiver to the 16-bit Data-
logger module described in the September 2014
edition of Elektor [13]. The ADC samples the
signal with a resolution of 15 bits and a sampling
rate of around 112 Hz. The article also explains
how the ADC module can be connected to an
Arduino Uno, which accepts the digitized data
using a simple program (Sketch) and relays this
to the PC and the recording software.
The recorder software is written in the Processing
programming language [12], which resembles
C. Curly brackets are used for code blocks; each
instruction must be closed off with a semicolon.
The programming environment is very simple:
just open the Editor and write the source text.
Then click on the Start button and you’re rolling.

22
12 | October 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


ELF Receiver

What is ELF?
ELF signals are a mysterious and, to some
degree, myth-ridden subject that amounts in
reality to nothing more than electromagnet-
ic waves of extremely low frequency (hence
ELF) from 3 Hz to 30 Hz. Because commercial
radio transmissions do not exploit such low
frequencies, it is naturally fascinating to inves-
tigate what is going on in this profound realm.
Wow! This signal occurred on one single occasion
over a night in September 2013. Duration around
In residential areas many of the signals de-
one hour. Recording made with electrodes. Frequency
tectable with the receiver described here
range: 0 to 20 Hz.
clearly take the form of magnetic waves ra-
diated by supply transformers at the local
substation. The sprawling network of metallic
conductors (ground connections, water and
gas pipes, etc.) evidently behave like a vast
underground antenna that gathers up the
weakest low-frequency alternating currents
flowing in the ground, wherever they may
arise from, and transports them to a common
connection point at the local substation. Here
A square-wave signal of 1.6 Hz, which arises in
(this is merely an assumption) these currents various locations across all Europe at irregular times.
are radiated as magnetic fields by the ground- Typical characteristics: phases of activity and intervals
ed Petersen Coil (used for ground/earth leak- changing regularly.
age compensation).

In addition to these signals, previous consid-


ered indeterminate, we must note the increas-
ing level of (mainly daytime-only) ‘pollution’
coming from (presumably) commercial and
communal installations such as inverters,
frequency changers and switch-mode power
supplies. With a little patience it is also fea-
sible to prove the presence of the fascinating Extremely powerful 16 Hz bursts, concentrated at
so-called Schumann Resonances [11] in the particular locations and even audible direct as a deep
region around 7.5 Hz along with the 16 2/3 hum in audio amplifiers.
Hz (50 Hz ÷ 3) ‘signature’ of traction current
used by electric trains, which makes an excel-
lent marker signal for testing and calibrating
the receiver (in places where traction current
uses this frequency). Another conceivable ap-
plication (somewhat frivolous in comparison)
for the receiver is as a highly sensitive detec-
tor for (exclusively) moving metallic objects.
Passing automobiles, for example, can be de-
tected at distances of up to around 20 meters
or 60 feet. Sounding like whistling when played back at high
speed, this sample has reappeared daily for several
hours at the author’s place of residence over the
The following shots show examples of some
years.
varied and interesting ‘signal harvests’:

23
www.elektor-magazine.com | October 2014 | 13

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Operation
Operation of the software recorder in the Win-
Figure 8.
dows-style window (Figure 9) is virtually self-ex-
Power section and filter/
planatory. The test results are shown in three
amplifier should be placed
windows on the left-hand side.
as far apart as possible from
one another. Inductance L4
is fitted in between them Time signal
(here on the underside of An iteration takes five seconds. After the program
the PCB). starts a signal is always visible here, even if it is
not being recorded—and after recording stops.
Software installation
To get a Processing program to run on your com- FFT vs. Time
puter, you need to download the necessary soft- Every x seconds (x depending on the value set
ware from the Internet onto your machine. when downsampling) a new line is plotted—even
Go to the Processing website [7] and follow the if no recoding is being made—and after record-
instructions given there. The data downloaded ing stops.
can go into any folder you choose on the hard
disk. Within this data is also a file with the name Supervisory signal
processing.exe. Run this program if you want to After each iteration of 5 seconds, the highest
write Processing software of your own. Numerous amplitude of this time segment is indicated in
impressive sample programs not only showcase the upper window.
the powerful capability of this language but also
indicate how you can make the best use of it. The parameters for measurement and display
The Recorder program written in Processing can are set on the right-hand side of the recorder:
be downloaded from the Elektor website [8] into
any folder of your choice. Recording time
Length of the recording.
Important: The Processing program must be
located in a sub-folder bearing the same name Downsampling
as the program itself—but without the ‘.pde’ suf- Zoom in the Y direction in order to see the lower
fix. Also all resources required by the program frequencies better. Relates only to the FFT dis-
(such as .wav files or associated graphics) must played and not to the recording.
be kept in this sub-folder. After double-clicking
on the recorder file (Recorder_.....pde) the Pro- FFT brightness
cessing editor window opens automatically and Renders the FFT displayed brighter or darker.
the program code is implemented. Relates only to the FFT displayed and not to the
In the following line you need to replace ‘COM3’ recording.
and enter the COM interface of the PC allocated
by Arduino (see Device Manager in Windows): FFT scrolling
Pages forwards and backwards through the
serport = new Serial(this, “COM3”, 115200); analysis data displayed. Valid only for the data
recorded during the current recording phase still
Then save the program code with File Ž Save. held in RAM. FFT data is not stored on the hard
After a (single) click on the arrow at top-left in disk.
the Editor window, the program begins. The Editor
window with the source code remains during this Mouse position
process on the screen (in the background). Unfor- Mouse position coordinates and number of but-
tunately (and not for want of searching count- tons clicked. Very important if you wish to work
less different sources) I have not managed to on the program yourself.
find a working .exe file for the program. Further
information about Processing can be found in the Recording
Editor itself (Help Ž Reference) and on countless Left-hand button
other Internet pages. Normal method of starting a recording of a dura-

24
14 | October 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


ELF Receiver

tion enter above, automatic saving at the end of


the set time and regular saving intermediately.
Show bright red during recording.
Note that the names of files saved automatically
contain the start time and the intended stop time
(for example 18:20, if the recording began at
12:20 and was set to record for six hours).
If the recording is cancelled ahead of time, you
will find the previously saved data under file name
planned at the outset (2014_07_02_1220_1820).
The file can nevertheless contain just nulls rather
than data from a particular point in the record-
ing, according to the moment of premature can-
cellation. This is because in this programming
language it is possible to save only complete
Arrays and not, as is otherwise normal, only the
section occupied with data. For this reason files
always retain their full size, even if cancelled case, the stop time specified in the file name is Figure 9.
prematurely. the clock time valid at the actual time of cancella- Graphical interface of the
tion. Pressing this button produces an additional recorder software.
Center button file afterwards.
For intentional buffering. This has the same valid-
ity for the filename as with automatic saving. Data output window
Pressing this button makes it possible to observe at lower right-hand edge of screen:
the data recorded up to the current time in an After starting, the time remaining until the time
analyzer. when the recording will end is displayed here
automatically, based on the record duration set.
Right-hand button At the very bottom is the file name, which is also
This button cancels the recording and saves the retained during buffering.
data recorded so far to disk. Note that in this (140035)

Web Links
[1] Online ELF blog: www.vlf.it
[2] https://en.wikipedia.org/wiki/Sallen%E2%80%93Key_topology
[3] Coiled wire: http://www.jameco.com/1/1/379-30pe-awg-plain-enamel-magnet-wire-1-4-lb-825-ft.html [USA],
http://www.scientificwire.com/acatalog/Solderable_Enamelled_Copper_Wire.html Ref: SX0250s-D200 [UK].
Alternatively just look on eBay.
[4] Input transformer: http://www.jensen-transformers.com/ln_in.html
[5] http://blackboard.serverpool.org/
[6] www.elektor-labs.com/project/arduino-16-bit-low-frequency-datalogger-130485-i-140035-i.13703.html
[7] http://processing.org/
[8] www.elektor-magazine.com/140035
[9] https://groups.yahoo.com/neo/groups/VLF_Group/info
[10] http://naturalradiolab.com/
[11] http://en.wikipedia.org/wiki/Schumann_resonances
[12] http://en.wikipedia.org/wiki/Processing_(programming_language)
[13] www.elektor-magazine.com/130485

25
www.elektor-magazine.com | October 2014 | 15

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

16-bit Data Logger


An ADC module for Arduino,
Elektor Linux Boards and more
By Jens Nickel To make accurate voltages
(Elektor Germany)
measurements you need an A/D
converter (ADC) chip which has
good resolution. The folks at
Elektor Labs have developed a
board containing a four-channel
16-bit ADC. It’s no coincidence
the board uses a Gnublin/
EEC connector which makes it
compatible with the Elektor’s
Linux board, Xmega Webserver
and the new Extension shield for
Arduino. A universal C library is
included to make integration a
walk in the park.

This project is a good example of where our Hunting for ELF signals
web-based project platform Elektor.Labs [1] has At Elektor.Labs you can read more details of the
provided the spark for new ideas. Kurt Diedrich, original project [2]: The ELF signal picked up by
an author well known to us, has recently been the large wire loop is first amplified, filtered and
busy experimenting with an Arduino Uno to then given a DC offset of 2.5 V so that the signal
expand his knowledge of microcontroller firm- swings between 0 and 5 V and does not go nega-
ware. It didn’t take too much encouragement tive. The Arduino Uno uses an ATmega328 which
to persuade Kurt to share his experiences with already has a built-in A/D converter but with only
a wider audience via Elektor.Labs. One of the 10-bit resolution. Kurt Diedrich did some research
designs he came up with is a data logger where and ended up ordering a small PCB from Ada-
an Arduino Uno measures a signal level and fruit which has on-board an ADS1115 (from TI).
sends it to a PC [2]. Kurt’s previous experience
with PC programming and graphical user inter- This particular A/D converter has four input chan-
face design could now be put to good use: using nels and can measure signals with 16-bit reso-
the programming language called Processing lution [3]. An I2C bus is used for control and to
he designed a Tool that not only represents the pass information between the chip and microcon-
sampled signal but can also performs spectral troller. It wasn’t long before Kurt was studying
analysis. The complete setup is ideally suited the Arduino code examples and software libraries
for processing the reception of low-frequency supplied by Adafruit. The routines he needed to
electromagnetic signals to be discussed in a implement are not complex; after a little tin-
follow up article describing an ELF Receiver kering with the code examples the data logger
(ELF = extremely low frequency). firmware was finished. An endless loop in the

26
40 | September 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


16-Bit Data Logger

Figure 1. 16-bit data capture using an Arduino:


The ADC module connects to the Elektor Extension shield ARDUINO
ADC-BOARD
via the Gnublin/EEC connector and the shield plugs into
K1
the Uno board. K3
flatcable

main program repeatedly calls the function ads.


USB
getLastConversionResults() from the library, K2
K2
which returns the latest measurement value from EEC / GNUBLIN

the ADS1115 . This is then sent over the serial


interface from the Arduino to the PC. There is no ELEKTOR EXTENSION SHIELD
delay or timer control implemented in the firm-
ware, the measurement frequency is only gov-
erned by the A/D converter’s sample rate. New
values are sent at a rate of about 112 Hz which
Kurt was able to deal with in his PC software.

The concept
The prototype worked really well but the fin- USB
ished set up looked a bit untidy with all those
flying leads between the ADC module and Arduino
board. Labs set about making improvements; the 130485 - 12
main decision was to not make the design into a
dedicated ADS1115 Arduino shield but instead
opt for a more flexible approach that would allow
the board to easily interface to a number of dif-
ferent systems [4]. C1
+3V3
47p
R2 ALERT/RDY POWER
100k
The ADS1115 chip should derive its power from D1 D2
R1
the attached controller board and be controlled 4
100k
REF2912 1
via an I2C bus. A good choice for the interface +3V3 AIDBZT R3 IC2
3 1V022
120k R8 R9 R10
would be the 14-way pin header used by the EEC/ 1 5
IC3 2 0V511 OPA377
C4
560R

1V25 560R IC2


1k

Gnublin boards. The ADC module can then be con- 100n 2


3

C3 C2 R4 R5 T1
nected via a length of flatcable to the Elektor-Li-
270k
120k

nux board [5], the Xmega-Webserver board [6] 470n 10u

or the Elektor Extension Shield [7] (Figure 1). 2N7002


Screw clamp terminal blocks have been used K1 IC2
JP1
for connection of the four analog input voltages.
The chip cannot measure any voltage level which
+3V3 JP4
goes negative below 0 V so to measure alternat- C5 I2C Address
1 2
ing voltages it is possible to select an offset of 3 4
K1 IC1 100n +3V3
around 1 V at the first analog input. 5 6
8

AIN0 7 8 K3
VDD

AIN1 4 1 EEC/Gnublin
AIN0 ADDR
Voltages 5
AIN1 ALERT/RDY
2 1 2
6 9 3 4
The ADC board circuit diagram is shown in Fig- 7
AIN2 SDA
10 5 6
K2 AIN3 SCL
ure 2. The Gnublin/EEC connector used by the R6 R7 7 8
GND

AIN2 9 10
board specifies a 3.3 V supply voltage but the ADC
2k2

2k2

AIN3 ADS1115 11 12
3

chip can operate with a supply range between IDGST JP2 JP3 13 14
2.0 and 5.5 V.
+3V3
130485 - 11

Figure 2. Schematic of the data logger ADC card.

27
www.elektor-magazine.com | September | 41

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

VDD

ADS1115 Comparator
Voltage
Reference ALERT/RDY
AIN0
AIN1 ADDR
AIN2 16-Bit 2
MUX PGA IC SCL
AIN3 ADC Interface
SDA

Figure 3. Oscillator

The ADS1115 has a few


GND 130485-13
built-in niceties such as an
integrated comparator.

The data sheet [3] gives details of how the chip diodes on the inputs which provide some degree
can be controlled and configured using I2C com- of protection but the data sheet recommends fit-
mands. It can be configured to measure: ting external zener diodes and series resistors to
give better protection.
• The voltage level on AIN0, AIN1, AIN2
and AIN3 relative to ground (i.e. four ‘sin- Jumper JP1 can be fitted to provide a 1.022-V
gle-ended’ inputs). offset. The voltage level is made up of the 1.25-V
• The voltage level on AIN0 relative to AIN1 reference voltage level produced by IC3 and the
and the voltage level on AIN2 relative to standard op-amp IC2. When the offset is applied
AIN3 (two differential inputs). the input voltage range is ±2.048 V. An AC input
• The voltage level on AIN0 relative to AIN3 signal swinging between the values of around
and from AIN1 relative to AIN3 (two differ- –1 V and +1 V will be translated into a voltage
ential inputs with a common node). at the ADC input AIN0 swinging between 0 to 2 V
with 15-bit resolution. In the software be aware
The chip outputs a digital value in the range that higher input voltages produce lower output
from –32768 to 32767; negative values indicate values (inversion).
a negative differential voltage (negative values
are expressed in twos-complement format). In Another possibility is to add the offset to AIN0 and
single-ended mode the voltage will always be use the tip described above. With the measured
positive so that the output values will be in the voltage applied to AIN1 or AIN3, the correspond-
range 0 to 32767 which corresponds to a 15-bit ing differential mode configured and a full-scale
resolution. Using a workaround suggested by Ton range of ±1.024 V set. This method makes it
Giesberts in our lab and described in more detail possible to measure a voltage in the range from
on the .Labs Website [8] it allows measurement 0 to 2 V with a 16 bit resolution.
of negative-going signals while producing a 16-bit
value: Apply a fixed DC voltage, say 1 V on input Timing
AIN3. Now an input voltage of 0 to 1 V on the The ADC operates using the Delta-Sigma princi-
inputs AIN0 and AIN1 produces a negative out- ple, which gives good resolution and accuracy.
put value when the corresponding differential This method of A-D conversion however is not the
mode is selected. fastest. A rate of up to 860 samples/s is possible.
The sample rate is configurable and has a default
In addition to an internal voltage reference the value of 128 samples/s. Like many other ADCs
ADC also has a built-in programmable amplifier the ADS1115 can work in single-shot or contin-
which allows you to setup the full scale voltage uous mode. In single-shot mode it is necessary
range that the ADC will measure. In our case, with to issue a command to the chip to tell it to mea-
a 3.3 V operating voltage, the ranges ±2.048 V, sure the input voltage. Once the measurement
±1.024 V, ±512 mV and ±256 mV are of interest. is complete and a valid digital value is available
With this board it is important to ensure the the chip will set a bit in one of its internal regis-
measured input voltage does not go above 3.6 V ters. The external microcontroller monitors the
or below –0.3 V. The chip uses integrated ESD state of this bit and reads the new value from an

28
42 | September 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


16-Bit Data Logger

internal register when it becomes available. It can the role of a slave. Using just write operations you
then go on to request a new measurement. In can, for example set up an internal configuration
continuous mode the chip continually measures registers or tell the chip to start a measurement
the input voltage and produces digital values process. In order to read out a digital value we
without the need for any external intervention. need to both write and read over the I2C bus.
In all our programs including the ELF receiver To be precise you need to write twice (which
application we use single-shot mode in a contin- includes the slave address) and then read once.
uous loop. After each new reading (and before The chip’s slave address can be set-up externally
issuing the next sample command) the value is so it allows more than one ADS1115 chip to be
processed in the microcontroller (e.g. to show connected to the same two bus wires (provided
on the display or send over the serial interface). you use different addresses for each chip). The
Using the default sample rate of 128 samples/s slave address is defined by how pin 1 is con-
produces a data rate of about 100 to 120 Hz nected. There are four possible slave addresses
which should be sufficient for the majority of available; pin 1 can be linked to either pin 3, 8,
data logger applications. 9 or 10 using a jumper on the header pins of JP4
to define the address.
The comparator
The Conversion-Ready-Pin (IC1 pin 2) can be The two I2C signals are connected from the
used to indicate when an A-D conversion has chip to pins 5 and 6 of the EEC/Gnublin connec-
been completed. The ADS1115 can also be con- tor. Jumpers JP2 and JP3 allow you to use the
figured to act as a comparator (Figure 3) and on-board pull-up resistors. The beauty of the
in this mode the pin acts as an alert output. I2C bus is that you can safely interface a slave
Now using values stored in the Low Threshold device operating at 3.3 V with a controller such
and High Threshold registers you can allow a as an Arduino Uno running at 5 V.
sort-of hysteresis or apply a voltage compari-
son window to the measured value so that an The software library
alert occurs only if the measured value is outside When it comes to the control software you know
these stored values. that even if you opt for the default settings of
In our module this output is made visible via the ADC you will still need to spend some time
transistor T1 and a yellow LED. In addition this studying its data sheet. Controlling a microcon-
signal is routed to pin 11 of the Gnublin/EEC con- troller’s I2C interface can also sometimes be a
nector K3 where it is available for use by either bit tricky. Don’t worry; we have simple solutions
the Linux- or Xmega-board but has no connection that should get around these potential problems.
on the Elektor extension shield. The technical boss at the Elektor Labs Clemens
Valens has written a C library that avoids the need
I2C to define which registers you need to address in
As we already mentioned communication with the the ADC and instead provides high level func-
ADC occurs over an I2C interface where it plays tions to control the chip. As a bonus he has also

Web Links
[1] www.elektor-labs.com
[2] www.elektor-labs.com/project/arduino-16-bit-low-frequency-datalogger-130485-i-140035-i.13703.html
[3] www.ti.com/lit/ds/symlink/ads1115.pdf
[4] www.elektor-magazine.com/130485
[5] www.elektor-magazine.com/130214
[6] www.elektor-magazine.com/120126
[7] www.elektor-magazine.com/140009
[8] www.elektor-labs.com/contribution/from-the-lab-using-differential-mode.14034.html
[9] www.elektor-magazine.com/120668

29
www.elektor-magazine.com | September | 43

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

As a bonus the functions

ADS1x1x_start_conversion(&my_adc);

and

uint16 Result = ADS1x1x_read(&my_adc);

are available.

my_adc is a structure, defined at the start of the


program (ADS1x1x_config_t my_adc;) which is
filled via the function ADS1x1x_init(…) with the
required configuration parameters. All following
commands will be given a pointer to this config-
uration structure. More structures can be defined
so that the library can allow more chips to be
Figure 4. addressed on the same bus and independently
To test the ADC module and configured.
the Data logger application
connect a wire from the Using the following command, for example
Arduino pin A3 to the ADC
indicates that the slave chip on the bus with
input at AIN0.
its address pin connected to ground will be
addressed. The input AIN0 will be used in sin-
integrated a small I2C software library, it uses gle-ended mode, the measuring range is –2.048 V
a bit-banging technique to generate the I2C sig- to 2.048 V.
nals. This means that they are also applicable to
controllers that don’t have a built-in hardware ADS1x1x_init(&my_adc, ADS1115, ADS1x1x_
I2C interface. The complete implementation can I2C_ADDRESS_ADDR_TO_GND, MUX_SINGLE_0,
effectively be used with any platform for which PGA_2048);
there is a C compiler. The files, together with a
brief description are available to download from The second parameter indicates that an ADS1115
the web page related to this article [4]. chip is addressed, the library is also usable for
the other ADS111x devices.
First off, bind the ads1x1x.c/.h and soft_i2c.c/.h
files to your own software project. Make sure you The Data Logger software
refer to them with an include statement in your To get a good overview of the design it is a worth-
code. In order to get it on your own microcon- while exercise to study the source code of the
troller, it is necessary to implement the following data logger Arduino sketches, which uses the
five functions (which shouldn’t be too difficult): libraries referred to above [4]. In the next issue

void soft_i2c_scl_write(uint8_t value) // write high or low state to the SCL pin

void soft_i2c_sda_write(uint8_t value) // write high or low state to the SDA pin

uint8_t soft_i2c_sda_read(void) // Read the SDA pin state

void soft_i2c_sda_mode(uint8_t value) // configure SDA pin as O/P (value=1) or I/P (value=0)

void soft_i2c_delay(void) // 8 µs delay

Five further functions bind the ADC library (from you will find more demo programs and interesting
Clemens) with the I2C software library, this code applications which make use of the Embedded
can just be dropped 1:1 into the project. Firmware Library [9].

30
44 | September 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Component List
Resistors (0.1W, 0603) IC1 = ADS1115IDGST
R1,R2 = 100kΩ 1% IC2 = OPA377AIDBVT
R3,R4 = 120kΩ 1% IC3 = REF2912AIDBZT
R5 = 270kΩ 1%
R6,R7 = 2.2kΩ 1% Miscellaneous
R8 = 1kΩ 5% K1,K2 = 3-way PCB screw termi-
R9,R10 = 560Ω 1% nal block, 0.2’’ pitch
K3 = 14-pin (2x7) pinheader, 0.1’’
Capacitors (0603) pitch
C1 = 47pF 5%, 50V, C0G/NP0 JP1 = 3-pin pinheader, 0.1’’ pitch,
C2 = 10µF 20%, 6.3V, X5R with jumper
C3 = 470nF 10%, 10V, X5R JP2,JP3 = 2- pin pinheader, 0.1’’
C4,C5 = 100nF, 10% 16V, X7R pitch, with jumper
JP4 = 8-pin (2x4) pinheader, 0.1’’
Semiconductors pitch, with jumper
D1 = LED, yellow, 0805 PCB 130485-1
D2 = LED, green, 0805
T1 = 2N7002 (SMD SOT23)

Our Arduino sketch performs the same software It is probably easiest to upload the sketch using
function as Kurt Diedrich’s original project: An the Arduino bootloader, that way you only need
endless loop repeatedly tells the ADC chip to a USB cable between the Arduino and PC. Once
measure and digitize the voltage at input AIN0 in the firmware has been flashed the measured val-
single-ended and single-shot mode. The measure- ues can be seen on the serial monitor display
ment range extends from –2.048 V to 2.048 V, in the Arduino development environment or via
while in Single-ended mode only 0 to 2048 mV a simple terminal emulator program (data rate
can be measured and with only 15-bit resolu- set to 115,200 Baud and the corresponding COM
tion. The decimal output values (0 to 32767) port selected).
after conversion are sent out as ASCII characters To achieve the highest measurement accuracy
over the serial interface, followed by a <CR> and it is better to power the Arduino from a bench
<LF> character. power supply rather than from a USB port. It
will provide much better common-mode noise
For testing we used an Arduino Uno fitted with performance.
the Elektor extension shield described in the
last issue [7] connected to the ADC board via a Some spooky signals
14-way ribbon cable. The I2C address of the ADC If you like you can now try out the recorder soft-
board is configured as ‘ground’ i.e. the jumper ware that Kurt Diedrich developed for a his ELF
is placed in the first position of JP4 nearest the reception experiments. Now when you turn the
Gnublin/EEC connector. Initially we will not use pot the values are recorded over time in soft-
any offset correction (JP1 jumper fitted nearest ware. You can also switch in the 1022 mV offset
the terminal blocks). and see how the measured values change. Volt-
Now to generate the voltage to measure we con- age levels in the range of approximately –1 V to
nect a flying lead from the Arduino pin A3 (you +1 V can be measured with 15-bit resolution,
can connect it at the shield box header connec- this set up can be put to good use investigating
tor as shown in Figure 4) to the AIN0 input the presence of ELF signals in your location. If
of the ADC board. The voltage on A3 can now this sounds interesting have a look at the ‘ELF
be adjusted by twiddling the pot on the shield; Receiver’ project described in this issue you may
this gives us a rudimentary test set-up to check be in for some surprises!
operation of the ADC board. The voltage at A3 (130485)
can be turned up to 5 V but it’s important that
the input voltage level does not exceed 3.6 V so
before connection ensure that the pot is turned
all the way down so that the voltage is at 0 V
then slowly increase it.

31
www.elektor-magazine.com | September | 45

Personal Download for Petar Crnojevic | copyright Elektor


•Labs

Arduino is a Tool
By Clemens Valens Barring you just woke up from a 10-year long coma you will have heard about
(Elektor.Labs) Arduino. Everybody is talking about Arduino and all & sundry are developing
programs (“sketches”) and extension boards (“shields”) for Arduino. We have
filled scores of pages in Elektor about, or on using Arduino. Here is another one.

to the Arduino
board to make
the serial port
MIDI compatible
(the Data signal
has to be inverted)
and connected it to the
device-under-test (DUT).
This article however is slightly different because We c o u l d h ave d o n e
it is not about an Arduino project but about without the transistor if we
using Arduino as a tool. I use Arduino quite had used a software serial
often because it is so easy to program and use. port on the Arduino, but it would have meant
I sometimes even use it as a calculator because more testing.
it is quicker to write an Arduino program (called
a ‘sketch’) than a PC application. With the tester ready all we had to do was power
up everything, lean back and watch everything
To give you an example, the other day at Elektor. work just fine. This to me shows the real power
Labs we had to test our prototype of the MIDI of Arduino: an easy-to-use multi-purpose tool
Channel Analyzer [1]. Hedwig our secretary had that can help you out in many prototyping and
brought a nice keyboard with MIDI capabilities test situations.
from home, but, for some reason, it wouldn’t allow So, if you are still wondering what all this Arduino
us to test the analyzer properly. We had run into fuzz is about, try to remember this article the
the chicken-and-egg paradox where we needed next time you can’t figure out how to test your
a MIDI analyzer to figure out the MIDI behavior almost-completed-but-not-working yet super-
of this keyboard to test the MIDI analyzer. So duper ultra gadget.
we called Arduino to the rescue. It took me less (140059)
than five minutes to write a sketch that sent a
Note-On and Note-Off message every second on
Web Link
a different, incrementing, MIDI channel. Elektor.
Labs veteran Ton Giesberts added a transistor [1] www.elektor-labs.com/node/3380

32
82 | July & August 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

My First Shield :-)


LEDs, buttons, display and more

In the microcontroller world as elsewhere,


learning by doing is a good approach. The
Arduino Uno, which features especially
low cost and a low entry threshold, has a
significant shortcoming: almost no on-board
peripherals. We have therefore developed
a compact shield that gives starters a text
display, LEDs and pushbuttons to provide a
good basis for their first projects. There are
also two extension connectors for users who
already have a bit of experience. They can
be used to connect relay modules, wireless
modules and many other devices.

By Jens Nickel Like it or not, very low-cost, mass-produced are fed out to two rows of socket headers which
(Elektor Germany) microcontroller boards have changed the electron- provide the basis for the shield concept. If you
ics landscape. If you want to or have to develop equip another PCB with a matching set of pin
a working project or demo that does not need headers, you can plug it directly into the micro-
very much computing power, you can simply controller board. A shield can hold a wide variety
grab an Arduino Uno – and there’s bound to be of peripheral devices, including displays, sensors,
one lying around somewhere, just waiting to be or interfaces such as Bluetooth or WLAN. Thanks
used. Beginners in particular benefit from the to the widespread use of the small Arduino Uno
free Arduino development environment, and all board, there are now hundreds of commercially
you need to download programs is a USB cable. available shields.
If you prefer to program in Basic, you can also
work with Bascom and the boot loader. Complex Getting started
programs in C or C++ are also possible with the Many of our readers are interested in learning
free AVR Studio environment and a small pro- how to work with microcontrollers and program
grammer, such as the AVR ISP mk2. in Bascom and/or C. For them, the Arduino Uno
is a natural choice. To become truly familiar with
Intelligent shields programming a microcontroller, you need to come
There aren’t many peripheral devices on the to grips with the key interfaces of the IC yourself
Arduino Uno; a single LED is all you get from at least once. The best way to do this, of course,
the board designers. You can also use the USB is to work with peripheral devices that use these
interface to access the microcontroller on the interfaces. Unfortunately, there is hardly any
Uno board (an Atmel ATmega328P) over its UART shield available that provides all the necessary
port. However, most of the microcontroller pins peripherals in a small, low-cost package, so we

33
66 | July & August 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Arduino Extension Shield

decided to develop our own shield. It contains a


display module, two user LEDs, two pushbuttons
and a potentiometer (Figure 1). That means you
can get started right away after you plug in the
shield. For larger projects the shield also has a
pair of connectors which allow other extension
boards to be connected over ribbon cables. A
relay board and a wireless module are already
available, for example.

The shield can be ordered from the Elektor Store Figure 1.


[1] as item no. 140009-91. if you are a nov- The shield is shown here on
ice programmer and you want to try out or use an Arduino Uno board, but it
this small board primarily for demo and exam- can also be used with other
ple applications, you actually don’t need to read 5-V Arduino boards.
any further in this article. Elsewhere in this issue
we describe some initial small applications for (see the “Voltages” inset). On our shield we con-
our shield, written in Bascom Basic. They are nected a power indicator LED to the 3.3 V pin,
also excellent for test purposes. For the C users so that you can see whether the Arduino board
(including would-be users) among our readers, is powered up when the shield is plugged in.
we promise that C software will be coming soon, There are also two user LEDs on the shield, which
since we plan to use shield fairly often in future can be driven by Arduino pins IO10 and AD2.
Elektor projects.

Socket headers Table 1. Arduino pins, microcontroller pins and shield functions
The socket headers of the Arduino Uno are dupli-
Arduino Pin ATmega328 Function
cated on the shield. There is an Arduino standard
SCL PC5 EEC-SCL (*)
for the signals available on these headers, which
must be adhered to regardless of the microcon- SDA PC4 EEC-SDA (*)
troller fitted on the Arduino board concerned. IO13/SCK PB5 ISP-SCK
The individual sockets are also called “Arduino IO12/MISO PB4 ISP-MISO
pins”. The Arduino pins and the corresponding IO11/PWM/MOSI PB3 ISP-MOSI
pins of the ATmega328 microcontroller are listed IO10/PWM PB2 LED2
in Table 1.
IO9/PWM PB1 ECC-GPIOB
IO8 PB0 ECC-GPIOA
Due to the display and the buttons, it is not
possible to plug another shield piggy-back onto IO7 PD7 LCD-D7
the Elektor shield. However, all of the Arduino IO6 PD6 LCD-D6
pins remain accessible when the Elektor shield IO5 PD5 LCD-D5
is plugged in, and in most cases their operation IO4 PD4 LCD-D4
is not affected by the connected shield, as you IO3 PD3 LCD-E
can see from the circuit diagram in Figure 2.
IO2 PD2 LCD-RS
Among other things, this applies to the analog
IO1/TX PD1 ECC-TX
inputs AD0 and AD1, the serial interface pins
RX and TX, and the digital IO pins IO8 and IO9. IO0/RX PD0 ECC-RX
Additional I/O pins can be freed up by pulling AD0 PC0 S1
the jumpers (JP1 and JP2) and unplugging the AD1 PC1 S2
display module. AD2 PC2 LED1
AD3 PC3 P1
LEDs, buttons and potentiometer
AD4 PC4 EEC-SDA
Two supply voltages are always generated on
AD5 PC5 EEC-SCL
Arduino boards: 5 V and 3.3 V. They are available
(*) Connected to AD4 and AD5 on the Arduino Uno
on a socket header and can be used by shields

34
www.elektor-magazine.com | July & August 2014 | 67

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

AD2 is actually intended to be used as an ana-


log input, but on the Arduino Uno board it is
100R
RX connected to the microcontroller port pin PC2,

R7

RESET 5
SCK
MISO 1
1k
GPIOA which can easily be configured in software as

R4
a digital output. LED1 is connected to AD2 and
10
2
4
6
8

3
ECC

ICSP
K1

K7
can also be used as a photosensor, as described
1
3
5
7
9

6
4
2
+5V

+5V
in the Microcontroller BootCamp article in this

MOSI
TX
100R
issue. According to the Arduino standard, pin
R6

GPIOB
1k
IO10 must be able to output a PWM signal. This
R5

gives us the option of using LED2 to visualize the


duty factor of that signal.
EA DIPS082

LCD1 Two pushbuttons and a potentiometer are avail-


VDD
VSS

R/W
RS
VL

D0
D1
D2
D3
D4
D5
D6
D7

able for user input. They are connected to the


E
1
2
3
4
5
6
7
8
9
10
11
12
13
14

AD0, AD1 and AD3 inputs. To allow AD0 and


LCD_RS

LCD_E

LCD_D4
LCD_D5
LCD_D6
LCD_D7

K4
SCL 10
SCL AD1 to still be used as analog inputs, we omitted
P2
10k

SDA
+5V

9
SDA
K3

8
8
7
AREF pull-up resistors and debounce circuitry. However,
7 GND
IOREF SCK 6
it’s very easy to connect internal pull-up resis-
3V3

6 RESET 1k IO13
RESET MISO 5
R3
LED3
3V3 +5V

5 IO12
3V3
5V
4
MOSI 4
3
IO11 tors in the ATmega328, both in C and in Bascom.
3 1k IO10
GND GPIOB 2
The potentiometer is connected to analog input
R1

JP1
LED2

2 IO9
GND GPIOA 1
1 IO8
VIN
1k
LED
AD3. If you configure the A/D converter of the
R2

JP2
LED1

ATmega328 with a 5 V reference voltage, which


K6

LCD_D7 8 IO7
LCD_D6 7 IO6 is common practice, the setting range is 1 to
S1

LCD_D5 6
K5

SDA IO5
AD0
1 330R LCD_D4 5 IO4 1023 (10 bits).
R8

2 LCD_E 4
AD1 IO3
LED LCD_RS
14
12
10

3 3 IO2
8
6
4
2

AD2
4 TX 2
EEC

AD3 IO1
K2

Display
S2

5 RX 1
AD4 IO0
140009 - 11

6
13
11
9
7
5
3
1

AD5
The alphanumeric display module from Electronic
+5V

SCL
10k

P1

330R
3V3

Assembly [2] is removable. It provides two rows


R9

of eight characters, which is sufficient for simple


indications. Two buttons are located next to the
display to enable simple menu control. We chose
Figure 2. Circuit diagram of the shield. The Arduino a display module with a 4-bit parallel interface,
signal lines are also available on socket headers on the which means that four lines in addition to the E
shield. and RS signal lines must be routed to the display.
This is a slight disadvantage compared to an SPI
interface, but software support for the parallel
Figure 3. A wide variety of extension modules can be
connected to the two extension connectors. interface is better. For instance, Bascom provides
specific instructions for writing character strings
to the display.
The display controller is of course HD44780 com-
ARDUINO
patible, which allows popular C libraries to be
433-MHz RELAIS used. The address offset for the second line is
40hex [3].

RS485
PORT-
EXPANDER
UART connector
K1 is a fully wired Embedded Communication
Connector (ECC), which has been described in
WIFI
detail in a previous article [4]. In accordance
(PLANNED) T-SENSOR
with the specification, the UART signals TX and
SHIELD
RX as well as two digital I/O lines are available
ECC EEC/
GNUBLIN ADC here, with a logic high level of 5 V. There is also
BLUETOOTH (PLANNED)
(PLANNED)
5 V constantly available on one pin for powering
140009 - 12
connected peripheral devices. In this case the

35
68 | July & August 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Arduino Extension Shield

Component List
Resistors K1 = 10-pin boxheader, 0.1” pitch
R1,R2,R3,R4,R5 = 1kΩ K2 = 14-pin boxheader, 0.1” pitch
R6,R7 = 100Ω K3,K4,K5,K6 = Arduino Shield stacking
R8,R9 = 330Ω header, Adafruit ID 85
P1 = 10kΩ trimpot with adjuster K7 = 6-pin (2x3) pinheader, 0.1” pitch
P2 = 10kΩ trimpot, SMD, Vishay JP1,JP2 = 2-pin pinheader with jumper, 0.1”
TS53YJ103MR10 pitch
LCD1 = LCD 2x8 characters with back-
Semiconductors ground lighting, Electronic Assembly
LED1,LED2 = LED, low-current, red (SMD DIPS082-HNLED
0805) 2 pcs. 7-way precision socket strip for LCD1,
LED3 = LED, low-current, green (SMD 0805) TE Connectivity 1814655-7
PCB # 140009-1 [1]
Miscellaneous or
Assembled board # 140009-91 [1]
S1,S2 = pushbutton

peripheral device is a small module that gives already been developed in the Elektor labs. The
user projects access to various interfaces to the latter allows the Arduino board to transmit and
outside world (see Figure 3). An RS485 module receive data wirelessly at an ISM frequency like
[4] and a wireless communication module have 433 MHz [5].

Advertisement





  
  
  
 
  
  
  
  
 
  



100uH
toroid YOU DESIGN IT – WE MACHINE IT

Professional quality front panels


www.schaeffer-ag.de

♦ ♦
♦♦••••
••••••
••••
From one piece and at a fair price! Simply
 download our free Front Panel Designer at


 www.schaeffer-ag.de, design your front
 panel and order it directly.


36
www.elektor-magazine.com | July & August 2014 | 69

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Voltages
Due to the countless shields now boards and automatically adjust which would make the shield more
available, the layout and pin to the operating voltage of the complicated and more costly.
assignments of the Arduino Uno socket microcontroller. That is why the However, we have not yet rejected
headers have become a sort of quasi- Arduino socket headers always have this plan, and there are already
standard for extension connectors. not only 5 V and 3.3 V supply voltage several prototypes in the labs. We
More and more microcontroller boards, pins, but also an IOREF pin that is decided to design a less complex
even with 32-bit processors, are being connected to the supply rail for the shield without level converters for the
equipped with this interface. However, microcontroller. Microcontroller BootCamp series from
some of these microcontrollers require Burkhard Kainka and relatively small
an operating voltage of 3.3 V instead We originally planned to develop projects. It is nevertheless possible
of 5 V as on the Arduino Uno board, a shield suitable for all types to connect 3.3 V peripheral devices
and their inputs and outputs are of microcontroller boards, and to the partially wired EEC connector,
therefore compatible with 3.3 V signal furthermore equipped with ECC and and the shield can even be used on a
levels. EEC extension connectors compatible 3.3 V microcontroller board with some
with both 5 V and 3.3 V peripheral restrictions.
Ideally, a shield can be plugged onto devices. That would of course compel
both 5-V and 3.3-V microcontroller the use of several level converters,

All signal pins of the ECC (TX, RX, GPIOA and a master device operating at 5 V, such as the
GPIOB) are connected to the corresponding Ardu- ATmega328 in this case, can easily be connected
ino pins through resistors, based on a suggestion to a slave device operating at 3.3 V, such as a
from Burkhard Kainka. This provides a bit of pro- Gnublin module. Both lines are held at the high
tection in the development environment, so that level by pull-up resistors, which in this case are
the Uno microcontroller will not die immediately located on the extension module, and pulled to
if something a bit higher than 5 V is inadvertently the active low level by the master or the slave.
connected to a pin. Resistors R8 and R9 attenuate reflections on rel-
atively long lines and provide some protection
EEC/Gnublin against noise pulses.
Extension modules compliant with the Gnublin/ The Gnublin modules available in the Elektor Shop
EEC standard can be connected to K2, which is include a board with eight relays, a port extender
configured as an Embedded Extension Connector with sixteen I/O lines, a temperature sensor and
(EEC). This connector is not fully wired because other devices [6].
the standard specifies a 3.3 V level and we omit-
ted a level converter to keep the cost down (see Programming
the “Voltages” inset). Most of the Gnublin mod- The Elektor shield provides everything you need
ules developed by the company Embedded Proj- for experimenting with or learning about the
ects, which are also available in the Elektor Shop, essential function of the ATmega microcontrol-
are controlled using only the I²C lines SDA and ler or another 5 V microcontroller on some other
SCL. One of the advantages of the I²C bus is that Arduino board: digital outputs and inputs, analog
inputs, a parallel interface (four bits), a serial
UART interface and I²C. The only thing that’s
Web Links missing is SPI. The pins for this are fed out to
[1] www.elektor-magazine.com/140009 connector K7, a 2x3 pin header. You can use
this connector to program the ATmega328P on
[2] www.lcd-module.de/eng/pdf/doma/dips082e.pdf
the Arduino Uno board, with the aid of a simple
[3] www.datasheetcatalog.com/datasheets_pdf/S/T/7/0/ST7066.shtml programmer such as the AVR ISP mk2. That will
[4] Elektor March 2014, www.elektor-magazine.com/130155 overwrite the Arduino boot loader, but it can be
[5] Elektor May 2014, www.elektor-magazine.com/130023 downloaded again using the Arduino IDE.
(140009-I)
[6] Elektor Gnublin series http://www.elektor.com/development/gnublin

37
70 | July & August 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Lathe Tachometer
Feat. Arduino Micro & OLED

By Andre Jordaan Here’s a non-invasive, all electronic add-on


(Switzerland)
to display the running speed (rpm) of your
lathe or milling machine, be it CNC or vintage. It’s state of
the art—witness the use of an Arduino Micro board and a .96 inch OLED
display for instantaneous readout. The little instrument also has a clock displaying
the equipment running time.

Attention Bridgeport lathe and milling machine Without even scratching the surface of elemen-
users; get in touch with an electronics geek and tary metalworking and finishing, electronicz peo-
have him build this circuit for you. ple should know that the turning speed is crucial
Attention Arduino users: build this circuit for a for anything that cuts, drills, mills, finishes or
nearby Bridgeport lathe owner and get access polishes metal, wood, glass, and recently, hard
to his prize machinery. plastics, Teflon® and rubber too. In the case
of a round steel bar being milled to end size,
In this project a reflective IRED / phototransistor the turning speed used to do the first couple of
device is used as a sensor to produce a retrofit rough passes using toolbit ‘A’ at angle x may
readout of the number of revolutions of a spin- differ considerably from that applied much later
dle (or “shaft”) on a lathe, a milling machine or for an ultra-smooth surface finish using toolbit
a similar piece of equipment in the metalwork- ‘B’ at angle y. In both cases, the shaft speeds
ing toolshop. have to be set and verified by the operator using

38
14 | June 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Lathe Tachometer

whatever gears or reduction drives are available black adhesive tape or similar is secured around
on the machine. the lathe’s shaft, leaving a narrow gap (of about
To the metalworker, the turning speed his prized 3 mm). Whenever the light emitted by the LED
machine is running at equals the supply volts and reflects off the shaft at the position of the gap,
amps to the electronics engineer. Get the turning it illuminates the internal phototransistor, caus-
speed (≡voltage) wrong and you risk destroying ing the SENS+ line to drop logic Low, and High
your precious stock material (≡64-bit ARM MPU), again when the LED light is not reflected. Hence
object being created (≡Linux dev system) and/ the speed of the rising edges of SENS+ signal
or $50K Bridgeport lathe (≡128-bit LeCroy logic indicates the shaft speed. Note that due to reduc-
analyzer). ≡You don’t want that to happen. tion gears being present in the lathe or milling
Where we write spindle or shaft in the remainder machine the shaft speed is not the motor speed.
of this article of course we mean chuck, 3-claw The Arduino Micro can be reset to force it to start
Figure 1. Schematic of
head, 4-claw head, boring head, end mill, polish executing its firmware from scratch by press-
the precision rev counter
pad, drill, tap, etcetera, since all of these tools are ing S1.
for CNC lathes and milling
fitted eventually to the powered shaft or spindle machines. All measurement
of the lathe or milling machine. Finally, the function of LED2 on Arduino Micro and control functions are
line D7 is free to assign by the programmer—like handled by an Arduino Micro
How it works over rev or call keith [4]. plug-on board.
As with most applications of embedded technol-
ogy the schematic in Figure 1 does not reveal
a lot about the workings or aim of the circuit. In
IC1
fact, you could be looking at NASA’s latest alliga- D1 78L05Z +5V
K1.1
tor counter for use at Cape Canaveral. One of the
reasons for the happy scarcity of components in 1N4148 R1
BT1
the schematic is the use of an Arduino Micro board

390R
C2 C1
9V
in position MOD(ule)1, resulting in all manner of
100n 100n LED1
things being controlled and decided by software
rather than discrete parts. The Arduino Micro is K1.2
first programmed with the project firmware of
+5V
course via its micro USB connector.
+5V R2

The unregulated supply voltage from a 9-V 6LR22


10k

MOD1 +5V
alkaline battery (or a 7 V to 9 V power adapter)
R3 R4
enters the circuit on K1, and gets reduced to 1 1
100R

S1 MOSI SCK
22k

5 volts by stabilizer IC1. LED1 acts as a Power K2 2


SS MISO
2

On indicator. LED+
1
RESET
3
TX VIN
3
2 4 ICSP 4
The Adafruit OLED (organic light emitting diode) LED– RX GND
3 5 5
SENS+ RST RST
display module [1] is connected straight onto 4 C3 6 6
SENS– GND +5V
8-pin connector SV1. The OLED module with its 7
D2 NC
7
10n
monochrome, 128 x 64 graphic display gets its SENSOR 8
D3 NC
8
SV1 9 9
5-volts supply voltage from the same regulator D4 A5
8 10 10
D5 A4
as the Arduino Micro. Other OLED modules may 7 11 11
+5V D6 A3
be used but be sure you match their pinout to 6 12
D7 A2
12
5 OLED_CS 13 13
the board. D8 A1
4 OLED_RESET 14 14
The only input device to the circuit, a reflective D9 ARDUINO A0
3 OLED_DC 15 MICRO 15
D10 REF
IRED / phototransistor (“reflective optical sen- 2 OLED_CLK 16 16
D11 3V3
sor” device) like the one at Yourduino [2], is 1 OLED_MOSI 17
D12 D13
17
R5
connected on K2. The LED inside the device is
OLED
390R

again powered from the +5 volts rail via R3. It


is on as long as the 5-V supply voltage is pres-
LED2
ent. The phototransistor’s SENS+ pin is pulled to
+5 volts by R4, and the signal fed to the INT/D3 130470 - 11

line of the Arduino Micro board. A piece of matt

39
www.elektor-magazine.com | June 2014 | 15

Personal Download for Petar Crnojevic | copyright Elektor


r p c bs
Component List to

er
.e l e k
K1.2 K1.1

v i c e.c
D1
Resistors

ww
R4 K2 R1,R5 = 390Ω 5%, 0.25W
Module 1 R3
om
R2 = 10kΩ 5%, 0.25W w
R2 R3 = 100Ω 5%, 0.25W
MOSI SCK C2
IC1
SS MISO
C1
R4 = 22kΩ 5%, 0.25W
TX VIN
RX GND
RST RST Capacitors
C3
GND +5V C1,C2 = 100nF 10%, 100V, 5mm pitch
D2 Arduino C3 = 10nF 10%, 100V, 5mm pitch
D3 Micro S1
D4 A5
D5 A4 Semiconductors
D6 A3 IC1 = 78L05Z
R5
D7 A2 LED1 = LED, yellow, 3mm
D8 A1 LED2 = LED, 3mm, color t.b.d., optional, see text
D9 A0
D10 AREF
D11 3.3V Miscellaneous
D12 D13 MOD1 = Arduino Micro, Farnell/Newark # 2285194
S1 = pushbutton, PCB mount, 6x6x9.5mm
SV1
SV1 = 8-way pinheader receptacle
8 1LED2 K2 = 4-way pinheader receptacle
R1 LED1 K1 = 9V battery connector clip + wires
Reflective Optical Sensor, like TCRT5000
Monochrome 0.96” 128x64 OLED graphic display, Adafruit #
Figure 2. Printed circuit board layout
326 (UG-2864HSWEG01)
designed by Elektor Labs for the project. 34-pin DIP socket for Arduino Micro (DIY from SIL pinheader
receptacles)
PCB # 130470-1

Software
Listing 1. Excerpt from Firmware.ino
The program “Firmware.ino” is recommended
//to be done when when sensor is interrupted: educational reading if you want to understand
void interrupt_rpm_time() all the ins and outs of the control program, and
{ how it got developed and tweaked. The program
// current_interrupt_time = micros();
is richly commended by the author.
// if (micros() - previous_interrupt_time > (1/fMax))
{
Arduino users will know how to transfer the file
current_interrupt_time = (micros() - previous_interrupt_time);
to their Arduino Micro board, starting from file
previous_interrupt_time = micros();
130470-1.zip, which can be downloaded free of
// Serial.print("+");
charge at [3].
// Serial.println(current_interrupt_time);
// digitalWrite(ledPin, HIGH);
} The Arduino program waits for a rising edge at
} its INT1 input and uses five rising edges to com-
pute the average time between them. Using some
math the rpm (revolutions per minute) is calcu-
void calc_run_Time() lated and sent to the OLED display.
{ A snippet of the program code is printed in List-
//calculating running time ing 1. Here we see how the interrupt produced
unsigned long elapsed; by the sensor gets handled, and the Tachometer’s
unsigned long over; internal clock is ticking to display the “up” time.
elapsed=millis();
h=int(elapsed/3600000); Build it, use it
over=elapsed%3600000; The printed circuit board designed by Elektor Labs
m=int(over/60000); has through-hole parts only and its component
over=over%60000;
overlay is given in Figure 2. Let the electronics
s=int(over/1000);
people handle the programming, board stuffing,
ms=over%1000;
soldering and wiring, and the mech people do
}
the mounting of the board in a case, and the

40
16 | June 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Lathe Tachometer

Figure 3. The Arduino Micro board secured on to the Figure 4. The Lathe Tacho board has boards fitted at
solder side of the tachometer board (early prototype). either side: an Arduino Micro at the solder side, and
a .96” OLED display at the front. Note the use of SIL
pin strip receptacles to ensure the correct mounting
distance.

mounting of the reflective sensor close to the


powered shaft of their lathe or milling machine.
If you are a mechatronics fan you do both jobs
with ease, in the proper sequence.

A slotted optocoupler and a vane fitted at a suit-


able place on the machine shaft may also be
suitable but the assembly is more intricate to
mount—if not invasive. If your machine shaft is
not reflective, stick a small piece of paper on it Figure 5. The Lathe Tachometer startup screens. The
to do the light reflection. OLED readout should blend in beautifully with all manner
of tech info and lights that can be seen in a 21st century
The Arduino Micro is plugged on to the rear (sol- metalworker’s toolshop.
der) side of the Tachometer board (Figure 3);
the OLED unit, on to the front (component) side
(Figure 4). should also be easy to add more channels and
other controls like relays etc. One wish of the
After switching on, the Arduino Micro initializes, author is send the count pulse on to Mach 3—the
then displays the Elektor logo and “Elector Elec- control software for his CNC machine.
tronics” (sic), then “Tachometer by A. Jordaan” (130470)
and the firmware version number (Figures 5a;
5b). Next, the current rpm value is displayed,
and the ‘up’ time of the tachometer (so you can
bill your customers and come across serious).

Over to you
The project being open in terms of hardware and Web Links
software, there should be nothing in your way to
[1] OLED display: www.adafruit.com/product/326
do custom adaptations like getting that k right. It
will be insightful for sure. The hardware for exam- [2] Reflective Infrared Sensor:
ple may be adapted to support different types http://yourduino.com/sunshop2/index.php?l=product_detail&p=217
of sensor types like Hall effect. Other possible [3] Arduino Micro firmware: www.elektor-magazine.com/130470
applications include a step counter, a rev counter [4] Keith Fenner’s Turn Wright Machine Works on Youtube:
for model planes, a PWM percentage meter, or a www.youtube.com/user/KEF791
simple event driven animation on the display. It

41
www.elektor-magazine.com | June 2014 | 17

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

3D Pad:
Touchless Gesture
Control interface
point to make the point

By Jean-Noël Lefebvre (France)

You can easily produce a Touchless


Gesture Control interface that’s capa-
ble of reliably providing 3-dimensional
co-ordinates (X, Y, and Z axes). This
simple, experimental device, designed
in collaboration with the Elektor Labs
team, consists of a sandwich made up
of a PCB called an electrode plane, an
Arduino Uno, and a shield, with control
software.

Be a part of the new revolution in person/machine Detection principle


interfaces, which began a long time ago with… How about ‘projecting’ capacitive detection?
punched cards, followed by keyboards, screens, To detect the proximity of the human body (e.g.
joysticks, mice… Today, touch screens are every- the hand or finger), we are going to be making
where, with so-called ‘gesture’ control, but using use of a technique known as projected capacitive
finger contact (to zoom, unlock, etc.) The new [3]. This is the principle of virtually all the touch
step that Elektor is inviting you to take now is screens on modern phones and tablets―except
touchless interaction, using gestures in the air in that here we are going to be detecting gestures
three dimensions. This isn’t science-fiction―this in the air, relatively far from the detector surface
article is here to prove to you that it’s even … at (10 cm max.) The principle is simple: normally,
your very fingertips. in our circuits, we expect a capacitor to present

42
8 | May 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Touchless Gesture Control

the least possible leakage of the electrostatic field


Specifications
outside its plates. Well, for our proximity detec-
• Touchless 3D gesture detection
tor, it’s just the opposite. We need a capacitor
• Projected capacitance via a plan of four electrodes, Z = 4 inches/ 10 cm
that’s as open as possible, built using copper
• Arduino shield and sketch
tracks (which we’ll be calling electrodes) on an
• Creative Commons license
epoxy panel, so as to obtain maximum “hand
effect” (Figure 1a).

An oscillator under the influence?


The capacitor formed by our electrodes is part Figure 1a.
of a logic-gate oscillator (Figure 1b) whose fre- The first step in
understanding this circuit
quency is influenced by the proximity of a hand
is to imagine the four
or finger when it enters the electrostatic field.
electrodes as capacitors:
This intruder in fact forms a third electrode which in the center, the common
is going to cut the field lines and divert the elec- electrode, and around it the
ON TOP SIDE
trical charges. One of the electrodes, connected ON BOTTOM SIDE 130508 - 13
4 spatialization electrodes
to an inverter output, at low impedance, is called (top, bottom, left, right)
emitting. The other, connected to the junction
between the resistor R and the inverter input
is called receiving; this is at high impedance
(depending on the value of R). Result: the closer
Z
the hand approaches the electrodes, the greater
the extent to which the capacitance between the
electrode diminishes, and the more the oscillator
frequency increases.
When the hand is 10 cm from the electrodes, the
1
oscillator frequency only varies very slightly―a receiver emitting
electrode electrode
few hundred ppm at the very most (100 ppm (top) (center) Figure 1b.
= 0.01%!) Now with this sort of oscillator, the 1 By diverting part of the
frequency is largely determined by other factors capacitive field projected
R by the electrodes, the
too – in particular, the temperature and supply
hand upsets the oscillator
voltage. So the main challenge in our circuit is to 130505 - 16
frequency.
distinguish the very slight variations in the oscil-
lation frequency caused by the hand from those
resulting from the other influencing factors. One What’s it used for?
part of this task is entrusted to the software, so it
There’s a wide range of applications―in the kitchen, for example, to
will also read from two reference electrodes that
adjust the oven or induction ring controls without touching them with
are not (or only slightly) influenced by the hand,
your greasy fingers! In the medical field, when care staff no longer have
but which are subject to all the other factors.
to touch devices, the risk of nosocomial infections will be reduced. In
the huge field of artistic expression, with instruments like the Theremin
“Switching” oscillator
which are played by using gestures in space. In the gaming field, like
As we’re not dealing here with a simple proximity
Fruit Ninja [1] or Despicable Me―Minion [1]. Instead of touching the
detector, but with a system capable of providing
tablet screen, you’ll soon be able to play with movements of your hand
co-ordinates in three dimensions (X, Y, and Z
in the air. I’m counting on you and your imagination and impatient to
axes), our oscillator will be connected to one of
see what you can create around the 3D-Pad!
six receiving electrodes in turn. This device has
four spatialization electrodes: top, bottom, left, Who is it useful to?
right, and two reference electrodes. In the cen- Anyone who wants it, as it’s a very open design. To make it easier to
tre of the electrode plane is the single emitting build and share, and above all to encourage you to express your own
electrode (Figure 1a). To ensure a good response creativity, it is presented in the form of a shield for Arduino. All the
time for the person/machine interface, the six design documentation, diagrams, and software are Open Source under
electrodes will be scanned in turn around 200 a Creative Commons CC BY-NC-SA 4.0 License [2].
times a second, in an operation vaguely akin to

43
www.elektor-magazine.com | May 2014 | 9

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

capacitance between electrodes IC6.D


12
11 ‘1’
& 13
receiver emitting
electrode electrode
(top) (center)

R9 IC6.A
1
3
2 & IC7.C
8
10
Figure 1c.
EN_TOP = ‘1’ 9 &
IC7.D
Detail of the switched ‘1’ 12
11
electrode oscillator circuit 13 &
from Figure 3. Here, the
logic circuit is shown ‘1’
configured with the top
electrode (EN_TOP = 1) 130505 - 15
connected to the oscillator.

multiplexing. The software’s job, at each step the logical AND and NAND operators (IC6, IC7,
in the scanning, is to analyze the oscillator fre- and IC8). You’ll also see that the switching and
quency with each of the electrodes in turn. receiving electrode (EN_X) selection signals come
Figure 1c shows the electrode oscillator in the from the Arduino Uno board (top left). The nom-
state it is at the moment the top receiving elec- inal frequency of our oscillator, in the absence
trode is in circuit. The control signal EN_TOP is of hand influence, is set by R9–R14 at around
high, all the other control signals EN_X are low. 1.6–1.8 MHz.
The three ports IC6A, IC7C, and IC7D now form
just a simple inverter. IC6D is also configured Now that we have an oscillator whose frequency
as an inverter. varies by a few hundred ppm according to the
So this circuit is equivalent to that of the “easily proximity of a hand, all that remains for us to
influenced oscillator” in Figure 1b. With a bit of do is to derive – if possible using a simple solu-
concentration, once you have familiarized your- tion―from that a signal that can be used for a
self with the circuit, you’ll be able to find it in final application. To do this, we need a frequency
the full circuit diagram in Figure 3, by spotting comparator comprising:

external
12 VDC linear 9V 3D Arduino Shield
power supply regulator

préscaler
12V top

phase/frequency
Aalog comparator 9V 5V
Input
buffer
right

center
left

injection
Arduino UNO
SPI reference
DAC SPI VCO
bottom
reference
VCO
USB 5V 9V
serial Port

Figure 2.
130508 - 14
The functions of each of the data to host
three boards.

44
10 | May 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Touchless Gesture Control

IC5 TP1

K6 +5V +9V VIN 78L09F +9V


1
AREF
2
GND
3 SPI_CLK C10 C11 C12
MOD3 13 C9 C8
4
K3 12
100u
6 5 SPI_DATA 100n 100n
TP2 RST 11 100n 100n 16V
5 6 DAC_CS
+3.3V 10 1 16
4 7 MCU_EN_REFA
+5V +5V ARDUINO 9 VCC VDD
3 8 MCU_EN_LEFT MCU_EN_BOT 3 2 EN_BOT
GND 8 AI AO R15 K7
2 MCU_EN_RIGHT 5 4 EN_RIGHT LED1 1
GND BI IC4 BO 470R
1 1 MCU_EN_TOP MCU_EN_REFB 7 6 EN_REFB 2
VIN VIN 7 CI CO
TP3
2 MCU_EN_REFB MCU_EN_TOP 9 10 EN_TOP
6 DI DO
CPF_OUT 6 3 MCU_EN_RIGHT MCU_EN_LEFT 11 4504D 12 EN_LEFT
0 5 EI EO R16 K8
SCPF_CLEAR 5 4 MCU_EN_BOT MCU_EN_REFA 14 15 EN_REFA LED2 1
1 4 FI FO 470R
ANALOG IN

VCO_INH 4 5 ENOSC_SENSE 2
2 3 MODE GND
LED1 3 6 SYNC_SCOPE
3 2 13 8
LED2 2 7
4 TX +9V
1 8
5 RX
K4 K5

14 C15 14 C17 14 C16


IC6 IC7 IC8
K1 7 100n 7 100n 7 100n
IC6.A
1 ELEC_TOP 1
3
2 EN_TOP 2 & IC7.C
8
3 10
IC6.B 9 & +5V
4 ELEC_LEFT 5
4 IC7.D
EN_LEFT 6 & 12
11
IC6.C
13 &
ELEC_CENTER_TL ELEC_REFA 8
10 1 C18
EN_REFA 9 &
IC9
R9 R10 R11 8 100n
C13

* IC6.D
47k

82k

22k

13
11
& 12 IC6, IC8 = HEF4011BT
K2 IC7 = HEF4081BT
IC8.A IC9 = 74HC50
MOD2 1 ELEC_BOT 1
3
130508 - 2 2 EN_BOT 2 & IC7.A
1
3 3
IC8.B 2 & IC9.C
4 ELEC_RIGHT 5
4 IC7.B 7 6
EN_RIGHT 6 & 5 1
4
IC8.C
6 &
IC9.D
ELEC_CENTER_BR ELEC_REFB 8
10 9 10
EN_REFB 9 & 1

R12 R13 R14


C14
IC9.A IC9.E
* IC8.D
47k

82k

22k

OSC_SENSE1 2 3 11 12
1 1
13
11
& 12 IC9.F
OSC_SENSE2 4 5 14 15
1 1

IC9.B

+5V
SYNC_SCOPE
VCO_INH

+5V
TP4
C3
C6
R1
CPF_OUT
100n 10k
100n
TP5 16
14 R3 T1
TP7 VDD C1
VDD 12 3 13
Q1 CIN PC2
1M

SCPF_CLEAR
IC2 11 4 1
OSC_SENSE1 1 Q2 VCOUT PP 2n2
CLK 9 5 2
Q3 INH IC1 PC1 2N7002
6 14 6
Q4 SIGIN CX
74HC24 Q5
5
DEM
10 C2
ENOSC_SENSE 2
RST 4 15 +5V
Q6 ZEN
3 12 HEF4046 7 220p
Q7 R2 CX C7
VSS 11 BT 9
R1 VCOIN
7
VSS 100n
4
OSC_SENSE2
R4
120k
8
R7
TP8 VDD
Figure 3.
Full circuit diagram. Top
10k

R5 R2
IC3 1 DAC_CS
R6 SYNC
+5V
470k

left, the Arduino Uno board


18k

6 3 SPI_DATA
10k DOUT DIN
2 SPI_CLK
C5 C4
R8
DAC8311
SCLK
and below it, the electrode
plane. Everything else is
18k

GND
4u7 100n 5
10V
on the Arduino shield. The
130508 - 11 supply voltage comes from
the Arduino Uno board.

45
www.elektor-magazine.com | May 2014 | 11

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Figure 4.
The scanning of each
electrode generates a
sawtooth whose amplitude
is an indication of the
capacitance detection.

and widely available. Here, it’s not being used as


• a reference oscillator a PLL, but let’s see in the block diagram (Fig-
• a phase/frequency (P/F for short) ure 2) how the 4046’s voltage-controlled oscil-
comparator lator (VCO) and P/F comparator are used. The
• a control and locking program. latter compares the signal from the VCO, which is
going to be our reference oscillator, with the one
Have you already seen that somewhere before? from the electrode oscillator, whose frequency is
Yes, these elements, often used for phase-locked brought down by the prescaler into a range com-
loops (PLLs), are found all together in the 4046, a patible with that of the VCO, i.e. a few hundred
prodigious elderly integrated circuit, well known kHz. Proven over decades, this simple system
allows us to assess the frequency variations in
Figure 5. the oscillator formed by the system of electrodes
These three boards together against the VCO frequency. The conversion of
form the (touchless) gesture the (small) frequency shift into a variation in a
detection device using voltage signal will be easy to use later. The VCO
projected capacitance. This
frequency is adjusted by way of a digital/ana-
principle is the same as for
log converter (DAC) controlled by Arduino via
the ootsidebox.
the SPI port.

Now let’s see how the scanning sequence runs


for each of the electrodes:

• Initial situation: electrode oscillator at rest


(no EN_X signal active), VCO inhibited, no
oscillation. P/F comparator output is zero.
• A set-point value is applied to the VCO such
that its nominal frequency is close to that of
the electrode oscillator. This set-point stays
the same for the rest of the sequence.
• The two oscillators are unblocked and we
let the analog signal coming from the P/F
comparator change for around 300 µs (i.e.
around 30 cycles at 100 kHz) and the scan
is stopped so as to capture the analog value
by launching an acquisition on Arduino; then
the oscillators are blocked again.

The result of this scanning sequence (on one


electrode) at the output of the P/F comparator is

46
12 | May 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Touchless Gesture Control

an analog signal, a sort of sawtooth (Figure 4a), Circuit


whose exact shape and above all maximum ampli- Now you know all about how it works, here are a
tude are a direct function of the frequency dif- few interesting details about the circuit (Figure 3).
ference between the two oscillators. A similar If you change the geometry of the electrodes
sequence will be produced for each of the receiv- by even a tiny amount, or even the technology
ing electrodes, starting the electrode oscillator used to produce the PCB (the influence of stray
with the corresponding EN_X signal and applying capacitances is not negligible), you’ll certainly
to the VCO each time the set-point appropriate have to adjust the values of resistors R9–R14,
for this electrode (Figure 4b). Obviously, it’s the which let you adjust the electrode oscillator fre-
software that determines this set-point. quencies (IC6, IC7, IC8). If you reduce their
In the block diagram (figure 2), the signal called value, the frequency goes up: you need to get
“injection”, coming from the electrode oscillator as close as possible to 100 kHz. Capacitors C13
prior to prescaling, is sent to the VCO to per- and C14 are not fitted.
form what we call “injection locking” [4]: when
an oscillator injects a small amount of energy Buffers IC9A and IC9B (4050) adapt the voltage
into another, it tends to drive the second oscil- level from the oscillator, powered at 9 V, to that
lator when certain conditions are met (in par- of the downstream components, powered at 5 V.
ticular, their nominal frequencies must be fairly The counter IC2 (4024) acts as a prescaler for
close). The driving oscillator tends to impose its the OSC_SENSE1 signal and supplies a lower fre-
own frequency on the other oscillator. The prin- quency (SIGIN) to the P/F comparator IC1. Its
ciple also works on a harmonic, i.e. a multiple Q4 output gives a frequency divided by 16. The
of the fundamental frequency. For our 3D-Pad, signal from its Q3 output (SYNC_SCOPE) is sent
the effect of this is to influence the phase rela- to one input on Arduino. This counter can also
tionship between the two oscillators, and thereby (and will) be reset to zero by the (\ENOSC_SENSE)
the shape of the waveform at the P/F comparator signal from the Arduino microcontroller.
output. The advantage lies in terms of the signal- The VCO and P/F comparator functions are found
to-noise ratio and the robustness against EMC together in the same 4046 IC (IC1); their two
interference – this is crucial, given the extreme end frequencies are determined by R2, R5, and
sensitivity of our system. C2. The electrode oscillator frequency (prior to
So even though it is achieved using logic gates, prescaling) is injected by R4, as per the injection
my detector in fact delivers an analog signal.
Maybe I’m a bit old-fashioned, but seeing this
analog signal directly on the oscilloscope is for I’m not going to go into details about getting started with Arduino. If
me a decided advantage. you need to familiarize yourself with this versatile tool (as I did before
this project), I recommend the following books: Arduino by Günter
When you test this circuit for yourself, once you’ve Spanner and Mastering Microcontrollers with the Help of Arduino by
built it, here’s what one of the electrode signals Clemens Valens [5]. The latter saved me a great deal of time and now
will give: has pride of place within easy reach, just next to my soldering iron.
And not forgetting the other Elektor articles that have already been
• Start by holding your hand far enough away published on the subject.
from the 3D-Pad (at least 6 inches / 15 cm):
the software has stabilized the analog value
at the end of the sequence at 0.7 V.
• Bring your hand closer to the electrodes: the
sawtooth amplitude changes from 0.7 V (@
5 inches / 10 cm) to nearly 5 V @ 0.4 inches
/ 1 cm!

Our 3D-Pad comprises three boards (Figure 5):


the Arduino UNO (in version R3 or higher), the
main 3D-Pad shield board, and lastly the elec-
trode plane. Their different functions are clearly
indicated in the block diagram (Figure 2).

47
www.elektor-magazine.com | May 2014 | 13

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

R1, R3, and C2, with its rapid discharge achieved


by T1, itself driven by an Arduino output (SCPF_
CLEAR). On TP4, we have the usable analog value
(CPF_OUT), both for observing operation on an
oscilloscope and for the Arduino software, after
analog/digital conversion.
For the electrode oscillator, we need 9 V, stabi-
lized by a linear regulator (IC5), itself powered
from a DC voltage of at least 12 V. This passes via
the Arduino, which we’ll be powering from a small
12 V DC power supply (Arduino UNO has provision
Figure 6. locking principle mentioned above. The VCO’s set- for this). IC4 is a step-up level-changer (4504)
The three boards assembled. point voltage comes from IC3, a DAC8311 14-bit which allows the Arduino controller’s 5 V outputs
DAC, itself controlled by Arduino. The resistor net- to control the electrode selection, even though
work R6, R7, and R8 that the DAC output voltage the electrode oscillator is powered at 9 V. The
passes through before reaching the VCO set-point connection between our shield and the Arduino
input makes it possible to avoid the 4046’s loss UNO board is made via K3, K4, K5, and K6.
thresholds―i.e. a minimum voltage below which
the frequency hardly reduces any further, and Construction
Figure 7.
a maximum voltage above which the frequency As all the drawings for the UNO board are acces-
An extract from the code of
the _3Dpad_sensor sketch, does not increase any further, or hardly. sible online, it’s not beyond the bounds of pos-
with (on the right) the data The P/F comparator (IC1) sees at its CIN input sibility for you to build it yourself. But I suggest
sequences corresponding to the signal from the VCO and on its SIGIN input you’d do better to buy a ready-built and tested
the movements detected by the Q4 output from the prescaler. The analog UNO board [6]. The same goes for the two dou-
the four electrodes. voltage is additionally cleaned by the network ble-sided 3D-Pad boards – the track layouts are
available on the Elektor website, but I’d recom-
mend ordering them from the ElektorPCBservice
[7]. A few details deserve special attention, like
capacitors C5 and C12, which must be less than
6 mm high, otherwise you’ll have to fit them
lying down. You’ll need an iron suitable for sol-
dering SMD components, and you’ll have to take
particular care soldering IC3: the DAC8311 is so
small, you need a magnifying glass to spot the
pin 1 identifier.
The electrode plane connectors must be fitted on
the underside of the PCB, so that the screen-print-
ing on this board is on the top once it is plugged
onto the 3D-Pad shield board (Figure 6).
The case must be plastic, not metal. If you’re
lucky enough to own a 3D printer, or have a
Fab-Lab near you, you could have fun designing
an original, futuristic case for it. I used a FIBOX
ABS 125/35 LT case (RS ref. 498-4306) which
has a transparent lid.

Software
The software (sketch) to be downloaded into the
Arduino UNO consists of a file named _3Dpad_sen-
sor.ino and a library ElektorLabs3DPad, to be
installed into the Arduino IDE in the usual way.
This program sends the data to the terminal via

48
14 | May 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Touchless Gesture Control

the USB port, which is used in COM port mode right), rotating movements with turns counting
(fig. 7). The data sequence contains the four and detection of the rotation direction, and push-
electrode measurement values: ing a virtual button (Push).
And for testing, with the _3Dpad_test.ino file
>IN/OUT EL_Gauche EL_Droite loaded instead of _3Dpad_sensor.ino, we have
EL_Haut EL_Bas < commands that allow us to activate the oscilla-
tors continuously, by choosing the electrode to
IN/OUT indicates when the hand is perceived be used. This lets us check the frequencies and
as being (IN) the detection field or not (OUT). adjust the resistors R9–R14 if necessary. There
The program on the UNO board has two main is also a command to make the VCO work with
functions: on the one hand, the scanning and these set-points: 0, Max and ½ (i.e., at the DAC
sequential measurement of the electrodes, on the output, 0 = 0 V, ½ = 2.5 V and Max = 5 V).
other, the regulation, i.e. maintaining the operat- As a bonus, I am offering a very simple but fairly
ing point, taking the two reference electrodes into comprehensive application program, for PC under
account. The principle is the same as for Touch Windows (XP and 7): this displays the 3D co-or-
detectors, e.g. the ones from Atmel. The level is dinates in the form of a cursor whose position on
regulated outside the detection window, which the screen reflects X and Y, while the Z axis is
makes it possible to overcome slow variations represented by the diameter of the cursor; it also
(mainly caused by temperature changes); then displays the words “Air Swipes” when it detects
when the detection is active, this regulation is a sideways sweep of the hand along one of the
usually blocked. In our case, this implies princi- four axes, or the word “Push” when you make
pally that the VCO set-points for each electrode the movement of pushing a button (Z axis); and
measurement are continuously being corrected lastly, it indicates the rotation direction of the
[8]. I can’t go into a detailed description of the hand or finger it detects and the number of turns
software here – it would take a whole article at (very handy for carrying out settings).
least as long again as this one. However, here It will be easy for you to draw inspiration from
are the successive states of the 3D-Pad: this program in Visual Basic 6 for your own
applications.
Self-calibration: (when first brought into ser-
vice or on command via a serial link) the sys- Set-up
tem seeks the operating point for each electrode, Your Arduino UNO board is operational and you
then memorizes the set-points into EEPROM on have installed the software into the Arduino IDE.
the Arduino. You’ll need a voltmeter, an oscilloscope, and a
frequency meter (the latter is unnecessary if you
Setup: each time it is powered up, or on com- can measure frequencies with the ’scope). Once
mand via a serial link, the system quickly (less the components have been correctly soldered,
than one second) seeks the operating point, start- I recommend the usual checks: orientation of
ing from the set-points read from the EEPROM. the integrated circuits and polarized components,
There are also automatic configuration conditions, examination of the soldering using a magnifier
e.g. in the event of saturation of the electrodes. (especially for the DAC IC3).

Run: the normal operating state, which always The tension mounts: Plug together all the
follows on from a successful configuration. boards to form the stack of PCBs (Figure 6)
then plug the 12 V DC supply into the Arduino
The software’s other tasks are: UNO external power jack. It’s a good idea to
check the power rail voltages: 12 V on K3-1, 9 V
Interpolating the co-ordinates: from the mea- on TP1, and 5 V on TP2.
surement values of the top, bottom, left and
right electrodes, it calculates 3D co-ordinates: All OK? Then upload and run _3Dpad_test.ino.
X, Y, and Z. Open the connection with the terminal set to
115,200 baud; a menu of the commands avail-
Gesture recognition: it recognizes swipes in all able appears.
four directions (upwards, downwards, left, and Let’s check the oscillators are working:

49
www.elektor-magazine.com | May 2014 | 15

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

VCO: enter the command to activate the VCO via the serial link, the corresponding command
oscillator with a set-point ½: you should see (e.g. “T” = top electrode, or “B” = bottom one)
2.5 V on TP8 and a nice square wave on TP5 at and check the oscillation signal on TP6. The fre-
a frequency of 100–110 kHz (depending on com- quency should likewise be close to 100–110 kHz.
ponent tolerances). The other commands are documented in the soft-
ware source code.
Electrodes: make sure you clear everything
away from around the electrode plane. For each If these checks are satisfactory, load the normal
of the six electrodes, use the terminal to send, program _3Dpad_sensor.ino in place of the test

Component List
3D-Pad Arduino shield

Resistors
SMD 0805, 0.125 W)
r p c bs
R1, R6, R7 = 10kΩ to

er
.e l e k
R2, R8 = 18kΩ

v i c e.c
R3 = 1MΩ
R9,R12 = 47kΩ

ww
om
R4 = 120kΩ w
R5 = 470kΩ
R10,R13 = 82kΩ
R11,R14 = 22kΩ
R15,R16 = 470Ω

Capacitors
default: SMD 0805
C1 = 2.2nF
C2 = 220pF
C3,C4,C6,C7,C8,C9,C10,C11,C15,C16,C17,C18 = 100nF
C5 = 4.7µF 16V (pitch 2mm)
C12 = 100µF 16V (pitch 3.5mm)
C13, C14 = not fitted

Semiconductors
IC1 = HEF4046BT
IC2 = CD74HC4024M
IC3 = DAC8311 ou AD5641AKSZ
IC4 = CD4504BM
IC5 = 78L09 (SOT-89)
IC6, IC8 = HEF4011BT
IC7 = HEF4081BT
IC9 = CD74HC4050M
T1 = 2N7002

Miscellaneous
K5, K6 = 8-pin pinheader*
K3, K4 = 6-pin pinheader *
K1, K2 = 4-pin pinheader *
K7, K8 = 2-pin pinheader

Electrode Plane

Semiconductors
LED1,LED2 = LED, green, SMD, Kingbright type KPT-2012SGC

Miscellaneous
K1,K2 = 4-pin pinheader*
K3, K4 = 2-pin pinheader*
PCB # 130508-21

* 0.1’’ pitch

50
16 | May 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Touchless Gesture Control

Serial Inventor and Entrepreneur


Jean-Noël Lefebvre learnt electronics with project will shortly be launched on the
his soldering iron in his hand and through Indiegogo crowdfunding website.
reading magazines and specialist books You can participate in his project and
(including Elektor, naturally) The 3D-Pad help him. Follow @ootsidebox on
circuit described here is based on his own Twitter: twitter.com/Ootsidebox or post
patents. A “DIY” enthusiast, he fully supports a LIKE on Facebook: www.facebook.
the concept of HackerSpaces and Fab-Labs, in com/ootsidebox
association with the Makers movement.
en.wikipedia.org/wiki/Hackerspace
Jean-Noël has been devoting his time for a edutechwiki.unige.ch/en/Fab_lab
year now to OOTSIDEBOX, a start-up that is
en.wikipedia.org/wiki/Maker_culture
going to be offering devices like the 3D-PAD,
and also an accessory for Android tablets that www.ootsidebox.com
enables them to be controlled by touchless
gestures, identical to the 3D-Pad system. This www.indiegogo.com

program. A good way of checking the 3D-Pad in scrolling on the terminal [9]. You can launch a
operation consists in connecting a ’scope probe to reconfiguration at any time, either with the com-
TP8 (DAC output) and another to TP4. The sync mand “R” from the terminal, or by saturating the
is taken from TP8. At first switch-on, or follow- electrodes by bring your hand flat within a few
ing the self-calibration command (send “A” from millimeters of the electrode plane.
the terminal), the voltage level on TP8 will fall
gently: this is the search for the set-points for I’ll be there to help you if you need help getting
each electrode. After a few moments, this trace it going or information for a specific application,
should be stabilized (end of self-calibration) and or if you have any suggestions for developing the
your oscilloscope screen should look like the one project. Don’t hesitate to contact me on Twitter
shown in Figure 4b. Bring your hand closer to the [10], I’ll be delighted to answer you personally.
electrode plane: you should see the sawtooth on (130508)
TP4 change and also the measurement values

Web Links
[1] games
Fruit Ninja: http://fruitninja.com/
Despicable Me - Minion Rush: https://play.google.com/
[2] CC BY-NC-SA 4.0 http://creativecommons.org/licenses/by-nc-sa/4.0/
[3] www.embedded.com/design/prototyping-and-development/4008781/
Getting-in-touch-with-capacitance-sensor-algorithms
[4] injection locking: http://en.wikipedia.org/wiki/Injection_locking
[5] www.elektor.com/arduino
[6] assembled, tested UNO board from the Elektor e-shop
www.elektor.com/arduino
[7] www.elektorPCBservice.com
[8] www.rtcmagazine.com/articles/view/101626
[9] video of the sawtooth signal on TP4 http://youtu.be/rYdyR49qFzU
demo video: http://youtu.be/11QGUxXFYq8
[10] @junowhynot + #3DpadElektor: https://twitter.com/junowhynot

51
www.elektor-magazine.com | May 2014 | 17

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Microcontroller
BootCamp (1)
Arduino and Bascom

By Burkhard Kainka
(Germany)

In the Editorial Office we receive a fair number of


requests from electronics enthusiasts who are looking
for an easy way to get started with microcontrollers. It’s
been a good while since we last ran a large series of articles
on this subject in Elektor, and the associated hardware is vintage,
so it’s high time to run a new series. This series is aimed at our readers
who already have some experience with analog electronics and now want to start
using microcontrollers in their own circuits.

You might ask why you should use a microcon- For comparison: the NE555 timer IC
troller when it’s possible to do so much with First of all there’s the output. When you look
ordinary analog electronics. At first glance, this at the internal block diagram of the NE555 on
looks like a good question. New microcontrollers the data sheet (Figure 1), you can see that it
with more features, higher performance, higher has a push-pull output stage that can actively
clock rates and even more memory are appear- switch high and low. Microcontrollers have exactly
ing all the time, but the first demo program for the same kind of outputs. They are called ports,
every one of them invariably makes a LED blink. where the name “port” can stand for a set of
This leads to the justified criticism that you could outputs or for pins that can be configured either
get the same result by simply taking an NE555 as inputs or as outputs. The circuitry connected
timer IC and adding a couple of resistors and a to the output for a LED blinker application is also
capacitor. That’s absolutely right, and the com- the same: a LED with a series resistor, connected
parison is better than you might think because either to ground (GND) or to the supply voltage
a lot of the elements of an NE555 timer IC can (Vcc). The NE555 also has a second output driven
also be found in a microcontroller. by an open-collector transistor, which can only

52
30 | April 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

switch something to ground. Many microcontrol- the other hand, an analog electronics solution is
lers can also emulate this function. Actually the a better and more economical choice for quite a
only difference is that microcontrollers usually few simple tasks.
have several outputs but the NE555 has only one,
since the push-pull output and the open-collector Anyone with a bit of experience in microcon-
output are not independent. troller development can also mention another
advantage of microcontrollers: once the circuit
Next we have the inputs of the NE555, which is complete, you don’t need to touch the solder-
consist two inputs to a comparator that controls ing iron again. From that point on, all you do is
an internal flip-flop. A typical application for this write and test code. Changes to device functions
is an astable multivibrator, which hobbyists often can be implemented and tested very quickly.
call a blinker circuit. You can put all this together Microcontrollers are general-purpose and versatile
in almost no time. You just plug the numbers computation workhorses. The learning curve is
into a couple of formulas to determine the right worth the effort, since you ultimately save time.
component values, and then the NE555 does Your first exposure to a microcontroller data
exactly what you want. Determining the compo- sheet may put you off, since it can easily amount
nent values for an NE555 circuit and program- to 300 pages or more. Fortunately, there are
ming a microcontroller are actually comparable
tasks. There’s another thing that’s very similar:
both devices (NE555 and microcontroller) have
VCC
a Reset input that you can use to set everything
RESET
back to the starting point. And with both devices 4 8
VCC
the Reset input is usually high in the quiescent
state and must be actively pulled to ground.
5k

DIS-
THRESHOLD 6 INHIBIT/ 7
Figure 2 shows a simple square-wave genera- R
RESET CHARGE
CONTROL 5
tor in the form typically used as an LED blinker. VOLTAGE

The NE555 data sheet also shows several other Q


5k

basic circuits, including a monostable and a pulse- FLIP-


FLOP
TRIGGER 2
width modulator—all of which are typical tasks S
3 OUT
for microcontrollers. If you further consider the
countless NE555 applications you can find some-
NE555
5k

where on the Internet, you certainly have to


agree that in many cases all you need is a 555 1
GND
timer IC and a microcontroller is overkill. For Figure 1.
everything from light curtains to servo controls Block diagram of the NE555.
or processing analog sensor signals, there are
many things that can be done with this IC and
similar devices. And you can be sure that there
are still lots of potential applications that haven’t
been worked out yet.

Reducing development time 4 8


7 RES VCC
The similarities between the NE555 and a micro-
100k

DIS
controller are summarized in Table 1. You could
3
OUT
formulate the result of a fair comparison as fol- 9V 6 NE555
THR
lows: The microcontroller has a bit more of 2 TR
1k

CV GND
everything and is therefore generally the better
5 1
choice for complex tasks. For example, a single LED

microcontroller could probably handle a task that


22u
would take ten NE555s. Above a certain level of
Figure 2.
complexity, the microcontroller solution is also Blinker circuit with the
smaller and cheaper than the analog solution. On NE555

53
www.elektor-magazine.com | April 2014 | 31

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

you don’t entirely understand how it works. The


Table 1. Comparison of NE555 and microcontroller.
main thing is to have a couple of positive expe-
NE555 chip ATmega microcontroller
riences at the beginning, and after that it just
Switching output Port outputs
goes automatically. That’s doubtless the reason
Inputs Port inputs why the first demo task for every microcontroller
Timing control Internal timer is a LED blinker. Here as well we remain true to
by RC networks driven by crystal-controlled clock this tradition, if only to maintain the comparison
Reset input Reset input with the NE555.
Comparator inputs Comparator; analog inputs
Arduino and Bascom
PWM function PWM outputs
Microcontrollers actually come in all sorts and
Analog signal processing Analog to digital converter
sizes. At the start of a series such as this we are
Flip-flop Memory cells faced with the choice of which system to use,
and there are many different options. We spent
a long time talking about which microcontroller,
approaches to the world of microcontrollers that which circuit board (existing or new), and which
do not require you to understand everything right programming language we could specifically rec-
up front. In many programming languages the ommend for beginners. Our discussions led to
first steps are very easy. You just need to have the following proposal: hardware: Arduino Uno;
enough confidence to try something even when software: Bascom.

Arduino has become the most popular system


in the hobby environment. The programs are
developed on a PC using a simple programming
language, and they can be downloaded directly
to the microcontroller over a USB connection.
A large variety of boards and extension boards
(Arduino shields) are also available at amaz-
ingly low prices. The entire system is based on
the open-source concept, so the software and
the hardware are fully documented. The low-
cost Arduino Uno board [1] is a good choice for
Figure 3. our course because it is equipped with a widely
The Arduino Uno board. used microcontroller. The ATmega328 is an AVR
microcontroller made by Atmel. Programming this
device is quick and quite easy. The microcontrol-
Table 2. Arduino Uno at a glance.
ler has enough memory to allow relatively large
Microcontroller ATmega328 programs to be executed later on (see Table 2).
Supply voltage 5V There is a dedicated development environment
USB port 5 V supply and device programming available for the Arduino. A development envi-
External power supply 7–12 V ronment in this context, also called an integrated
development environment (IDE), is a PC pro-
Digital I/O pins 14 (of which 6 can be used for PWM output)
gram that is used to develop programs for a
PWM channels 6
microcontroller. In the development environment,
Analog inputs 6
the microcontroller programs are typed in using
Current per I/O pin 40 mA (max.) an editor and then converted into bytes by the
3.3-V output 50 mA (max.) compiler, after which they are downloaded to the
Flash memory 32 KB (with 0.5 KB occupied by the boot loader) microcontroller.
SRAM 2 KB (ATmega328)
To ensure that the compiler understands what
EEPROM 1 KB (ATmega328)
the microcontroller is supposed to do, you must
Clock speed 16 MHz
adhere to the syntax rules of a particular pro-
Price (for Elektor Members) $39.70 / £24.75 (check [1]) gramming language when you write the pro-

54
32 | April 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

gram. The Arduino IDE uses a simple version of


+5V
the C programming language, which is the lan-
guage used by most professional programmers.
It also has several special commands that make
program development easier. Many users have 100n

become familiar with this programming language 20 7 21


AVCC VCC AREF
and have no trouble working with it. Neverthe- 1
RES
less, for this course we chose the Basic program-
23 14
ming language. There are many reasons for this C0 B0
24 15
C1 B1
choice. One is the Bascom Basic compiler for 25 16
C2 B2
AVR microcontrollers, which is widely used and 26
C3 B3
17
27 18
popular. The learning curve is especially easy, in 28
C4 B4
19
C5 B5
part because Bascom includes many special com-
ATmega328p
mands for sending characters from a microcon- 2
D0 D7
13
3 12
troller to a PC, for showing letters and numbers D1 D6

1k
4 11
D2 D5
on a display, and much more. However, perhaps 5
D3 D4
6

the most important reason for using Bascom is GND X1 X2 GND


that it makes you fit for all AVR controllers. The 8 9 10 22
LED
selected Arduino board (Figure 3) is used here
as a learning platform, but in the end you can 16MHz

use any desired AVR microcontroller on other 22p 22p


Figure 4.
commercially available boards or on your own linker circuit with a
boards. You also don’t have to limit yourself to microcontroller.
ATmega devices. For example, you may be able
to manage with the compact ATtiny13, which a piece of prototyping board. This means that
has only eight pins. if you wish, you can follow the entire course
without the Arduino board. However, it’s more
A special feature of the Arduino board is the USB convenient and easier for beginners to use the
port. In addition to downloading programs to the Arduino Uno board.
microcontroller as described below, you can use Listing 1 shows the Bascom program for the LED
it to send characters back and forth between the blinker. It starts off with two directives for the
PC and the ATmega328. Among other things, compiler, which define what is called the envi-
you can use this to control the microcontroller
remotely from a PC program or to send mea-
surement values captured from sensors by the Listing 1. LED blinker
microcontroller to the PC and display them on '-----------------------------------
the PC. Another thing is that the board can be 'Uno_LED1.BAS
powered over USB if you so wish. All you need
is a USB cable, and you’re ready to go.
'-----------------------------------
$regfile = "m328pdef.dat" 'ATmega328p
Your first program
One option for putting together a blinker circuit $crystal = 16000000 '16 MHz
with an ATmega328 is shown in Figure 4. To '-----------------------------------
make it easier to see what matters here, the cir-
cuit diagram shows the microcontroller without Config Portb = Output
all the peripheral circuitry of the Arduino board.
The LED is already present on the Arduino board, Do
so you don’t have to put anything together. Portb.5 = 1 'LED on
Similar simplified circuit diagrams are also used Waitms 500 '500 ms
for the other example applications described later Portb.5 = 0 'LED off
on. The idea behind this is that you can also try
Waitms 500 '500 ms
out all of these examples using a bare micro-
Loop
controller, for example on a breadboard or on

55
www.elektor-magazine.com | April 2014 | 33

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

ronment. This is necessary because the Bascom Portb.5 = 1


compiler needs to know the target microcontroller Waitms 500
for compiling the program. The Arduino Uno is Portb.5 = 0
equipped with an ATmega328P, so the directive is: Waitms 500

$regfile = “m328pdef.dat” The individual line to the LED is switched to the


“high” voltage level (close to the supply volt-
You also have to tell the compiler what clock age of the microcontroller) by the instruction
speed the microcontroller runs at. The higher Portb.5 = 1. This causes a current to flow through
the clock speed, the faster the microcontroller the LED. The port pin is switched back to the
executes the instructions. This can be important “low” voltage level (close to the ground level) by
when dealing with things that require exact tim- the instruction Portb.5 = 0. There is also a wait
ing. An example is sending characters to the PC instruction to delay program execution. Waitms
at a particular data rate. The board has a 16-MHz 500 is self-explanatory; it causes a time delay
crystal that sets the clock speed of the controller. of 500 ms. All of this is built into a loop struc-
ture. Everything between “Do” and “Loop” will
be repeated indefinitely. The only way to stop
the program is to switch off the supply voltage
or press the Reset button.

Software: the compiler


So far, so good. But how is the program con-
verted into an executable form, and how do you
get it into the microcontroller? The Bascom Basic
compiler was developed by Mark Alberts for the
8051 family and for AVR microcontrollers. First
you have to get a copy of this PC software. It is
available from the website of MSC Electronics
[2]. You can opt for the paid full version or the
free demo version. The demo version is fully
adequate for trying out the software and for get-
ting starting with programming. It is limited to
programs that occupy up to 4 KB (4,096 bytes)
Figure 5. The corresponding directive for the compiler is: after compilation. By comparison, the Arduino
The first program in the has room for up to 32 KB. However, 4 KB is not
Bascom editor. $crystal = 16000000 peanuts; it takes a fair amount of programming
effort to fill it up. Most of the examples in this
Before you get to the actual program, there’s series will be much smaller.
another important configuration issue: the port Installing Bascom is very easy. After you launch
pins of the microcontroller can be used as inputs the program, the first thing you see is an empty
or as outputs. All port pins are initially config- Editor window where you can type in your own
ured as inputs after a restart. Here we need an program. Of course, you can also import an exist-
output, so the corresponding port must be con- ing program into the Editor (see Figure 5). These
figured accordingly: program files (with the suffix .bas) are plain text
files that can also be viewed with Windows Note-
Config Portb = Output pad or another editor program. This is called
“source code” because the compiler uses the con-
This instruction configures all six pins belonging tents of these text files as the source for compila-
to port B as outputs. The program actually only tion. The compiled program is called “hex code”
uses port pin PB5; all of the other pins remain because the bytes are often shown in hexadecimal
unused. Why did we choose PB5 in particular? notation, always with two hex characters in the
Because a yellow LED is already connected to range 0–9 and A–F per byte. Numbers in the form
this pin on the Arduino Uno board. of bits and bytes and the various notations used

56
34 | April 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

for them will be a frequent topic in this series on doesn’t work in practice, and likewise a micro-
microcontroller programming. controller with nothing in its program memory
cannot program itself. However, this is possible if
You can type in the program in Listing 1 yourself a boot loader is already present in memory, and
or download it from the Elektor page. The file the Arduino comes with a built-in boot loader.
UNO_LED1.bas is located in the zip folder [3]. The development environment on the PC also has
Compiling the program is very easy: simply click to be able to download program code using the
Program/Compile, click the corresponding icon Arduino boot loader. Fortunately, Bascom devel-
on the toolbar (a black IC), or press the F7 key. oper Mark Alberts already guessed that some-
If there is any sort of error in the source text, one would want to program an Arduino board in
an error message will be displayed. If there are Bascom at some point in time, so this capabil-
no problems, a pop-up window shows what per- ity is already incorporated. After you configure
centage of the memory is occupied. In this case the right settings, everything is quite easy. Here
it is less than 1%, which is rounded down to 0%. we describe how this works with the demo ver-
What matters is the resulting hex file UNO_LED1. sion, since there is a small difference with the
hex or the binary file UNO_LED1.bin, which are full version.
two different file formats with the same con-
tent. They contain the executable code for the
microcontroller. Now you have to load this code
into the microcontroller’s flash memory. There
are many ways to do this, and for now we only
describe the simplest way. Other options will be
described in subsequent instalments.

The simplest way: use the boot loader


This program must be located in the microcon-
troller’s flash ROM in order to run on the micro-
controller. Flash ROM is a special type of memory,
Figure 6.
similar to EEPROM, in which electrical charges
The settings for the Arduino
ensure that the memory contents are retained
boot loader.
reliably for many decades. Flash ROM can be
rewritten repeatedly (“flash” refers to very fast
writing), so programs stored in flash memory can First you have to install the original Arduino soft-
always be altered at a later date. Special pro- ware available from [4], which includes the USB
gramming devices are available for programming driver for the Arduino Uno board. Then you con-
flash memory. They are connected to specific pins nect the Arduino Uno over a USB cable. The driver
of the microcontroller, and the program bytes are is loaded automatically, after which the Arduino
received from the development environment on Uno should be visible in the Windows Device Man-
the PC via the USB link. ager window. There you can see which COM port
However, this can also be done without a pro- number (e.g. COM2 or COM3) has been assigned
gramming device. When the Arduino board has to the Arduino Uno. If you wish you can change
a USB connection to the PC as mentioned above, the COM port number in Device Manager, but this
the program bytes can be sent to the micro- is usually not necessary. However, you should
controller over the USB link as long as there is note or write down the COM number. If you wish,
a small program running in the microcontroller you can also open the Arduino IDE and try out a
that receives the data and writes it to the micro- couple of sample programs. However, here we
controller’s flash memory. want continue straightaway with Bascom.
This small program is called a boot loader, which
is related to the expression “booting up” for start- In Bascom you can choose from a large variety
ing up a computer. This term originates from the of programming devices and boot loaders under
word “bootstrap” in the saying “pull yourself up the menu item Options/Programmer. The right
by your bootstraps”. Of course, pulling yourself setting is “ARDUINO” (not “Arduino STK500/2”),
out of the mud by tugging on your bootstraps as shown in Figure 6. It’s also important to con-

57
www.elektor-magazine.com | April 2014 | 35

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

program is stuck. Incidentally, ESC also works


with the full version.
Now you’re done, and it’s time for action. As pre-
viously mentioned, press F7 to compile the source
code. Then press F4 to start the programmer.
Alternatively you can click the small green PCB
symbol “Program Chip”; the result is the same.
In any case, a new Programmer window opens.
There the compiled program (UNO_LED1.bin) is
already nicely loaded and displayed in the form
of hexadecimal numbers (Figure 7).

Good job: it works!


After this you can sit back and relax; the rest is
automatic. However, you can also do everything
yourself. If you opt for this, you must be very
careful because there is a function here that can
completely erase the microcontroller memory,
which means that the Arduino boot loader is also
gone. Stay well clear of anything with the word
“erase” in it. The only right option is “Chip/Write
Buffer into Chip”.
Now you will see a long chain of messages in
the programmer window, with the lovely word
“Started” at the end. During the programming
Figure 7. figure the right COM port (in this example COM2), process you can see from the activity of the Tx
The compiled program in and it’s essential to configure the right baud rate and Rx LEDs on the Uno board that a lot of data
the form of hex numbers. (115,200). This is because both parties must traffic is going on. At the end the window closes
agree on the data transmission rate in bits per again.
second (baud). We’ll come back to this subject
later on in the course when we talk about send- The downloaded program starts running imme-
ing messages and measurement data to the PC. diately after the end of programming, and the
If you only go by the Bascom help and the exam- yellow LED blinks. It may be a tiny program,
ples included with Bascom, some of your settings but it’s a big step for you as the programmer. If
will be wrong here because the Arduino Uno is you’re not quite sure about all this, try making
relatively new and the Arduino camp has only some small changes to the program. For example,
recently changed to the highest standard trans- you can change the blinking rate. For really fast
mission rate of 115,200 baud. All in the interest blinking, change Waitms 500 to Waitms 100, or
of fast data transfer and correspondingly super- for very slow blinking change it to Waitms 2000.
fast device programming. Time is scarce in our After editing the code, recompile it and repro-
fast-paced era. gram the microcontroller, and then check the
result. If the LED does exactly what you pro-
In Figure 6 you can see that the option “Auto grammed it to do, there’s no room for doubt: it
Flash” has also been ticked. This saves a mouse really works! In the next instalment we turn our
click later on, and it reduces the risk of doing attention to inputs.
something wrong. The “Terminal Emulator” option (120574-I)
is also very helpful if you want to have programs
Web Links
send messages and data to the PC later on. Once
the right settings have been selected, close the [1] www.elektor.com/arduino
window with ESC. That’s the previously mentioned [2] www.mcselec.com
difference between the demo version and the full [3] www.elektor-magazine.com/120574
version, which has an “OK” button. If you don’t
[4] http://arduino.cc/en/Main/Software
know about using the ESC key, it looks like the

58
36 | April 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Microcontroller
BootCamp (2)
Digital inputs
By Burkhard Kainka
(Germany)

When a microcontroller has to do more than just blindly follow a predefined pro-
cess, it needs additional information while the program is running. Inputs enable
microcontrollers to detect external events and respond accordingly.

Microcontrollers, including the ATmega328 on be used to measure voltages, and digital inputs,
the Arduino board, have many different types which can only detect whether a signal level is
of input. They include analog inputs, which can high or low. This can be used to read the state of
a button or switch, among other things.

Digital inputs
IN Each port pin of the ATmega328 can be configu-
red as an input or as an output, as mentioned in
+5V
LED the previous instalment of this series [1]. Here
100k

we want to use port pin PC5 as a digital input


1k

(see Figure 1). Incidentally, all pins of port C


28 27 26 25 24 23 22 21 20 19 18 17 16 15
can also be used as analog inputs for measuring
voltages. However, to do this you have to use spe-
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
GND
AREF
AVCC

cific instructions to configure the microcontroller


ATmega328p accordingly. The microcontroller is configured by
writing specific values to separate memory loca-
GND
VCC
RES
D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2

1 2 3 4 5 6 7 8 9 10 11 12 13 14 tions inside the device, which are called registers.


There are also program instructions to read the
16MHz
contents of the registers that hold the current
states of the microcontroller. We have more to
100n
22p 22p say about this later on.
130568-11
Figure 1. The developers of the Arduino board assumed
A digital input. that port pins PC0 to PC5 would be used as ana-

59
34 | May 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

log inputs, so the corresponding terminals on the diodes only start conducting at –0.6 V and +5.6 V
Uno board are labelled A0 to A5. Port pin PC5 is (assuming a supply voltage of 5 V).
connected to A5 at the edge of the board diago-
nally opposite the USB connector, which makes Reading input states
it easy to find. That’s actually why we chose this The program UNO_Input1.Bas in Listing 1
particular port pin for our first program. Figure 2 (the code can be downloaded from the Elektor
shows all the pins of the ATmega328 with their website [2]) reads the state of the signal on
official pin names (PC6, PD0, etc.), the special port pin PC5 and outputs it to the LED on port
functions of individual pins (which we will discuss pin PB5. First all pins of port C (PC0 to PC5)
in due course), and the abbreviated Arduino pin are initialized as digital inputs. In the interest of
names (at the outside edges). readability, the instruction Config Portc = Input
After a restart or reset, every pin of port C is is used for this purpose. Actually you could omit
configured as a high-impedance CMOS input with this instruction, since as previously mentioned
the same properties as the familiar 4000 family port C is automatically configured with all pins
of CMOS ICs. Accordingly, it’s not a bad idea to as inputs after power-up.
use 100 kΩ resistors here for protection against ATmega microcontrollers have output registers that
excessive voltages and static discharges. determine the states of the output port pins. When
you program the software to write a particular
Protection diodes value to an output register, the corresponding port
All modern CMOS devices have a pair of protection pins are set to 0 or 1 according to the content of
diodes on each input, with the one connected to the register. There is a separate input register that
ground and the other to Vcc. Their job is to limit holds the actual states of the pins. This register
excessive voltages. The first CMOS ICs in the
4000 family, which came on the market a long
time ago, did not have input protection diodes.
Premature IC failures due to improper handling ATmega328p
were therefore fairly common at that time. Static
RESET (PCINT14/RESET) PC6 1 28 PC5 (ADC5/SCL/PCINT13) A5
discharges from people to grounded objects at 0 (PCINT16/RXD) PD0 2 27 PC4 (ADC4/SDA/PCINT12) A4
voltage levels from 100 to 1000 V happen all the 1 (PCINT17/TXD) PD1 3 26 PC3 (ADC3/PCINT11) A3
time, but MOSFET gates don’t like them at all 2 (PCINT18/INT0) PD2 4 25 PC2 (ADC2/PCINT10) A2
and may break down at voltages as low as 50 V. 3 (PCINT19/OC2B/INT1) PD3 5 24 PC1 (ADC1/PCINT9) A1
Now that protection diodes are integrated in all 4 (PCINT20/XCK/T0) PD4 6 23 PC0 (ADC0/PCINT8) A0
5V VCC 7 22 GND GND
ICs, failure due to static discharge breakdown
GND GND 8 21 AREF AREF
has become rare. You can detect these protection
(PCINT6/XTAL1/TOSC1) PB6 9 20 AVCC 5V
diodes with an ordinary ohmmeter. This is often
(PCINT7/XTAL2/TOSC2) PB7 10 19 PB5 (SCK/PCINT5) 13
very useful because it is an easy way to check 5 (PCINT21/OC0B/T1) PD5 11 18 PB4 (MISO/PCINT4) 12
the connections to the pins of an IC in a circuit 6 (PCINT22/OC0A/AIN0) PD6 12 17 PB3 (MOSI/OC2A/PCINT3) 11
to see whether or not they are okay. 7 (PCINT23/AIN1) PD7 13 16 PB2 (SS/OC1B/PCINT2) 10
The protection diodes are what make it safe to 8 (PCINT0/CLKO/ICP1) PB0 14 15 PB1 (OC1A/PCINT1) 9
touch an open CMOS input with your finger through 130568-12
a 100 kΩ resistor, despite the fact that your body
may have static charges and carry induced AC
voltages up to 100 V under no-load conditions. Figure 2.
The human body is a sort of node with numerous The ATmega328 pinout and
capacitive links to all sorts of cables and power the corresponding Arduino
outlets. As audio designers and troubleshooters names.
know, a finger is an excellent source of a hum Rpu
signal. The protection diodes (Figure 3) limit the
Logic
high-amplitude sinusoidal signal to a low-amplitude PXN
Cpin
square wave (5 V peak to peak). You can see See Figure
'General Digital I/O'
this for yourself by measuring the signal with an for Details
oscilloscope. Actually the amplitude of the square Figure 3.
130568-13
wave is 6.2 V peak to peak, since the protection Input protection diodes.

60
www.elektor-magazine.com | May 2014 | 35

Personal Download for Petar Crnojevic | copyright Elektor


•Projects
Bits and Bytes
Each register in the AVR microcontroller holds eight bits, set to 1 remain in that state, but in the second case they are
or one byte. A bit can only have the value 1 or 0. A byte all set to 0.
(in a register or otherwise) consists of eight bits, so a byte
register can hold values from 0 to 255 in decimal notation. If To take another example, in Listing 1 you could replace the
you write the values in binary notation instead, you can see line Portb.5 = Pinc.5 with Portb = Pinc. If you only consider
the individual bit values directly. For example: 00000000, bit 5, you have the same circuit and the same result, but
11111111 or 100110010. there’s a big difference because now you’re moving eight
In many registers each bit is directly associated with a bits at a time instead of just one. As a result, any change on
specific pin. One example is the PORTD register. Bit 7 (at the input PC0 will affect output PB0.
left end) determines whether port pin PD7 is high or low. Along with binary notation (such as &B00100000), Bascom
Similarly, bit 0 (at the right end) determines the state of port supports two other commonly used notations. Instead
pin PD0. of &B00100000, you can write the value in hexadecimal
Many programming languages have instructions for setting notation, in which case the instruction takes the form Portb
or clearing individual bits in a register, which are accordingly =&H20. The other alternative is decimal notation: Portb =
called single-bit instructions. There are also instructions that 32.
can write a specific value to a register and therefore affect all
of the bits at the same time. The best way to understand how these different ways to
represent numbers work is to consider the example of a
To take an example from Bascom, Portb.5 =1 sets bit 5 of four-bit number. The smallest possible value is 0000 (all bits
the eight-bit register PORTB to 1, which means that the off), and the largest possible value is 1111 (all bits on). In
signal level on PB5 is high. None of the other bits is affected, mathematical terms, this is called a base-2 number system.
since this is a single-bit instruction. However, you can also Each bit has a specific weight, which increases from right to
access all bits of the PORTB register at the same time with left: 1, 2, 4, 8. Bit 0 has the weight 2^0 = 1, bit 1 the weight
the Bascom instruction Portb = &B00100000, where &B is 2^1 = 2, bit 2 the weight 2^1 = 4, and bit 3 the weight
the Bascom notation for a binary number. This has the same 2^3 = 8. As you can see, the value doubles with each bit
effect on bit 5 as the previous instruction: in both cases the position. You can obtain the corresponding decimal number
yellow LED on the Arduino board lights up. However, the by adding up the values of the individual bits. In hexadecimal
difference can certainly be significant for the other seven port notation, the numbers 10 to 15 are represented by the
pins. In the first case, any of these bits that were previously letters A to F.

can be read by the software to determine whether the state of a single port pin.
the pins are high or low. Each register holds one In the case of port B, the output register (write
byte (eight bits) with a value range from 0 to 255 register) is called PORTB and the input register
(see the Bits and Bytes inset). Each bit shows (read register) is called PINB. The software
sees these registers as memory locations that
can be read and written. However, in hardware
terms they are physical circuits with external
Listing 1. Copying an input to an output.
connections. There is another register for each
'-------------------------------- port called the Data Direction Register, which
'UNO_Input1.BAS allows the port pins to be configured as inputs
'------------------------------- or as outputs. For port B, this register is called
$regfile = "m328pdef.d 'ATmega328p DDRB. There is no obvious way to write data to
$crystal = 16000000 '16 MHz this register in a Bascom program, since this
operation is performed indirectly by the Config
instruction. For example, Config Portb = Output
'-------------------------------
sets all bits of DDRB to 1, which causes all pins
of port B to act as outputs.
Config Portb = Output
If you run the program and connect the input to
Config Portc = Input
ground, the LED will be off (dark). If you connect
the input to +5 V, the LED will light up. As you
Do can see, the input state is copied to the output.
Portb.5 = Pinc.5 'Copy Input to Output Now try something different: first make sure that
Waitms 19 '19 ms you are standing or sitting or standing completely
Loop insulated from any conductive objects, and then
touch the input with your finger. Remarkably

61
36 | May 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp
directly as a hexadecimal number. For example, the binary
8 4 2 1 Decimal Hexadecimal
number &B00100000 (0010 0000) is the same as &H20 in
0 0 0 0 0 0
hexadecimal notation.
0 0 0 1 1 1
0 0 1 0 2 2 To convert a hexadecimal number into a digital number, you
0 0 1 1 3 3 only need to know that the hexadecimal system is based on
0 1 0 0 4 4 16 as the name indicates (of course, in that regard it helps
0 1 0 1 5 5 if you know a bit of classical Greek and Latin). The weights
0 1 1 0 6 6 of the digits from right to left are therefore 1, 16, 256, 4096
0 1 1 1 7 7 and so on. For example, the number &H20 corresponds to
2 x 16 = 32.
1 0 0 0 8 8
1 0 0 1 9 9
If you often need to convert binary numbers into decimal
1 0 1 0 10 A
numbers, you should memorize the weights of the eight
1 0 1 1 11 B binary digits of a byte. Armed with that knowledge, all you
1 1 0 0 12 C have to do is to add up the individual bit values.
1 1 0 1 13 D
1 1 1 0 14 E Position 7 6 5 4 3 2 1 0
1 1 1 1 15 F Value 128 64 32 16 8 4 2 1

For comparison (and for those of you who have forgotten Now for a question: what is the largest number that can
your first-grade math): our usual number system with be represented by a byte? If you said ‘255’, you’re right.
base 10 comes from the more or less random biological Once you know this, the world of numbers is an open book
circumstance that we have a total of ten fingers and thumbs. for you and it is no longer a mystery why you can replace
The weights of the individual digits are 1. 10, 100, 1000 and the instruction Portb = Output in Bascom with the simple
so on. instruction Ddrb = 255. This says that all bits in the data
The eight bits of a byte can be divided into two sets of direction register for port B (DDRB) are set to 1 and all pins
four bits. Each set of four bits can then be expressed from PB0 to PB7 are outputs.

enough, you will see that the LED blinks. At first value where the pin is guaranteed to be read as
this may seem very strange, but when you think high is 0.7 Vcc (corresponding to 3.5 V) and the
about it the reason becomes clear: a stroboscope maximum value where the pin is guaranteed to
effect. Your finger couples a signal into the input – read as low is 0.3 Vcc (corresponding to 1.5 V).
the well-known 50-Hz AC hum signal with a period That sounds a bit like a disclaimer intended to
of 20 ms, or 16.6 ms for 60 Hz. By contrast, prevent unjustified complaints about supposedly
the wait time in the program is 19 ms. The 5% incorrect operation: if you connect a signal
difference between the two times yields an output between 1.5 and 3.5 V to an input, whatever
signal with a frequency of 2.5 Hz (50 Hz x 0.05). happens is your responsibility. But what actually
If you live in an area where the AC line frequency happens in that case? The only way to find out is
is 60 Hz, the output frequency—and thus the to simply do it and observe the results.
blinking rate—is correspondingly higher. Go ahead, try it! Use an external power supply for
this so that Vcc is exactly 5 V, since the voltage
What makes a high level high? available from a USB port is usually only 4.5 V or
Like all digital circuits, microcontroller output pins so. Connect a potentiometer as shown in Figure 4
have only two states, which are variously called and vary the input voltage over the range of 0
on and off, high and low, 1 and 0, or whatever. to 5 V. Here’s what you should measure with the
Furthermore, microcontrollers can only detect microcontroller: If you gradually raise the voltage
these two signal states on their input pins. from 0 V, the output state changes from low to
However, in practice any voltage from 0 V (ground) high at 2.7 V and the yellow LED lights up. If you
to the supply voltage (Vcc) can be applied to an then slowly reduce the voltage, the output state
input pin. You might think that anything above changes back to low at 2.2 V. You can repeat
2.5 V is a high level and anything below 2.5 V is this process as often as you like. The switching
a low level. However, the ATMega328 data sheet points are 0.5 V apart, and no change occurs in
states somewhat circumspectly that the minimum the range between 2.2 and 2.7 V. This means

62
www.elektor-magazine.com | May 2014 | 37

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

that there is a hysteresis of 0.5 V. The data sheet


+5V doesn’t actually say this, perhaps because nobody
at Atmel wants to claim that you can rely on this
LED property. However, it’s a useful property because
V

1k
10k it means that the inputs act like Schmitt triggers.
As you may know, the purpose of Schmitt triggers
28 27 26 25 24 23 22 21 20 19 18 17 16 15 is to convert analog signals with variable voltage
levels into digital signals.

C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
GND
AREF
AVCC
ATmega328p Switching back and forth

GND
VCC
RES
D0 You can also automate the above process and
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2
1 2 3 4 5 6 7 8 9 10 11 12 13 14 dispense with the potentiometer. You already
have the necessary hardware in the form of the
16MHz microcontroller, and the idea is to have it measure
100n
its own switching points. In the circuit in Figure 5,
22p 22p the capacitor connected to the input pin is charged
130568-14
Figure 4. by the output pin through a series resistor. The
Measuring the input voltage. output should go to 0 when a 1 is read at the input,
and it should go to 1 when a 0 is read at the input.
This circuit is effectively a sort of on/off controller
Figure 5. with hysteresis. You need to change the program
A control loop. slightly for this purpose, as shown in Listing 2.
Scope 10k...1M The Not function inverts a digital state, in the same
V way as an inverter gate in hardware logic. The
1k

100n...100u
LED wait time is not necessary because the program
+5V
should respond immediately when a new state
is detected. In this case, “immediately” means
within a microsecond or so.
28 27 26 25 24 23 22 21 20 19 18 17 16 15
The potentiometer of the previous circuit is
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
GND
AREF
AVCC

replaced here by an RC network. The component


ATmega328p values of this network (and the corresponding time
constant) can be chosen freely over a wide range.
GND
VCC
RES
D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2

1 2 3 4 5 6 7 8 9 10 11 12 13 14 For instance, you could use 100 nF and 10 kΩ if


you have an oscilloscope available. In that case
you can view the triangular waveform and see
16MHz
the hysteresis directly (Figure 6). If you use a
100n
Figure 6. 22p 22p
digital multimeter with high input impedance to
130568-15
Voltage waveform at the make your measurements, it’s better to use 100 µF
input. and 1 MΩ. In that case the voltage changes so
slowly that you can easily read the minimum and
maximum levels from the meter.
Actually you don’t need a measuring device for
this process, since you can use the analog inputs
of the Arduino board to measure the voltage. Any
voltage in the range of 0 to 5 V can be measured
digitally with a resolution of approximately 5 mV.
We’ll focus on how to do this in the next part
of this series.
Incidentally, if you want to examine the response
time of the program in more detail, you can simply
omit the RC network and connect pin PB5 directly
to pin PC5. If you then measure the signal with an
oscilloscope, you will see a rectangular waveform

63
38 | May 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

with a frequency of approximately 500 kHz. This An interesting aspect in this regard is that your
means that the circuit responds to changes in the finger acts like a high (logic 1) signal. This means
input state roughly once per microsecond. that if you touch the input pin when nothing else
There’s only one strange thing about this circuit: is connected to it, the LED will blink at a steady
with a symmetrical 500-kHz square-wave signal, rate. This results from the Wait instruction in the
the yellow LED on the Arduino board should be lit If block. When the program sees a 0 level on PC5,
at half its normal brightness, but it remains dark. it immediately jumps to End If and then back to
This reason for this can only be determined by the start of the loop. This means that a 0 level
examining the circuit diagram of the Arduino Uno causes the If condition to be tested repeatedly in
in more detail. The built-in LED on the Uno board rapid succession. If you apply a 50-Hz signal to the
is connected to PB5 through a buffer consisting input by touching it with your finger, after at most
of one half of an LM358 dual opamp. This is 10 ms a 1 level is detected at the input. Then the
unusual on a digital circuit board, and it comes
from the fact that the other half of the LM358 is
used as a comparator for the supply voltage. If Listing 2. Inverting the input signal.
you connect an external power supply, the Uno '--------------------------------
board automatically disconnects the USB supply 'UNO_Input2.BAS
voltage—very user-friendly and reliable. The other
'--------------------------------
opamp is redundant and actually shouldn’t be
$regfile = "m328pdef.dat" 'ATmega328p
used, but the designer took advantage of its high
$crystal = 16000000 '16 MHz
input impedance to use it as buffer that allows port
pin PB5 (Arduino pin 13) to also be used as an
input. However, a 500-kHz signal is simply outside '-------------------------------
the frequency range of an ordinary opamp, so
the LED on the board remains dark. If you want Config Portb = Output
to actually see something, you have to connect Config Portc = Input
your own LED to the board as shown in Figure 1.
Do
Branching Portb.5 = Not Pinc.5 'Inverted Input to Output
Microcontrollers can make decisions by following Loop
program branches. In practical terms, this means
that parts of a program are either executed or not
executed, depending on specific conditions. The
program structure used for this in Bascom is the If Listing 3. An If block.
block, which takes the form If <condition> Then '--------------------------------
<instructions> End If. The instructions inside the
'UNO_Input3.BAS
If block are executed if the condition is fulfilled,
'--------------------------------
and otherwise these instructions are not executed
$regfile = "m328pdef.dat" 'ATmega328p
and the program jumps directly to End If.
In the program in Listing 3 you can also see $crystal = 16000000 '16 MHz
another new instruction called Toggle, which '-------------------------------
means “switch to the opposite state” and
causes the output to change state each time
the instruction is executed. The blinker runs as Config Portb = Output
long as the signal level on port pin PC5 is logic 1, Config Portc = Input
which means 5 V or at least something higher
than 2.7 V. When the input pin is connected to Do
ground, which corresponds to logic 0, the LED If Pinc.5 = 1 Then
remains in its current state – either constantly
Toggle Portb.5
lit or constantly dark.
Waitms 250
The circuit is the same as in Figure 1. Here as well,
End If
you can test the circuit by connecting the input to
ground or +5 V, or by touching it with your finger. Loop

64
www.elektor-magazine.com | May 2014 | 39

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

case the LED will not blink – but you can’t say in
+5V advance whether or not the LED will blink. If you
hold your hand close to the input and move your
LED feet, the static charge on your body can cause
10k the port to change states as a result of capacitive

1k
coupling through the air. An outside observer who
doesn’t know all the details might start looking for
28 27 26 25 24 23 22 21 20 19 18 17 16 15
a pesky intermittent contact, and perhaps start to

C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
GND
AREF
AVCC
doubt the reliability of microcontrollers in general.
ATmega328p Many experienced designers have learned about
this the hard way by spending hours looking for a

GND
VCC
RES
D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2
1 2 3 4 5 6 7 8 9 10 11 12 13 14 suspected software bug or hardware error, when
the actual problem was an open input.
16MHz
Reading switch states
100n
22p 22p
with a pull-up resistor
130568-17
Figure 7. From the above, we can conclude that open inputs
A pull-up resistor. cause problems. Suppose you want to read the
state of a switch. This means that the input must
LED changes state and the program waits 250 ms have a defined state when the switch is open. The
before testing the If condition again. usual way to achieve this is to use a pull-up resistor,
This aspect of the program also shows you what which is a resistor connected to Vcc to pull the input
you shouldn’t do. Open inputs are bad news and high when it is open. If the microcontroller sees
cause nasty problems, especially if you overlook a low level at the input, it knows that the switch
them. In the case of this simple program, it’s connected to the input is closed.
totally unpredictable what will actually happen The pull-up resistor in Figure 7 is shown connected
when nothing is connected to the input. The input by dashed lines, which means that the resistor
may be at the high level, in which case the will is optional. This is because the microcontroller
LED blink, or it may be at a low level, in which has built-in pull-up resistors; all you have to do
is connect them. Many microcontrollers have a
separate register for this purpose. However, AVR
Listing 4. Polling a port with a pull-up resistor.
microcontrollers manage to handle everything
'-------------------------------- with a total of three registers: PORTC, PINC and
'UNO_Input4.BAS DDRC. In this case you set all bits of DDRC to
'-------------------------------- 0, which configures all pins of port C as inputs.
$regfile = "m328pdef.dat" 'ATmega328p You also set all bits of PORTC to 1, as though you
$crystal = 16000000 '16 MHz
wanted to set all the pins to high outputs. What
actually happens in this case is that each port pin
'-------------------------------
is connected to Vcc by an internal pull-up resistor
(marked “Rpu” in Figure 3) with a resistance of
Config Portb = Output
approximately 30 kΩ. This causes the input pins
Config Portc = Input to have a high signal level and a relatively low
Portc.5 = 1 'Pullup input impedance, instead of a high impedance. As
a result, all bits in PINB will be read as 1 unless
Do they the corresponding pin is connected to ground
If Pinc.5 = 1 Then by an external switch.
Toggle Portb.5 In Listing 4 you only need the instruction Portc.5
Waitms 250 = 1, which connects the internal pull-up resistor
Else to pin PC5. The other inputs of port C are left
Portb.5 = 0
in the high-impedance state without a pull-up
resistor. That doesn’t matter here because they
End If
are not used in the program. With this change,
Loop
the program response is unambiguous. An open

65
40 | May 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

input is always read as a high level (logic 1), and and 50 kΩ. To check this, connect an ammeter to
the LED blinks. Another change is necessary to the input pin instead of the switch, or in parallel
ensure that there is no ambiguity when the switch with the switch. In our case, we measured
is closed. This consists of adding an Else section 140 µA. This corresponds to a resistance of
to the If block. The instructions between Then and 35.7 kΩ (5 V ÷ 0.14 mA), which is exactly in
Else define what has to be done when the switch is the middle of the range specified by Atmel.
open, and the instructions between Else and End (130568-I)
If define what has to be done when the switch is
Web Links
closed. In this case, the LED should be off then.
By the way, you might want to measure the actual [1] www.elektor-magazine.com/120574
value of the internal pull-up resistor. The data [2] www.elektor-magazine.com/130568
sheet says that it is somewhere between 20 kΩ

Latch-up
You can use the input protection diodes of If your body has a static charge and you
the port pins intentionally in your circuits touch an IC input, the current pulse may
to limit input voltages higher than Vcc. To be large enough to trigger latch-up. Many
30k

take an RS232 interface as an example: modern ICs can withstand static discharges
the signal voltage on the output line of a IN up to 15 kV, based on a human body model
PC serial port is often –12 V and +12 V, with a contact resistance of 1 kΩ. In that
100n
or in some cases somewhat less. This is a case the ignition threshold is about 15 A,
complete mismatch to CMOS inputs with 5 V and you can certainly feel static discharges
signal levels. The quick and dirty solution of that magnitude. However, no IC can
is to connect the signal line directly to the survive contact with a 12 V power lead
30k

input through a protective series resistor lying loose on the bench, especially if the
(value 10 kΩ or 100 kΩ) as illustrated in IN 1u power supply has a hefty output capacitor.
Figure 1. Here the protection diodes take If the power lead touches an IC pin, the
100n
care of the rest. microcontroller is guaranteed to be dead.
However, there’s one thing you have to Have a look at the circuit diagram in the
watch out for: the current through the above figure. Do you see anything to be
protection diodes should never exceed a worried about? To all appearances, the
30k

few milliamperes. This is because every only thing the capacitor on the input does
10k
CMOS IC has a parasitic thyristor that can IN
is to debounce the switch contacts. This
be triggered unintentionally. It basically is common practice to ensure that the
100n
consists of an NPN transistor and a PNP microcontroller only sees a single level
transistor, which are a sort of undesirable 130568-18 change when the switch contacts bounce
side effect of the CMOS structure. This back and forth a few times. What the circuit
thyristor can be triggered by the current diagram doesn’t show is the length of the
through the protection diodes if it rises above a certain wires and their inductance. If you imagine an inductor in the
value, which might be 100 mA or as high as 1 A —but you circuit as shown in the middle diagram, you have something
never know the precise value. The worst thing about this is that looks a lot like Marconi’s spark-gap transmitter. When
that even very short current spikes can trigger the thyristor. the switch is closed, there is an excited resonant circuit that
After the device enters the latch-up state, what happens oscillates at 500 kHz, assuming a capacitance of 100 nF
next depends on how much current the power supply can and an inductance of 1 µH There’s also enough energy
deliver. The latched CMOS IC draws as much current as it available, since the capacitor has previously been charged
can and gets blistering hot. So if you get your fingers get through the pull-up resistor. The first peak of the oscillation
burned, switch off the power right away and wait a few waveform hits the protection diode with full force, and under
minutes. There’s still a small chance that the IC will have unfavorable conditions it can trigger that nasty thyristor.
survived, but in most cases it’s game over. If you measure The circuit diagram at the bottom shows how you can
the resistance between the Vcc and ground pins, you’ll only prevent this. All you need is a current limiting resistor that
read a few ohms. soaks up the excess energy.

66
www.elektor-magazine.com | May 2014 | 41

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Microcontroller
BootCamp (3)
Serial interface and A/D converter
This instalment focuses on the analog
to digital converter, which is effectively
a voltmeter built into the microcontrol-
ler. However, it does not have a pointer
or a display, so you have to do a bit
of work to be able to read the mea-
surements. The A/D converter simply
supplies data. In order to be displayed
somewhere, this data has to be trans-
mitted. That’s where the serial interface
comes into play.

By Burkhard Kainka Although most PCs nowadays have dispensed with Instead of this, the Arduino board has a serial
(Germany) the traditional serial interface, it is still widely to USB converter that sends the data over USB.
used in the microcontroller world. This interface This means that you need a driver for a virtual
was originally developed to transfer serial data serial port (such as COM2) on the PC. For pro-
over a conductor. The individual bits obediently grams running on the PC, that makes the data
travel down the wire one after the other. The bit transported over USB look like it entered the PC
timing is precisely defined so that the receiver through a conventional serial port. This data can
can make sense of the serial bit stream. A com- therefore be displayed using a standard terminal
monly used data rate is 9600 bits per second, emulator program.
which is also called 9600 baud. In addition to the We recommend that you use the terminal emu-
eight data bits of each byte, there is a start bit lator program integrated into Bascom. You can
and one or two stop bits. Each data bit is pres- open it under Tools > Terminal Emulator or with
ent on the wire for an interval of approximately the key combination Ctrl-T, but you have to con-
100 µs (at 9600 baud). figure the right settings to make it work prop-
erly. In particular this means selecting the right
Print output COM port (the same one you configured for the
Every ATmega microcontroller has a serial inter- boot loader) and setting the right baud rate (in
face (UART) with RXD (PD0) and TXD (PD1) lines. this case 9600). For the rest you can use the
These signals are TTL compatible, which means default settings: 8 data bits, 1 stop bit and no
that the signal level is 5 V in the quiescent state parity (Figure 1).
and 0 V in the active state. By contrast, a COM Now you have to persuade the Arduino Uno to
port on a PC operates with RS232 signal levels. transmit something. That’s easy in Bascom, thanks
They are -12 V in the quiescent state and +12 V to the Print command. See Listing 1 for an exam-
in the active state. For this reason, a periph- ple of how to use the Print command (note that all
eral interface IC such as the MAX232 is often code files can be downloaded at [1]). This com-
necessary to invert and adapt the signal levels. mand can be used to send output to a printer,

67
30 | June 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

which explains its name. However, to avoid wast- be a problem – namely when you have inadver-
ing paper it’s better to send text and data to the tently chosen a number type that is too small
monitor. The result is shown in Figure 2. and the overflow is not detected.
There are two Print commands in the program. There’s another detail that should be noted here:
The second one sends a message in quotation why does the display always go to a new line after
marks: “Uno”. But first a number is sent – more “Uno”, but not after the number? The answer is
particularly, the number N. If it’s been a while
since you had anything to do with math, you may
still have a vague memory that unknown quan-
tities in algebra are often designated as x. You
could do the same in Bascom, but in situations
where numbers are simply incremented (1, 2, 3
and so on), the symbols N, M, I and J are com-
monly used in source code. However, you are
free to choose your own symbols for variables
of this sort. The only thing that really matters is
that you first tell Bascom what type of number
each variable represents. This is because Bas-
com has to know how many bytes of memory the
Figure 1.
number needs and how computations should be Terminal emulator settings.
performed with the number in the code. For this
reason, the variables must be declared (dimen-
Listing 1. Print output
sioned) before they are used. That’s the purpose
of the following instruction: Dim N as Byte. This ‘------------------------------------
means that N is a number of type Byte, which ‘UNO_Print.BAS
clearly indicates that this number consists of eight ‘------------------------------------
bits (recall the previous instalment) and has a $regfile = “m328pdef.dat”
number range from 0 to 255.
$crystal =
$baud = 9600
Assignments
Now you can perform calculations with the num-
Dim N As Byte
ber variable N. The variable is assigned the value
0 at the start of program execution. Although
you might think this is only logical, it is actually Do
a particular feature of Basic. In other languages Print N;
you have to write ‘N = 0’, but in Bascom this Print “ Uno”
is done automatically. The value of N is subse- Waitms 200
quently incremented by 1 each time the loop is N = N + 1
executed. My old math teacher would have boxed Loop
my ears if I wrote ‘N = N + 1’, because it is not
valid mathematical equation. However, in many
programming languages the equal sign is used
as an assignment operator. The intention here
is that the variable N is assigned a new value by
adding 1 to the existing value.
You can see the results of this ongoing incre-
menting in the terminal window: the value of N
increases by 1 after each output. You can also
see something else: the value stops rising after it
reaches 255, since we defined N as a single-byte
number. This means that 255 + 1 is not 256, but Figure 2.
instead 0. This is called number overflow. Here Print output transmitted
this is not a problem, but in other places it can over a serial line.

68
www.elektor-magazine.com | June 2014 | 31

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

itor. After all, our original intention here was to


0...5V display measurements from the A/D converter,
A ref and now we’re ready to do so.
+5V The serial bits output by the Atmega328, which

10k
V are sent to the serial to USB converter on the
Uno board, can easily be seen with an oscillo-
scope. Simply touch the scope probe to the TX
pin of the microcontroller, which is routed to the
28 27 26 25 24 23 22 21 20 19 18 17 16 15
socket header at the top right on the Arduino

GND

AVCC
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
AREF
board. Then you can see the data stream. The
ATmega328p RX pin is next to the TX pin, and if you type some
characters on the terminal you can see them

GND
VCC
RES
D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2
on the RX line. This shows that the PC can also
1 2 3 4 5 6 7 8 9 10 11 12 13 14
send data to the microcontroller. At this point
the received data does not do anything because
16MHz
the program ignores it.

100n The A/D converter


22p 22p
Figure 3. 140028 - 13 The analog to digital converter (ADC) in the
Using the A/D converter. microcontroller is a sort of measuring device.
As we all know, measuring involves comparing.
simple: by default, Bascom sends the control First you need some sort of unit to serve as a
character CR (which stands for ‘carriage return’, reference quantity. Before you can measure a
like an old-fashioned typewriter) and LF (line distance in meters, you have to know how long
feed) at the end of each Print command. If this is a meter is. Likewise, you have to know how big
not what you want, you have to put a semicolon a volt is before you can say how many volts are
at the end of the instruction (Print N;). That’s lurking in your wall outlet. The situation here is
why the text is on the same line as the number. similar. The microcontroller needs a reference
A space is also inserted to separate the num- voltage so that it can compare the voltage on a
ber from the text. As you can see, it’s all very selected analog input (A0 to A5 on the Uno board)
simple and straightforward; you could use the to the reference voltage. The reference voltage
same approach to display ‘200 mV’ on the mon- is connected to the AREF pin. However, you can
also use a register to select the reference voltage.
For example, you could apply an external refer-
Listing 2. Using the A/D converter
ence voltage of 1 V or connect a 5 V reference
'---------------------------------------- voltage from inside the microcontroller, but of
'UNO_AD1.BAS ADC course you shouldn’t do both at the same time.
'---------------------------------------- Now try measuring the voltage between AREF
$regfile = "m328pdef.dat"
and GND (see Figure 3). Since the A/D con-
verter hasn’t been configured yet, the voltage is
$crystal = 16000000
zero. If you load the program in Listing 2 into
$baud = 9600
the microcontroller and make this measurement
again, you will see a voltage of 5 V. This is due
Dim D As Word to the following configuration statement:

Config Adc = Single , Prescaler = 64 , Reference = Avcc '5 V Config Adc = Single , Prescaler = 64 ,
Reference = Avcc
Do
D = Getadc(0) This initializes the ADC, which means it enables
Print D the ADC with specific attributes. Here Single mode
Waitms 200 means that only one measurement is made for
Loop
each request. The other option is Free (short
for free-running mode), in which measurements

69
32 | June 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

are made repeatedly without interruption. The


prescaler generates a clock signal for the A/D
converter by dividing the processor clock sig-
nal, which is 16 MHz on the Uno board. In this
case the A/D converter runs at 250 kHz (16 MHz
divided by 64). It can also run faster, but then it
is not quite as accurate. The setting ‘Reference
= Avcc’ connects the Aref pin to Avcc, which the
supply voltage of approximately 5 V. Incidentally,
it’s worthwhile taking a look at the data sheet for
the microcontroller – the section on the A/D con-
verter is practically a data sheet in its own right.
Figure 4.
If after that you still don’t have any idea of what
Measurement data from a
settings you can or should use, the Bascom Help 50 Hz signal.
is a good source of information. Simply point the
mouse to ‘Config’ and press the F1 key, and you
will be rewarded with all sorts of useful informa- far as latchup (as described in the previous part of
tion and a bit of sample source code. this series). However, here again a 10-kΩ resistor
The ‘instruction D = Getadc(0)’ initiates a mea- in series with the analog input can prevent serious
surement of the voltage on A0 and copies the problems. With that precaution in place, it’s even
result to the variable D. The A/D converter pro- okay to touch the input with your finger. If you do
vides readings with a resolution of 10 bits, which so, you will see varying readings in the terminal
corresponds to a number range of 0 to 1023. window (Figure 4), including many limit values (0
The variable D must therefore never be dimen- and 1023) because the hum voltage exceeds the
sioned as a byte variable. You should use either measuring range. The overall effect is similar to
the type Word (range 0 to 65535) or the type the waveform from a half-wave rectifier as seen on
Integer (range -32768 to +32767) to ensure that a oscilloscope. If you compare the measurement
the readings will fit. cycle time, consisting of the programmed wait
The measurements are made using a successive interval of 200 ms plus the actual measurement
approximation algorithm with ten steps. First the time, with the AC line voltage period of 20 ms (at
converter compares the input voltage to half the 50 Hz), you can see that here again there is a stro-
reference voltage. If it is higher than the reference boscope effect. This is called undersampling, and
voltage, the next comparison is to three-quarters it produces a low-frequency alias signal because
of the reference voltage. If it is still higher, the the measurement samples do not all lie within the
next comparison is seven-eighths, and so on. same period of the measured signal. In fact, there
The resolution doubles with each step. At the end are several periods of the input signal between
you have number that indicates which step on each pair of samples.
a ladder with 1024 steps between zero and the
reference voltage corresponds to the measured A bit of math
voltage. Each step is approximately 5 mV (5 V Our first simple measurement program only gen-
divided by 1023) if you use a reference voltage erates raw data, so you have to calculate the
of 5 V. For comparison, the resolution of a digital signal voltage yourself. Consider the following
voltmeter with a 3-½ digit display is roughly twice example: You connect analog input A0 to the
as good (2000 steps). This makes the microcon- 3.3 V output of the Arduino board. Now you see
troller a fairly good measuring device, although a reading of 676, or something close to that.
you shouldn’t confuse resolution with accuracy You grab your pocket calculator and calculate:
– the accuracy can be seriously compromised by 676 ÷ 1023 × 5 V = 3.305 V (okay). Another
an inaccurate reference voltage. option is to modify the program and have the
microcontroller do the math (Listing 3). For this
The analog inputs are subject to the same con- you need a variable that can hold more than just
siderations as the digital inputs: an input voltage integer values. You can use a variable U of type
well below zero or well above the supply voltage Single (which means a single-precision floating
can lead to undesirable side effects, extending as point / real number variable), which is fully suf-

70
www.elektor-magazine.com | June 2014 | 33

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

off readings of this sort, but for the time being


it’s nothing to worry about.
At this point you can see that it makes a dif-
ference whether you power the Uno board over
USB or from an external power supply. The sup-
ply voltage on the USB port can easily differ
from 5 V by 10% or more (see Figure 5), and
the accuracy of the measurement results will
vary accordingly. By contrast, the 5 V regulator
on the Uno board has a relatively narrow toler-
ance, typically around 1%. Try both options for
Figure 5.
Measuring the
yourself. Also measure the actual voltage on the
microcontroller’s own supply 3.3 V terminal and the voltage on the AREF pin
voltage. in each case. Armed with that information, you
can significantly improve the accuracy. Suppose
ficient. Now you can convert the raw data in two you measure a reference voltage of 5.03 V with
steps. You can only perform one calculation in an external power supply (using a high-precision
each instruction (that’s a Bascom rule). The long DVM). Enter this value in the program in place
chained equations you see in C or Pascal are not of the nominal value of 5.0 V, and your readings
possible here. will be nearly spot on.
You should also try other reference settings. If
U = D * 5.0 you configure ‘Reference = Aref’, at first you do
U = U / 1023 not have any reference voltage at all. You have
to provide your own reference voltage, with a
Now you can see the result in the terminal win- free choice anywhere in the range of 0 to 5 V.
dow. Of course, you should treat the large num- For example, you can connect the Aref pin to
ber of decimal places with caution, since they the 3.3 V terminal of the Uno board. In this case
give a false impression of the actual resolution. the measuring range extends to 3.3 V. Another
Later we will show you how to properly round option is ‘Reference = Internal’. In that case the
A/D converter uses an internal 1.1 V reference
voltage, and you can measure this voltage on the
Listing 3. Conversion to volts
Aref pin. The data sheet very modestly states a
'---------------------------------------- tolerance of approximately 10%, which means
'UNO_AD2.BAS 0...5 V 1.0 V to 1.2 V. In our case we measured 1.08 V,
'---------------------------------------- which is only 2% away from the nominal value.
$regfile = "m328pdef.dat" However, you should measure the actual value
yourself. There are two things worth noting about
$crystal = 16000000
this relatively low reference voltage. The first is
$baud = 9600
that the accuracy is independent of the supply
voltage; and the other is that it gives you a rel-
Dim D As Word
atively high resolution of approximately 1 mV.
Dim U As Single
Measuring the microcontroller’s own
Config Adc = Single , Prescaler = 64 , Reference = Avcc '5 V supply voltage
You might wonder whether the microcontroller
Do can measure its own supply voltage At first the
D = Getadc(0) answer appears to be no, since you would need
U = D * 5.0 a sufficiently large reference voltage that is inde-
U = U / 1023 pendent of the supply voltage. However, it turns
out that this is indeed possible because the data
Print U ; " V"
sheet reveals several interesting details about the
Waitms 200
A/D converter. The input multiplexer (an ana-
Loop
log switch similar to the well-known 4051) has

71
34 | June 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

External programmer
When you want to use a microcontroller, you usually need can always restore everything to the original state if you do
some sort of programming device. This is not necessary something really wrong, such as accidentally deleting the
with the Arduino because it boot loader.
has a built-in boot loader,
as described in the first part You can also use the
of this series. However, you programmer to read out the
do not have a boot loader content of the flash memory,
when you buy a new AVR for example in order to make
microcontroller and fit it on a backup copy (including the
your own PCB, so you have boot loader) that you can
to use a programmer. One use to restore the Arduino
low-cost option is the Atmel if necessary. A backup copy
ISP mkII. It can be used (UnoBoot.hex) [1] is also
with the free AVR Studio 6 available in the Elektor
development environment. However, there are lots of other archive in case you need it.
programmers that can do the same job. In order to load your own program into the microcontroller,
you first have to load the hex file. In this case you must
A six-pin ISP connector is normally tick the option ‘Erase chip before
used for in-system programming programming’ to ensure that the
(ISP) of AVR microcontrollers. boot loader is deleted. This means
Many microcontroller boards, you have to decide whether or not
including the Arduino, have a you want to use the boot loader.
suitable 6-pin header for this. The You can also opt to use another
SPI interface, which consists of boot loader, such as the MCS boot
serial data streams (MOSI to the loader. We’ll describe how that
microcontroller and MISO back to works in one of the upcoming
the programmer) and a clock signal instalments.
(SCK), is often used to transmit the
programming data. This interface You can also view the
will be described in more detail in a microcontroller fuse settings with
later instalment. The pinout of the Bascom or in Atmel Studio 6.
ATmega328 is: By the way, the term ‘fuse’
comes from the early days of
1 MISO, PB4 microcontroller technology when
2 Vcc there was program memory in
3 SCK, PB5 which links were literally burnt
4 MOSI, PB3 through to program the memory
5 Reset once and for all. The modern
6 GND fuses in ATmega microcontrollers
are actually flash memory cells
The Arduino Uno board has two ISP that must be configured to define
ports for external programmers. specific basic settings. Among other
The one close to the USB connector things, they allow you to switch
is best ignored, since it is used to back and forth between the internal
program the USB to serial converter clock and an external clock source.
described in the body of this article. The screenshot shows the factory
The ISP port for the ATmega328 is default fuse settings of the Arduino
located at the edge of the board. Uno board. You can see that the
It’s nice to know that it’s possible boot loader is enabled (BOOTRST)
to connect an external programmer, because it means you and how much memory is reserved for it.

72
www.elektor-magazine.com | June 2014 | 35

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

reference voltage. The trick here is to use the


imprecise supply voltage as the reference volt-
age and measure the precise internal reference

220R
+5V voltage. In this case the program must calculate
in the opposite direction to determine the actual
supply voltage (see Listing 4). The first mea-
surement (Figure 5) shows the supply voltage
28 27 26 25 24 23 22 21 20 19 18 17 16 15 with USB power, which in this case is about 4.5 V.
Then an external power supply is connected while

GND

AVCC
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
AREF
the program is running, so the supply voltage is
ATmega328p provided by the distinctly more precise 5 V volt-
age regulator. The corresponding measurement

GND
VCC
RES
D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2
is accordingly close to 5.0 V.
1 2 3 4 5 6 7 8 9 10 11 12 13 14

Measuring the temperature


16MHz In addition to measuring its own supply voltage,
the ATmega328 can measure its own tempera-
100n
Figure 6. ture thanks to an internal temperature sensor
22p 22p
Temperature measurement 140028 - 16 connected to channel 8 of the A/D converter. The
under load. output voltage of this sensor is proportional to
the temperature, with a factor of approximately
a total of eight channels, of which six are con- 1 mV per degree. The accuracy is not especially
nected to pins A0 to A5. The other two are only high – the specified tolerance is ten degrees.
fed out in the SMD version of the ATmega328. However, you can always calibrate it yourself.
However, there are also several ‘hidden’ internal According to the data sheet, the sensor output is
channels, and one of these (channel 14) allows 242 mV at –45 °C, 314 mV at 25 °C and 380 mV
the microcontroller to measure its internal 1.1 V at 85 °C. To obtain meaningful readings with volt-
ages in this range, you have to use the relatively
low internal reference voltage (1.1 V). However,
the same program is supposed to measure higher
Listing 4. Measuring VCC.
voltages as well, so it automatically switches to
‘---------------------------------------- the higher reference voltage (Avcc) as necessary.
‘UNO_AD3.BAS Vcc / 1.1 V For internal temperature measurement the A/D
‘---------------------------------------- converter operates with the internal 1.1 V ref-
$regfile = “m328pdef.dat” erence voltage and a resolution of about 1 mV,
$crystal = 16000000 which roughly corresponds to 1 degree at the
$baud = 9600 temperature sensor output. At 25 degrees C
the sensor output is approximately 314 mV.
We decided to take a quick-and-dirty empirical
Dim D As Word
approach, and we determined that the tempera-
Dim U As Single
ture in degrees C could be found by subtracting
338 from the measured value (see Listing 5).
Config Adc = Single , Prescaler = 64 , Reference = Avcc However, even better results could be obtained
with a bit more computation effort. In any case,
Do you should adjust the results according to your
D = Getadc(14) ‘Ref 1.1 V actual situation to obtain the best possible match
U = 1023 / D with the temperature shown by an ordinary ther-
U = U * 1.1 mometer. Next we held a finger on the micro-
Print “Vcc = “; controller to see whether the temperature rose.
Print U ; “ V” Then we wanted to see whether the tempera-
Waitms 1000
ture of the microcontroller increases when it is
driving a load. Figure 6 shows a 220 Ω resistor
Loop
connected between two port pins. If one output

73
36 | June 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

is set high and the other is set low, the voltage


on the load resistor is close to 5 V. This results
in a load current of roughly 20 mA. We wanted
to see whether this causes the microcontroller to
warm up. The program also measures the volt-
age drops on the port pins. For this purpose, the
reference voltage must be briefly switched to 5 V.
Although it is somewhat unusual for a program
to work with two different reference voltages,
switching voltages while the program was run-
ning does not cause any problems.
The results: with an output current of 20 mA, the Figure 7.
voltage drops are just 0.4 V at the lower output Temperatures and voltage
and 0.5 V at the upper output. This leaves 4.1 V drop

Listing 5. Temperature and voltage drops

‘-------------------------------------------
‘UNO_AD4.BAS Temp
‘-------------------------------------------
$regfile = “m328pdef.dat”
$crystal = 16000000
$baud = 9600

Dim D As Word
Dim N As Word
Dim U As Single

Config Portb = Output


Portb.5 = 1
Portb.4 = 0

Do
Config Adc = Single , Prescaler = Auto , Reference = Internal ‘1,1 V
Waitms 200
D = Getadc(8) ‘Temperature
D = D - 338
Print D ; “ deg”
Waitms 500
Config Adc = Single , Prescaler = Auto , Reference = Avcc ‘5 V
Waitms 200
D = Getadc(0)
U = D * 5.0
U = U / 1023
Print U ; “ V”
D = Getadc(1)
U = D * 5.0
U = U / 1023
Print U ; “ V”
Loop

74
www.elektor-magazine.com | June 2014 | 37

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

across the load resistor, yielding a current of the total current should not exceed 200 mA. In
19 mA. The additional power dissipation in the our experiments we found that the ports could
microcontroller is 17 mW (0.9 V x 19 mA). Sig- handle currents up to 100 mA without damage,
nificant warming cannot be expected from this which means that even small DC motors could be
amount of power, and that’s exactly what we saw operated directly from the ports without driver
from the temperature measurement (Figure 7). ICs. However, if you want to be on the safe side
According to the data sheet, the maximum cur- the rule is to never exceed 40 mA.
rent at any port pin should not exceed 40 mA and

Listing 6. Measuring the input hysteresis 100k

‘---------------------------------------------------

1k
‘UNO_AD5.BAS Hi/Lo Input Threshold +5V 100u
LED
‘---------------------------------------------------
$regfile = “m328pdef.dat”
$crystal = 16000000
$baud = 9600 28 27 26 25 24 23 22 21 20 19 18 17 16 15

GND

AVCC
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
AREF
Dim D As Word
ATmega328p
Dim Dmin As Word

GND
VCC
RES
Dim Dmax As Word

D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2
Dim N As Word 1 2 3 4 5 6 7 8 9 10 11 12 13 14

Dim U As Single
Config Portb = Output
16MHz
Config Adc = Single , Prescaler = 64 , Reference = Avcc ‘5 V
100n
22p 22p
For N = 1 To 10000 140028 - 18

Portb.5 = Not Pinc.5


Next N Figure 8. Measuring the input hysteresis.

Dmin = 1023
Dmax = 0

Do
For N = 1 To 10000
Portb.5 = Not Pinc.5 ‘13 100k A5
D = Getadc(5) ‘A5 100µF GND
If D < Dmin Then Dmin = D
If D > Dmax Then Dmax = D
Next N
U = Dmin * 5.0
U = U / 1023
Print “Min = “;
Print U , “ V”
U = Dmax * 5.0
U = U / 1023
Print “Max = “;
Print U , “ V”
Loop Figure 9. The upper and lower switching thresholds of an
input.

75
38 | June 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Advertisement
Addressable RGB 30-LED Strip,
Measuring the input hysteresis
5 V, 1 m (WS2812B)
In the previous instalment of this series we used external
ITEM #2546

1695
test equipment to determine the switching thresholds of a
digital input. Now we want to the same thing entirely auto-
$
matically with the built-in A/D converter (see Figure 8).
Waterproof, individually addressable LED strip that runs on 5 V. Can be
For this we use two new variables (Dmin and Dmax) to hold chained to form longer strips or cut for shorter sections. Other lengths
the values of the lower and upper switching thresholds (see and LED densities available.
Listing 6). The measurement loop is preceded by a control
loop which ensures that the input voltage is already within 37D mm Metal Step-Up/Step-Down
the desired range before the actual measurement starts.
Gearmotors Voltage Regulator
At first the maximum possible value is stored in the Dmin
variable and zero is stored in the Dmax variable. The pro-
$
2495 S18V20ALV
ITEM #2572

gram then looks for the actual limit values. This is done
using a random-sample approach. The longer the mea-
$
1595
Other sizes available
surement session lasts, the more accurate the determined
•• 3Adjustable
V to 30 V input
limit values are.
This program shows how to use loop counters. The For-Next
•• Several gear ratios stocked
Versions with integrated
4–12 V output can be
above or below input voltage
loop counts down from N = 1000 to 0 and executes the encoders also available • 2 A typical max output current
instructions inside the loop exactly 1000 times. Although one A-Star 32U4 Micro
thousand iterations may sound like a lot, the entire process ITEM #3101

1275
takes only a fraction of a second. The large number of mea-
surements increases the probability that the measurement
$
results include the true limit values. This means that you have
a good chance of finding the correct values after just one Smallest
ATmega32U4
round. This can be seen from the fact that the subsequent board
rounds do not yield any significant changes.
•• 1’’ATmega32U4
× 0.6’’ programmable module with native USB
with Arduino-compatible bootloader
For N = 1 To 1000
… instructions … Mini Maestro 12-Channel Sub-Micro
Next N USB Servo Controller Servo
ITEM #1352 ITEM #1053

2995 495
Figure 9 shows the result of this experiment. The switching
$ $
thresholds are 2.23 V and 2.62 V. These are approximately
the same as the values determined using the external test
equipment. Other
(130568-I)
• USB, serial, and internal scripting • 3.7 g
servos


available
control Specs at 6 V:
Web Link
• 6-,also18-,available
and 24-channel versions •• 60.07oz·insec/60°
[1] www.elektor-magazine.com/130568

Zumo Robot for Arduino


(Assembled with 75:1 HP Motors)
ITEM #2506

99
Get a little pushy!
$ 95
Arduino-controllable tracked robot small enough for mini-sumo (less
than 10 cm × 10 cm) and flexible enough for you to make it your own.
Individual parts and kit version also available — build your own
configuration!

Finding the right parts for your design can be difficult, but
you also don’t want to spend all your time reinventing the
wheel (or motor controller). That’s where we come in:
Pololu has the unique products — from actuators to
wireless modules — that can help you take your design
from idea to reality.
Find out more at: www.pololu.com
76
www.elektor-magazine.com | June 2014 | 39

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Microcontroller
BootCamp (4)
User interfaces

By Burkhard Kainka Serious microcontroller applications usually have some sort of interface between
(Germany)
humans and the machine. You can do a lot with a just a small display, a few but-
tons, a potentiometer and a couple of LEDs. What’s more, you can hit the ground
running with the Arduino shield developed by Elektor, which is described elsewhere
in this edition.

First let’s see what it takes to drive a display. Arduino board. You can also see the other periph-
Various types are available, including graphic and eral components there: two LEDs, two pushbut-
text displays. Text displays range from tiny with tons and a potentiometer. If you wish, you can
a single line of 8 characters, to large with four build all this yourself on a piece of prototyping
lines of 20 characters. As the saying goes, small board. You don’t even have to use exactly the
is beautiful, and in many cases you don’t have to same type of display module. One with two lines
display a lot of characters. That’s why the new of 16 characters would work just as well. If you
Elektor shield has a small two-line text display like to keep things simple, you can order the new
with eight characters per line. In any case, that’s shield on the web page for this article [1], where
enough room for messages such as “V=3.3V” as usual you can also download a file containing
or “I=8.2mA”. What more do you need on your the code for the programs described here.
electronics bench? The display occupies six pins on port D: D2 to
D7. That’s handy, because it leaves exactly two
LCD connection spare for the serial interface: D0 (RXD) and D1
Figure 1 shows how the display module on the (TXD). Ports B and C remain free for whatever
shield is connected to the ATmega328 on the strikes your fancy. All standard display modules

77
58 | July & August 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

of this sort can optionally be operated in 8-bit is designed for two lines of 16 characters (16 *
mode, which means that the data is sent to the 2), even with this small display. That’s not a
display over eight lines in parallel. However, 4-bit problem in practice because the program keeps
mode has become customary to reduce the num- on running without an error if you accidentally
ber of port pins used on the microcontroller. In write up to 16 characters in a line. However, when
this mode each data byte is sent to the display you see the truncated output on the display you
in two steps. For example, if you want to write will have to consider how you can shave a few
an upper-case A you have to send the hex value more characters off the message.
&H41 (binary &B01000001, or 65 in decimal nota-
tion), as specified in the ASCII code table. In fact After you initialize the display, you should clear
you first send &B0001 and then &B0100. How- everything with the Cls (Clear Screen) command.
ever, you don’t actually need to know all these Everything written after this lands on the first
details or how to go about initializing the display, line, starting at the left end. Here it is the word
since Bascom does all the hard work for you. If “Elektor” – seven characters, short and sweet.
you simply write Lcd “A” in your program, the If you send another character to the LCD now, it
letter A will appear on the display. will be written to position 8 on the first line, but
Our first example program (Listing 1) shows how what you actually want is to start with the sec-
it all works. First you need a Config instruc- ond line. For this you use the Locate command.
tion to tell the compiler how the display pins Here Locate 2 , 1 causes the next character
are connected to the port pins. Next you have to be written to the leftmost position of the sec-
to initialize the display with the Config Lcd = ond line. The program outputs an incrementing
16 * 2 instruction. You can choose from several number at this position. The count variable N is
formats here. The format 8 * 2 is not supported incremented once per second, so you can use
because the display controller in the LCD module the program to measure time. For example, it’s

Listing 1: Text and number output.


LED1 LED2
'------------------------------------
'UNO_LCD1.BAS Text Output S2 S1
1k

1k

'------------------------------------
$regfile = "m328pdef.dat" +5V
10k
'ATmega328p
$crystal = 16000000 '16 PWMB PWMA

MHz 28 27 26 25 24 23 22 21 20 19 18 17 16 15
$baud = 9600
GND

AVCC
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
AREF

ATmega328p
Dim N As Word
GND
VCC
RES
D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2

1 2 3 4 5 6 7 8 9 10 11 12 13 14
Config Lcdpin = Pin , Db4 = Portd.4 ,
Db5 = Portd.5 , Db6 = Portd.6 , Db7 =
Portd.7 , E = Portd.3 , Rs = Portd.2
16MHz
100n
Config Lcd = 16 * 2

Cls 22p 22p


10k
Lcd "Elektor"
Contrast
'Cursor Off
Do 1 2 3 4 5 6 7 8 9 10 11 12 13 14

Locate 2 , 1
D0
D1
D2
D3
D4
D5
D6
D7
GND

R/W

Figure 1.
RS

E
VEE
VCC

Lcd N Basic diagram: how the


LCD
N = N + 1 LEDs, buttons and display
Waitms 1000 on the Elektor shield are
140064 - 11 connected to the ATmega328
Loop
on the Arduino Uno board.

78
www.elektor-magazine.com | July & August 2014 | 59

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

taken me 1200 seconds to write these lines since on its own what has to be done, which is very
I started the program. That’s 20 minutes, which convenient for the user. In other languages the
means I’m pretty slow today. programmer has to do more in these situations.
On the display you will see an underscore after
There are two Lcd instructions in this example the number that was output, which represents
program, and it’s important to understand that a cursor. The cursor shows where the next char-
they do two completely different things. The pure acter will be written if and when it comes. This
text output instruction simply copies the charac- may be very helpful when you’re busy typing
ters set in quotation marks by the programmer. something in, but in our case the cursor is irri-
By contrast, the instruction Lcd N converts the tating. Fortunately, we can do something about
numerical value in the variable N into text and this with the Cursor Off command, which is ini-
then sends this text to the display. In this case tially commented out in the code. If you delete
N is an integer, but in other cases it could be a the comment character, recompile the program
real number with decimal places. Bascom decides and download it to the microcontroller, you will

Liquid Crystal Displays


Liquid crystal displays (LCDs) are very popular because There are usually 14 lines, and in some cases two more for
they are easy to read and don’t need much power. They the backlight. The display on the Elektor shield need only 14
can be operated without a backlight, although the backlight lines because the backlight is hardwired.
on the Elektor shield is always on. This still results in much About the individual lines: GND and Vcc are obviously
less power consumption than an LED display with the same ground and +5 V. Vee is connected
number of characters. to a contrast trimpot. With many
LCD modules the optimal setting
The reason LCDs are is approximately 4.5 V between
so energy efficient is Vee and Vcc. It is therefore often
that they do not have sufficient to connect a fixed resistor
to generate light. with a value of 470 Ω to 1 kΩ
Instead, they control between Vee and ground, which
whether ambient light is saves the cost of a trimpot.
transmitted or blocked.
The liquid crystal material, RS is an input that allows the
which is located between display be set to receive either
two sheets of glass, rotates data commands (RS = 1) or
the polarization plane of control commands (RS = 0). Data is necessary
the incident light depending to display text, while control commands are necessary
on the applied voltage. A for initialization and positioning the cursor. R/W switches
polarization film is always located on one of the glass between reading and writing. Reading is actually only
sheets. (Incidentally, if you have a defective LCD module necessary to determine whether the display is ready to
you should sometime pull off this film, because you can use receive the next data. This can also be ensured by a short
it to perform interesting experiments with light [2][3].) The wait time, so the read direction is often not used and R/W is
display element of an LCD module is driven by square-wave tied to ground. E is the Enable input. It is used to indicate to
voltages with no DC component, which are applied across the display controller that valid data is present on the data
the individual segments. There are dedicated CMOS ICs for bus (lines D0 to D7) and should be read in by the controller.
this purpose, but some microcontrollers can also drive LCDs The controller always reads in the current data after a
directly. However, standard LCD modules have special built- falling edge. In 8-bit mode all eight data bits are put on the
in controllers that handle the actual drive tasks. bus and then a falling edge is generated on the E input. In
4-bit mode this process occurs twice, with only the upper
The great-grandfather of all LCD controllers was the four data lines (D4 to D7) being used for data transfer. The
HD44780. Even today, most controllers are HD44780 lower nibble (least significant bits) is sent first, followed by
compatible. This involves several standardized control the upper nibble. The display must be initialized to operate
commands as well as the connections to the display module. in either 4-bit mode or 8-bit mode before it is used.

79
60 | July & August 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

see that the cursor has vanished. Measuring brightness


This is a good place to remind you how easy it is Now let’s edit the program so that the ADC2
to display more information by using the Bascom channel is displayed instead of ADC0 (see List-
help function. Simply move the cursor (here we ing 3). On the shield board, LED1 is connected to
mean the one on your PC monitor) to the key- this channel through a jumper and a 1 kΩ series
word concerned and press the F1 key, and you’re resistor, since this port pin can also be configured
already a lot wiser. For instance, you can learn as an output. However, in this case we leave it
how to make the cursor blink. in the high-impedance state. Now you can see

A two-channel voltmeter
Happen to need a two-channel voltmeter? List- Listing 2: Displaying voltages.
ing 2 shows one of many possible solutions.
'------------------------------------
In the previous instalment we told you how to
'UNO_LCD2.BAS Voltage A0, A3
convert the data provided by the A/D converter
'------------------------------------
into a voltage reading. Now let’s see how you
$regfile = "m328pdef.dat"
can show it on the display. First we write a string
'ATmega328p
at the start of each line that identifies the input.
$crystal = 16000000 '16
The is followed by a space character to separate
MHz
it from the reading. We also tack on a couple of
$baud = 9600
spaces after the reading (in this case a real num-
ber) has been output. Without them, the follow-
Dim D As Word
ing situation could occur: Your last reading was
4.859 V, and the new reading is 5.0 V. Bascom Dim U As Single
outputs “5.0” just as it should, but the rest of
the previous output is still there on the display, Config Adc = Single , Prescaler = 64 ,
so you see “5.059 V” and wonder what’s going Reference = Avcc '5 V
on. To prevent this from happening, we always
delete anything that might be present after the Config Lcdpin = Pin , Db4 = Portd.4 ,
current output. Here we accept the risk that this Db5 = Portd.5 , Db6 = Portd.6 , Db7 =
may involve characters intended for a larger dis- Portd.7 , E = Portd.3 , Rs = Portd.2
play that are not visible on the actual display. Config Lcd = 16 * 2

Incidentally, this program uses the ADC0 and Cls


ADC3 channels for its measurements. You can Cursor Off
connect a signal source to ADC0, preferably with Do
a protective series resistor as shown in Figure 2. Locate 1 , 1
There’s already something connected to ADC3: Lcd "A0 "
the potentiometer on the Elektor shield. You can D = Getadc(1) 'A0
adjust it to provide a voltage from 0 to 5 V. U = D * 5.0
All of the Arduino pins are also fed out to socket U = U / 1023
headers on the shield. If you connect a hefty Lcd U
electrolytic capacitor (you surely have an elec- Lcd " "
trolytic somewhere on your bench – but don’t
exceed 470 µF) between the GND and ADC3 pins, Locate 2 , 1 'Pot
which puts it in parallel with the potentiometer, Lcd "A3 "
you have a low-pass filter and you can see on the
D = Getadc(3)
display how the voltage gradually adjusts after
U = D * 5.0
you change the potentiometer setting. The rea-
U = U / 1023
son for the 470 µF limit is that you might allow
Lcd U
the capacitor to charge slowly to 5 V and then
Lcd " "
quickly turn the potentiometer towards zero. If
Waitms 1000
the capacitor is too large, the resulting discharge
Loop
current could fry the potentiometer.

80
www.elektor-magazine.com | July & August 2014 | 61

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

to a certain extent by the potentiometer voltage


LED1 LED2 on ADC3. This is due to the sample-and-hold
capacitor at the input of the A/D converter. This
0...5V
capacitor is first charged to the voltage present

1k

1k
100u...
470u on the measurement input, and then its charge
+5V
10k is measured. If the capacitor last saw 3 V from

10k
the potentiometer during the previous measure-
ment, some of its charge will still be left because
28 27 26 25 24 23 22 21 20 19 18 17 16 15 it cannot discharge quickly enough through the
extremely high impedance of the LED. For this

GND

AVCC
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
AREF
ATmega328p reason, the microcontroller data sheet recom-
mends that the internal resistance of the signal

GND
VCC
RES
D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2
1 2 3 4 5 6 7 8 9 10 11 12 13 14 source should not exceed 10 kΩ. Here we are
dealing with many megohms instead, so it’s bet-
16MHz
ter to set the potentiometer to zero. Then you
100n
will see that there is still a measurable voltage
Figure 2.
22p 22p
140064 - 12
at low light levels. This circuit shows that the
Using the analog inputs. A/D converter has very high input impedance. A
typical digital voltmeter with an input impedance
that a perfectly ordinary LED can also act as a of 10 MΩ would not be able to measure the LED
photodiode – in this case as a light sensor. If you voltage, but the ATmega can do so.
shine a bright light on the LED, it can deliver a
voltage as high as 1.5 V—three times as much With very high impedance signal sources, you
as a silicon photodiode. That’s because a larger can connect a 10 nF bypass capacitor in parallel
band gap means a greater voltage, which applies as shown in Figure 3. This makes the measure-
equally well to the forward voltage of a diode and ments much more reliable. Even with very dim
voltage it generates. light, you can now measure a voltage of roughly
Another thing you might notice is that at low light 1 V. For all PN junctions with their exponential
levels the voltage measured on ADC2 is affected characteristic curves, the rule of thumb is that
the voltage rises by approximately 70 mV when
the current is increased by a factor of 10. This
Listing 3: Measuring the LED voltage means that the span between 1.0 V and 1.5 V cor-
and the potentiometer voltage. responds to seven decades of current range, and
Do thus seven decades of brightness. That should
Locate 1 , 1 be more than enough for measuring from 10 lux
Lcd "A2 " to 100,000 lux, and we can see the makings of
a light meter here. Maybe that’s an attractive
D = Getadc(2) 'LED1
job for an enthusiastic reader? There’s nothing
U = D * 5.0
wrong with a nice collection of Bascom programs
U = U / 1023
with contributions from many people.
Lcd U
Lcd " " PWM outputs
When precise timing matters, timers come to the
Locate 2 , 1 fore. Most microcontrollers have several timers.
Lcd "A3 " Timer1 of the ATmega328 has a resolution of
D = Getadc(3) 'Pot 16 bits. You can regarded it as a sixteen-stage
U = D * 5.0 counter, similar to the well-known CD4040 (which
U = U / 1023 has only twelve stages). A clock signal (or other
Lcd U pulse signal) entering at one end comes out at
Lcd " " the other end with a lower frequency. You can
use the CD4040 to build a clock generator or a
Waitms 1000
frequency divider, or as the basis for a binary
Loop
pulse counter. Timer1 can also handle all of these

81
62 | July & August 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

functions; you just have to initialize it properly.


There are also two 8-bit timers on board (Timer0 LED1 LED2

and Timer2).

1k

1k
One of the many operating modes of Timer1 is 10n

PWM mode. It can generate two pulse width mod-


+5V 10k
ulated signals, which means rectangular pulse
signals with adjustable mark/space (on/off) ratio.
Among other things, they can be used to con-
28 27 26 25 24 23 22 21 20 19 18 17 16 15
trol the brightness of a lamp, much in the same

GND
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
AVCC
AREF
way as a dimmer on the AC line which simply
switches the voltage on and off at a high rate. ATmega328p

GND
VCC
RES
Here we want to do the same thing by using the

D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2
1 2 3 4 5 6 7 8 9 10 11 12 13 14
PWM output to control the brightness of an LED.
The PWM output has a maximum adjustment 16MHz

range of 10 bits, but it can also be configured in


8-bit mode. Here 10 bits is an attractive choice 100n
22p 22p
Figure 3.
because it matches the resolution of the A/D con- 140064 - 13 Using an LED as a light
verter. In both cases the counter runs from 0 to sensor.

Listing 4: PWM control.

'-------------------------------------- Portc.0 = 1 'Pullup


'UNO_LCD3.BAS PWM Portc.1 = 1 'Pullup
'-------------------------------------- Config Portb = Output
$regfile = "m328pdef.dat" Cls
'ATmega328p Cursor Off
$crystal = 16000000 '16 MHz Do
$baud = 9600 Locate 1 , 1
Lcd "PWMA="
A = Getadc(3)
S1 Alias Pinc.0 Pwm1a = A
S2 Alias Pinc.1 Lcd A
Lcd " "
Dim D As Word
Dim U As Single If S1 = 0 Then
If B > 0 Then B = B - 1
Config Adc = Single , Prescaler = 64 , End If
Reference = Avcc '5 V If S2 = 0 Then
If B < 1023 Then B = B + 1
Config Timer1 = Pwm , Prescale = 1 , End If
Pwm = 10 , Pwm1b = B
Compare A Pwm = Clear Up , Compare B
Pwm = Clear Up Locate 2 , 1
Lcd "PWMB="
Config Lcdpin = Pin , Db4 = Portd.4 , Lcd B
Db5 = Portd.5 , Db6 = Portd.6 , Db7 = Lcd " "
Portd.7 , E = Portd.3 , Rs = Portd.2 Waitms 100
Config Lcd = 16 * 2 Loop

82
www.elektor-magazine.com | July & August 2014 | 63

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

clock frequency is used. You might think that this


PWMA PWMB
LED1 LED2 yields a PWM frequency of 15.625 kHz (16 MHz
divided by 1024), but in fact it is only half of this
S2 S1
(approximately 7.8 kHz). This come from the fact

1k

1k
that Bascom uses the “Phase Correct PWM” mode
instead of the “Fast PWM” mode. You can learn
+5V 10k
more about this from the microcontroller data
sheet, but that’s more like a book than a data
sheet. Here Bascom saves developers time and
28 27 26 25 24 23 22 21 20 19 18 17 16 15
effort by always choosing a reasonable option for

GND
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
AVCC
AREF
each setting. This means you can obtain work-
ATmega328p ing results with Bascom even if you don’t fully

GND
understand all the details.
VCC
RES
D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2
1 2 3 4 5 6 7 8 9 10 11 12 13 14

LED 2 is connected to the second PWM output


16MHz
(PB2). In our program this output is controlled
100n by the two pushbuttons S1 and S2. To make
Figure 4.
22p 22p the program easy to read, the Alias instruc-
A pair of LEDs connected to 140064 - 14

the PWM outputs. tion is used to assign the button names to the
port inputs. This means that when you write If
1023. You could for example program the out- S1 = 0 Then in your code, Bascom knows that
put to switch off when the counter reaches 511, what you actually mean is If Pinc.1 = 0, so the
which results in a PWM signal with a 50% duty state of port pin PC1 has to be polled. Another
factor. This is achieved by repeatedly comparing important consideration is that the buttons are
the counter value with the programmed value connected to ground and therefore require pullup
in a compare unit. There are two compare units resistors. As a result, the program normally sees
in the microcontroller, so you can generate two the quiescent state S1 = 1. This only changes to
independent PWM signals with the same timer. S1 = 0 when someone presses the button. That
PWM1A is output on port pin PB1, while PWM1B makes things very simple. When you press S1
is output on pin PB2. That reminds us of some- you reduce the PWM output level (assuming it
thing. You guessed it: LED 2 is connected to PB2 is greater than 0), and when you press S2 you
through a 1 kΩ series resistor. Coincidence? Not raise the PWM output level (assuming it is less
at all, because now you can use the PWM signal than 1023). This proceeds in single steps if you
to control the brightness of the LED. press the button briefly, but if you press and hold
The program in Listing 4 uses the PWM1A out- the button it changes continuously at ten steps
put together with the A/D converter input ADC3, per second. The current output value is always
which is connected to the potentiometer. The shown on the LCD.
measured value of the potentiometer setting is
used as the comparison value for the PWM sig- Button polling
nal. If you set the potentiometer to mid-range, The program shows a very simple example of
the PWM output is a symmetrical square wave. how to use buttons and corresponding program
Everything from 0 to 1023 is possible. The actual branching. Of course, there are lots of other ways
output value is shown on the LCD. If you want to obtain the desired result. Developing the ideal
to look at the signal, you can connect a scope user interface for a given task is a fascinating
probe to PB1 (Arduino pin 9). job. You can configure a wide variety of things
with two buttons and a potentiometer. A lot can
What is the frequency of the PWM signal? That be achieved with just a few buttons.
depends on the frequency of the clock input to the The program uses everything that the Elektor
timer. It can be the clock signal from the Arduino shield has to offer. The LCD shows the two cur-
board (16 MHz), but it can also be a lower-fre- rent PWM values, the potentiometer controls the
quency signal derived from the clock signal by PWMA output, and the two buttons control the
passing it through a prescaler. Here the initializa- PWMB output and thereby LED 2. Is that really
tion instruction Prescale = 1 means that the full everything? Well, not quite—LED 1 isn’t doing

83
64 | July & August 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

anything. So let’s plug a wire into PB1 (Arduino ness using the potentiometer. The LCD reveals
pin 9) and ADC2 (Arduino A2) to connect PWMA how well this went. Then the two players swap
to LED 1 through a 1 kΩ resistor and a jumper roles. All differences between the two values are
(Figure 4). Now you can control the brightness recorded. The player with the lowest score at the
of the LED with the potentiometer. end is the winner and is designated “Hawkeye”.
With two LEDs whose brightness can be set (140064-I)
independently, you have the makings of a little
Web Links
skill-testing game. The first player sets the bright-
ness of LED 2 to some arbitrary value using the [1] www.elektor-magazine.com/140064
buttons. Then this LED is covered, and the sec- [2] http://b-kainka.de/bastel49.htm (in German)
ond player tries to set LED 1 to the same bright- [3] http://en.wikipedia.org/wiki/Polarizer

MCS Boot Loader


Up to now we have described two MSC boot loader, you must configure
options for programming the Arduino: Bascom accordingly. Here again it is
using the Arduino boot loader or important to set the right COM port
using the ISP interface, which is also and the right baud rate, in this case
brought out on the Elektor shield. 19,200 (see the second screenshot).
With an external programmer, you
can also use the ISP interface to load There is another important setting
a different boot loader. on the MCS Loader tab. As you may
recall, data is transmitted to the
Bascom has the MCS boot loader, Arduino board over the USB bus,
which can be adapted to various but it arrives through a simulated
microcontrollers. That’s attractive RS232 port. All Arduino systems use
because it allows you to equip the RS232 DTR line as a Reset line;
different microcontroller boards a falling edge on this line triggers
with the same boot loader. The a reset. That’s what starts the boot
source code is included with the loader, because the microcontroller
Bascom example programs. All that runs the program code stored at the
is necessary for adaptation is to boot address (&H3C00) when it starts
configure the microcontroller type, up. This code waits for a specific
the clock frequency and the desired action from the PC. Either new
baud rate. The configuration for program comes down the pipe or it
the ATmega328P was not yet there, doesn’t, and then execution branches
but the adaptation was easy. The to the start of program memory at
fully adapted boot loader, including address zero. This process occurs
the source code and hex file, can with every reset, which is what allows
be downloaded from the Elektor Bascom to force a jump to the boot
website [1]. The files are called loader by changing the level on the
BootLoaderUno_16.bas (16 stands DTR line. Users have it easy because
for 16 MHz) and BootLoaderUno_16. they don’t have to press the reset
hex. Note that the fuse settings button themselves.
must be slightly different (see the
first AVR Studio screenshot) than
for the Arduino boot loader because
more memory space is needed.
The boot area is 1024 words with
the MSC boot loader and starts at
&H3C00. If you intend to use the

84
www.elektor-magazine.com | July & August 2014 | 65

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Microcontroller
BootCamp (5)
Using timers

by Burkhard Kainka Flip-flops, dividers and counters


(Germany)
are fundamental components in
digital circuits. They are also found in
microcontrollers, where they have a wide range of uses:
here we look at a few.

One of the longest chapters in the ATmega328 which has a resolution of 16 bits. Now, all the
data sheet is the one that describes its three timer module does is simply act as a counter of
timers. The timers can be used in so many dif- regular events. In this case, with a 16-bit counter,
ferent ways that we only have space here to look the maximum count is 65535, after which the
at a small fraction of the possibilities. The main counter returns to zero: this is called ‘overflow’.
application areas are in measuring time inter- If things are arranged so that the counter incre-
vals and frequencies, and in generating various ments once a microsecond we can measure time
signals including PWM output. intervals of up to 65535 µs. Between the crys-
tal oscillator and the clock input of the counter
Measure those microseconds there is a programmable prescaler (similar to the
The need to measure time intervals often crops arrangement for the A/D converter) that divides
up in electronics. For example, we might want to down the clock frequency. If a 16 MHz crystal is
know how long it takes to output some data to an used then the required division ratio to obtain
LCD module: is it milliseconds or microseconds? a 1 MHz clock for the timer is 16. So our first
Without some inside knowledge, the only way attempt reads
is to measure it. The ATmega328 has a suitable
module already on board in the form of Timer1, Config Timer1 = Timer , Prescale = 16

85
30 | September 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

but unfortunately this does not work. The error takes around a millisecond per character because
message we get is ‘Prescale value must be 1, Bascom allows plenty of time for the controller
8, 64, 256 or 1024’, and the data sheet of the in the module to accept the data. If you take a
ATmega328 confirms the problem. So, we shall look at the E signal on the LCD (port pin PD3,
set the prescaler ratio to 8 and obtain an input Arduino pin 3) using an oscilloscope you will see
clock to the timer of 2 MHz and a maximum the 1 ms delays.
interval measurement of 32767.5 µs. At any time
the 16-bit register that holds Timer1’s value can Measuring the period of a signal
be read or a new value can be written to it. This A small modification to our program (see List-
makes our example very straightforward. Before ing 2) allows it to measure the length or period
outputting the data to the LCD module we set the of a pulse. We use input PC0 (Arduino A0: see
counter to zero (‘Timer1 = 0’). After outputting Figure 2), and we will measure the time between
the data we read the counter value (‘D = Timer1’) two rising edges of the input signal. We need two
and we have the result of the measurement in sampling loops to detect an edge reliably: first
units of 0.5 µs. To convert to microseconds we we wait until the input reads as a zero, and then
simply divide the result by 2. Listing 1 shows we wait until it reads as a one. This will detect
the complete program.

As in all the programs we shall look at here, the


result is displayed on the Arduino shield LCD
module we described in the previous installment 16 MHz
in this series, and simultaneously the result is 2 MHz
/8 Timer1, 0 ...65535
0,5 us
output to the terminal using a ‘Print’ command.
The program will work even if the display is not
connected: Bascom does not check whether the
display has actually received the data it sends to
it. The first result we see is ‘Timer 1 = 0 us’: this
happens because at this point, before the first Figure 1.
Listing 1. Measuring the time
Time measurement using
measurement, the variable D has not been set. taken to output to the LCD.
Timer1.
The second result looks rather more interesting,
'------------------------------------
giving the time taken to output the first result to
'UNO_Timer1.BAS Timer1 0.5 us
the LCD: ‘Timer 1 = 17105 us’. Now in this case
'------------------------------------
four additional digits have had to be sent to the
...
display, and so we would expect the process to
take a little longer. And indeed it does, the third
Dim D As Word
result being 21933 µs. The results now stabilize,
Config Timer1 = Timer , Prescale = 8
with variations between successive readings of
'Clock 2 MHz
at most one microsecond.
Do
So now we know exactly how long a complex
Print "Timer1 = ";
process like writing a string to the LCD takes.
Print D;
The precision and repeatability we have seen
Print " us"
would be unimaginable on a Windows or Linux
Timer1 = 0
machine, since these complex operating systems
Locate 1 , 1
do not handle real-time functions well: there is
Lcd "Timer1 ="
always some process running in the background
Locate 2 , 1
that makes it impossible to predict exactly how
Lcd D
long some action will take. Under Bascom things
Lcd " us"
are different: the processor executes exactly the
D = Timer1
code you tell it to execute and nothing more.
D = D / 2
Moreover, being so close to the hardware, some
Waitms 1000
commands such as setting an output bit execute
Loop
in less than a microsecond. Outputting to the LCD

86
www.elektor-magazine.com | September | 31

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

a little on the slow side. Since the mains supply


in most of mainland Europe is phase-synchro-
nous, we can only conclude that perhaps too
many power stations had been turned off or the
+5V sun was not shining brightly enough or the wind
122.549 Hz

10k
not blowing strongly enough. Perhaps it might
be worth turning a couple of lights off and try-
ing again...
28 27 26 25 24 23 22 21 20 19 18 17 16 15
In order that we have a reliable signal to mea-
sure, the program includes its own clock source,

GND

AVCC
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
AREF
ATmega328p taking advantage of the PWM outputs. However,
there is a potential problem. PWM1A and PWM1B

GND
VCC
RES
D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2
1 2 3 4 5 6 7 8 9 10 11 12 13 14
cannot be used because we have already commit-
ted Timer1 for making the measurement itself.
16MHz That leaves us with Timer0 and Timer2, each of
which can also drive two PWM outputs. However,
100n these extra outputs mostly appear on Port D and
Figure 2. 22p 22p would therefore interfere with the LCD interface.
140049 - 12
Measuring the period of a An exception is PWM2A which is on port pin PB3
signal. (Arduino pin 11), and so this is the one we use to
output our test signal. Timer2 has only an 8-bit
the first rising edge, and we set the timer reg- counter but if we set its prescaler ratio to 256,
ister to zero. We now wait for the second edge, we can obtain an output frequency of 16 MHz /
and read the result from the timer. 256 / 255 / 2 = 122.549 Hz and hence an output
If a finger is touched on the input pin, the micro- period of 8.16 ms. Connecting PB3 to PC0 lets
controller will receive a signal picked up from the us measure this signal, and the reading we get
mains supply, which will be at 60 Hz in the USA is 8160 µs. Result!
and 50 Hz in most other countries. We would
expect a result of around 16667 µs or 20000 µs Square wave generator,
respectively. In a real experiment (carried out 125 Hz to 4 MHz
in Europe) a reading of 20030 µs was obtained, A variable-frequency signal generator is often a

Listing 2. Measuring the period of a signal in microseconds.

'----------------------------------------- Timer1 = 0
'UNO_Timer2.BAS Timer1, 0.5 us Do
'----------------------------------------- Loop Until Pinc.0 = 0
... Do
Loop Until Pinc.0 = 1
Dim D As Word D = Timer1
D = D / 2
Config Timer1 = Timer , Prescale = 8 'Clock 2 MHz Locate 1 , 1
Config Timer2 = Pwm , Prescale = 256 , Lcd "Timer1 ="
Compare A Pwm = Clear Up Locate 2 , 1
Ddrb = 255 Lcd D
Pwm2a = 128 Lcd " us "
Print "Timer1 = ";
Do Print D;
Do Print " us"
Loop Until Pinc.0 = 0 Waitms 1000
Do Loop
Loop Until Pinc.0 = 1

87
32 | September 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

Listing 3. Timer1 used as a square wave generator.

'----------------------------------------- If S1 = 0 Then
'UNO_Timer3.BAS B1 Fout 250 Hz...4 MHz D = D + 1
'----------------------------------------- If D > 100 Then D = D + 1
... If D > 1000 Then D = D + 100
If D > 10000 Then D = D + 1000
Dim D As Long If D > 64000 Then D = 64000
Dim F As Long End If
Dim N As Byte If S2 = 0 Then
If D > 2 Then D = D - 1
Config Timer1 = Pwm , Prescale = 1 , Pwm = 10 , If D > 100 Then D = D - 10
Compare A Pwm = Clear Up If D > 1000 Then D = D - 100
If D > 10000 Then D = D - 1000
Tccr1a = &B10000010 'Phase-correct PWM, Top=ICR1 If D > 64000 Then D = 64000
Tccr1b = &B00010001 'Prescaler=1 End If
Locate 1 , 1
D = 8000 F = 16000000 / D
Do F = F / 2
N = Ischarwaiting() Lcd F
If N = 1 Then Lcd " Hz "
Input F Icr1 = D
D = 8000000 / F Ocr1a = D / 2
If D > 64000 Then D = 64000 Waitms 50
If D < 2 Then D = 2 Loop
End If

useful tool to have. At 1 MHz it might be used to a terminal emulator program or using buttons.
test a frequency counter, or at 440 Hz it might When pressed, the buttons increase or decrease
be used to tune a violin. The program shown in the division ratio, and the program calculates
Listing 3 covers the whole range from 125 Hz the resulting frequency and displays it. A brief
to 4 MHz. Timer1 is used as a frequency divider press of a button changes the ratio in small steps,
and the signal is output on the PWM1A pin (B1, while a longer press causes the ratio to change
Arduino pin 9: see Figure 3). This is an exam-
ple of an application where we are going a little
beyond the standard uses of Bascom, and in par-
125 Hz ... 4 MHz
ticular its built-in initialization functions are not S2 S1
+5V
suitable for our purposes: we have to program
a few registers directly. I borrowed some ideas F+ F–
1k

from Roger Leifert’s DCF simulator [1], and he in


turn borrowed from the code in Martin Ossman’s 28 27 26 25 24 23 22 21 20 19 18 17 16 15
SDR course [2], which is written in C. We use a
GND

AVCC
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
AREF

variant of PWM output mode where we adjust the


frequency while trying to maintain a duty cycle ATmega328p
GND

of approximately 50%. Register LCR1 is loaded


VCC
RES
D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2

with the desired division ratio. If, for example, 1 2 3 4 5 6 7 8 9 10 11 12 13 14

this value is 100, then the output frequency will


16MHz
be 16 MHz / 100 / 2 = 80 kHz. To ensure that
the output is a symmetric square wave we need
100n
to load register OCR1A with the value 50. Figure 3.
22p 22p
The program can be controlled (simultaneously) 140049 - 13 Adjustable square wave
in two different ways: over the serial port using generator.

88
www.elektor-magazine.com | September | 33

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

the frequency range. This means that many fre-


quencies will only be approximated rather than
generated exactly. The output frequency is dis-
16 MHz 1 kHz
250 kHz played in Hertz and the numbers involved are
/64 Timer0, /250
Interrupt such that the calculations must be done not using
word variables but with ‘long’ (32-bit) quanti-
ties: this applies both to the frequency F and to
the division ratio D.

Figure 4. (almost) continuously. Since it would be rather It is perhaps not completely obvious how the
Producing 1 kHz from tedious to step through all the possible ratios in program manages to respond both to button
16 MHz. this way (there are more than 65000 of them), presses and to input on the serial port. If we
the amount of increment changes depending on write simply ‘Input F’ then the program will wait
at this point until a value is entered, and will not
respond to the buttons. We therefore have to
Listing 4. Counting seconds check first whether there is a character available
exactly using an interrupt. on the serial interface: the function IsCharWait-
ing() returns a value of 1 if there is at least one
'------------------------------------
character available and zero otherwise. In our
'UNO_Timer4.BAS
case, if one character arrives on the serial inter-
'Timer0-Interrupt, Seconds
face then we know that there are more to come,
'------------------------------------
and we can safely read in a new value for F.
...
From F we can calculate the required division
ratio, in many cases obtaining an exact result. At
Dim Ticks As Word
440 Hz there is only negligible error, although at
Dim Seconds As Word
549 kHz, for example, only a rough approxima-
Dim Seconds_old As Word
tion is available: the program chooses a division
ratio of 14, which results in an output frequency
Config Timer0 = Timer , Prescale = 64
of 571428 Hz. The smallest division ratios give
On Ovf0 Tim0_isr
rise to the highest frequencies, namely 4 MHz,
Enable Timer0
2.666666 MHz, 2 MHz, 1.6 MHz, 1.333333 MHz
Enable Interrupts
and 1 MHz. If these are useful to you, then you
could build the design as a self-contained unit.
Do
The steep edges on the signal on output PB1
If Seconds <> Seconds_old Then
mean that it contains harmonics well into the
Print Seconds
VHF range. This means it is all too easy for the
Seconds_old = Seconds
signal generator to become a source of radio
Locate 1 , 1
interference. For example, if you connect the
Lcd Seconds
oscilloscope probe to the output but forget to
End If
connect the ground clip close by then a large and
Loop
rather effective VHF loop antenna can be cre-
ated via the ground connection to the USB port
Tim0_isr:
and then through the PC’s power supply and the
'1000 µs
mains. Unsurprisingly this can disrupt reception
Timer0 = 6
on nearby FM radios and hence relations with
Ticks = Ticks + 1
your neighbors! To keep on the right side of the
If Ticks = 1000 Then
EMC regulations (and your neighbors) it is neces-
Ticks = 0
sary to use either a screened cable, or a resistor
Seconds = Seconds + 1
close to the signal generator’s output to reduce
End If
the amplitude of the higher harmonics. A resistor
Return
of 1 kΩ in conjunction with a cable capacitance
of 30 pF forms a low-pass filter with a cutoff
End
frequency of 5 MHz. The edges of the signal are

89
34 | September 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

smoothed considerably, and VHF interference is


AC/DC 0 ...1 V
reduced by around 20 dB.

Timer interrupts +5V


In the previous installment of this series we 1,25 kHz

10k
looked at an example program that generates
a one-second clock. The timing used a simple
‘Waitms 1000’ command. Now this approach 28 27 26 25 24 23 22 21 20 19 18 17 16 15

does not give an exact result, as the other parts

GND

AVCC
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
AREF
of the program such as the infinite loop and the
ATmega328p
code that generates the output all take time. The

GND
VCC
RES
problem can be avoided using a timer interrupt:

D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2
1 2 3 4 5 6 7 8 9 10 11 12 13 14
that is, allowing a certain part of the code to
execute exclusively under control of a timer. It
16MHz
works as follows. A hardware timer counts away,
completely independent of other activity in the
100n
microcontroller. When it reaches its maximum 22p 22p
Figure 5.
count and resets to zero (‘overflow’) the program 140049 - 15 AC and DC voltage
executing in the foreground is interrupted and measurement.
a special piece of code called an ‘interrupt ser-
vice routine’, or ISR, is called. Within this piece every millisecond. The word variable ‘Ticks’ is
of code we can carry out any actions that need incremented by one on each timer overflow.
to happen at exactly-specified time intervals. It When it reaches 1000 the variable ‘Seconds’ is
makes no difference how long the ISR itself takes incremented. The variables ‘Seconds’ and ‘Ticks’
to execute as the hardware timer is continuing can be read from the main program code. In
to count: the only thing that matters is that the this example the program outputs the number
routine completes before the next time the timer of seconds since it was started, both to the LCD
overflows and triggers the interrupt again. and to the terminal.
For the job of generating a precise one-second
clock Timer1 is overkill: the eight-bit resolution To ensure that the interrupt service routine is
of Timer0 is plenty for this application. We will actually called, the corresponding interrupt (the
arrange for the timer to overflow and hence gen- Timer0 overflow interrupt) must be enabled. This
erate an interrupt every 1000 µs. The interrupt is done with the line ‘Enable Timer0’. Interrupts
service routine, which, as it is triggered from must also be globally enabled, using the com-
Timer0, we have called ‘Tim0_isr:’, will thus be mand ‘Enable Interrupts’. The complementary
called every millisecond. The colon means that command ‘Disable Interrupts’ prevents all inter-
‘Tim0_isr:’ will be interpreted as a label, marking rupts from occurring.
a point in the code which can be jumped to. The
command ‘On Ovf0 Tim0_isr’ tells the micro- Averaging analog readings
controller to jump to this label whenever there Analog readings often have mains hum, at 50 Hz
is an overflow (‘Ovf’) on Timer0. The interrupt or 60 Hz depending on the local frequency, super-
service routine must finish with a ‘Return’ com- imposed on them. One way to try to remove this
mand: after that point the interrupt routine can is to take the average of a number of consecutive
be called again. samples: see Listing 5. If readings are aver-
The example program shown in Listing 4 ini- aged over an integer number of mains cycles
tializes Timer0 with a prescale ratio of 64, which (that is, over a multiple of 20 ms or 16.667 ms
means it increments at 250 kHz (see Figure 4). If respectively), the effect is to create a null at that
we did not take any further steps the timer would frequency. In other words, the hum will be sig-
overflow on every 256th clock, as the counter is nificantly attenuated.
eight bits wide. To arrange for an overflow every Again in this example we use a timer interrupt to
250 clocks, the first thing the interrupt service ensure accurate timings. We will take the aver-
routine does is load the counter with the value 6. age of 500 consecutive readings from ADC0 (see
The result is that the routine is called exactly Figure 5), which a total of 400 ms. Now this is

90
www.elektor-magazine.com | September | 35

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Listing 5. Averaging within a timer interrupt. exactly 20 periods at 50 Hz and 24 periods at


60 Hz and so in either case we are averaging over
'----------------------------------------------- an integer number of mains cycles. The period
' UNO_Timer5.BAS Timer1-Interrupt, ADC0 average between conversions is 800 µs, and to generate
'----------------------------------------------- this timing we use Timer2, again with a pres-
... cale ratio of 64. Each time Timer2 overflows it
is reloaded with the value 56, and so the next
Dim Ticks As Word overflow occurs exactly 200 clocks later.
Dim Ad As Word Eight hundred microseconds is long enough to
Dim Ad0 As Long carry out one conversion (or even several) and
Dim Ad0_mean As Long accumulate the results. The calls to the inter-
rupt routine and hence the individual readings
Config Adc = Single , Prescaler = 32 , Reference = Internal are counted in the variable ‘Ticks’, and after 500
Config Portb.2 = Output readings have been accumulated the sum in vari-
able ‘AD0’ is copied to the variable ‘AD0_mean’.
The foreground code can read this variable and
Config Timer2 = Timer , Prescale = 64
send the result to the terminal.
On Ovf2 Tim2_isr
It is sound practice to use an oscilloscope to check
Enable Timer2
that the interrupt routine is running as expected.
Enable Interrupts
Is it really being executed every 800 µs, that is,
at 1.25 kHz? How long does it take to service
Do the interrupt? A simple trick helps to see what
Disable Interrupts is going on: at the start of the interrupt service
Ad0_mean = Ad0_mean * 2443 'AC routine set a port pin high, and at the end take it
'Ad0_mean = Ad0_mean * 1100 'DC low again. In this example we use port PB2, which
Ad0_mean = Ad0_mean / 1023 is connected to LED 2. The oscilloscope does
Ad0_mean = Ad0_mean / 500 indeed show a pulse every 800 µs lasting about
Print Ad0_mean 60 µs, and so there is nothing to worry about.
Locate 1 , 1 In other cases, however, it can happen that so
Lcd Ad0_mean much is packed into the interrupt service routine
Lcd " mV " that the main program never gets executed, and
Enable Interrupts it is not always obvious what is happening. Fur-
Waitms 1000 thermore, when interrupts are used, the timing
of the main program is no longer so easily pre-
Loop
dictable; a good rule of thumb is to ensure that
no more the 50 % of the microcontroller’s time
Tim2_isr:
is spent in interrupt service routines.
'800 µs
The averaging process is so good at removing
Timer2 = 56
the mains hum component of the signal that it
Portb.2 = 1
can be used to measure AC voltages using half-
Ticks = Ticks + 1 wave rectification. The A/D converter already
Ad = Getadc(0) performs half-wave rectification, in that it only
Ad0 = Ad0 + Ad measures positive voltages and all negative volt-
If Ticks >= 500 Then ages read as zero. If an AC voltage is applied to
Ticks = 0 the A/D converter input via a 10 kΩ series pro-
Ad0_mean = Ad0 tection resistor then the converter will only see
Ad0 = 0 the positive half-cycles. The program will then
End If average these readings, with the result that, in
Portb.2 = 0 the case of a square wave input, the average of
Return these half cycles is half the DC voltage with the
same effective (RMS) value as the input. In the
End case of a sinusoidal input there is a further factor
of pi/2 = 1.571: in other words, the calculated

91
36 | September 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

Listing 6. Frequency measurement up to 4 MHz.

+5V 31.373 Hz '--------------------------------------


'UNO_Timer6.BAS Frequency 0...4 MHz
'--------------------------------------

10k
...
28 27 26 25 24 23 22 21 20 19 18 17 16 15

Dim Lowword As Word


GND
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
AVCC
AREF

ATmega328p Dim Highword As Word


Dim Ticks As Word
GND
VCC
RES
D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2

1 2 3 4 5 6 7 8 9 10 11 12 13 14 Dim Freq As Long

16MHz
Config Timer0 = Timer , Prescale = 64
On Ovf0 Tim0_isr
100n Enable Timer0
22p 22p
140049 - 16
Config Timer1 = Counter , Edge = Falling , Prescale = 1
On Ovf1 Tim1_isr
Enable Timer1
Figure 6. Frequency meter with test output.

Config Timer2 = Pwm , Prescale = 1 , Compare A Pwm = Clear


Up
average is 90.03 % of the true RMS value. These Pwm2a = 128 'B3: 31373 Hz
factors can be taken into account in calculating Enable Interrupts
the displayed reading in millivolts. For pure DC
measurements the fact that the reference voltage Do
is 1100 mV means the correction factor is 1100. Print Freq;
For AC voltage measurements the factor should Print " Hz ";
be 2443, and readings will be correct up to a Print Chr(13);
peak input voltage of 1.1 V. The procedure also Waitms 1000
works at other frequencies, and in fact voltages Loop
at any frequency from 50 Hz to 50 kHz can be
measured, meaning that the set-up can be used Tim0_isr:
as a wide-bandwidth millivoltmeter in audio and '1000 µs
other applications. Timer0 = 6
Ticks = Ticks + 1
Frequency measurement If Ticks = 1 Then
In the examples we have looked at so far the Timer1 = 0
timer has received its clock pulses from within Highword = 0
the processor, either directly from the proces- End If
sor’s clock or via a divider. However, it is possi- If Ticks = 1001 Then
ble to clock the timer using an external signal, in Lowword = Timer1
which case the timer behaves as a pulse counter. Freq = Highword * 65536
Timer1 in an ATmega328 clocked at 16 MHz can Freq = Freq + Lowword
reliably count external pulses at a frequency of Ticks = 0
up to 4 MHz. Unfortunately, the input lies on port End If
pin PD5 (see Figure 6) and so we cannot use the Return
LCD module as well. We could alternatively use
an external LCD module controlled over a serial Tim1_isr:
interface, but for now we will simply send our Highword = Highword + 1
results to a terminal emulator running on a PC. Return
To use Timer1 as part of a frequency counter End
(see Listing 6) we also need to measure the

92
www.elektor-magazine.com | September | 37

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Listing 7. Text output on the LCD.

'----------------------------------- Do
'UNO_Display.BAS COM input B0 'Input Text1
'---------------------------------- Input #2 , Text1
... Locate 1 , 1
Lcd Text2
Dim Text1 As String * 16 Text2 = Text1 + " "
Dim Text2 As String * 16 Locate 2 , 1
Lcd Text2
Open "comb.0:9600,8,n,1" For Input As Loop
#2
'Software COM input at B0 End

gate time accurately. To do this we use a second


timer and two interrupts. So that we can mea-
sure frequencies above 65535 Hz, the interrupt
service routine Tim1_isr is called whenever it
overflows to increment the variable ‘Highword’.
Timer0 is responsible for providing a gate time of
exactly one second. When the variable ‘Ticks’ is
equal to one Timer1 is reset and counting starts.
Exactly 1000 ms later the current counter value
Figure 7.
The frequency displayed
in Timer1 is read into the variable ‘Lowword’ and
using the terminal emulator. then the frequency is calculated from this and
the value in ‘Highword’. The foreground code can
now output the result as a frequency in Hertz.
If we configure Timer1 as an ordinary timer with a
+5V
16 MHz clock (using the command ‘Config Timer1
= Timer , Prescale = 1’) then we should see a
reported frequency of exactly 16000000 Hz. With
28 27 26 25 24 23 22 21 20 19 18 17 16 15
the timer configured as a counter, however, the
GND

AVCC
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
AREF

maximum increment rate is limited to a quarter


ATmega328p of the processor clock, because the state of the
GND

input pin is only sampled at a limited rate. If


VCC
RES
D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2

1 2 3 4 5 6 7 8 9 10 11 12 13 14
RX-Input 2
we try an input frequency of 6 MHz we find that
approximately every other pulse is lost, giving
a reading of around 3 MHz. At frequencies up
100n to a little over 4 MHz, however, the counter is
16MHz
very accurate.
Observe one special aspect of the ‘Print’ com-
22p 22p mands. Normally Bascom terminates each print
10k
command by emitting Chr(13) and Chr(10), which
Contrast
makes it easy to send the output of one Bascom
1 2 3 4 5 6 7 8 9 10 11 12 13 14
program to the input of another. However, in the
receive direction only the character Chr(13) is
D0
D1
D2
D3
D4
D5
D6
D7
GND

R/W
RS

E
VEE
VCC

expected, which means that we can suppress


LCD
the line feed character (the Chr(10)) and send
just the carriage return (the Chr(13)). To display
Figure 8. 140049 - 18 the results we can use Bascom’s own terminal
The LCD terminal. emulator: the effect is that each new reading

93
38 | September 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

overwrites the old on the same line rather than the frequency measurement). The disadvantage
beginning a new line for each: see Figure 7. is that communication during the next program
upload using the bootloader will be disturbed. It
External display is easy to forget this, which can lead to a lot of
A simple solution to the problem of not being head-scratching when you next make a change
able to use the display directly is to use another to the program!
Arduino. One, with an Elektor shield fitted, func- The second possibility takes advantage of Bas-
tions as the display module, while the other acts com’s ability to implement a serial port in soft-
as the frequency counter, sending its results over ware using any desired port pin. Here we have
a serial interface to the first. Listing 7 shows the chosen PB0 (Arduino pin 9: see Figure 8) and
code for a simple display with scrolling output. use the command ‘Input #2, Text1’. The text is
The last two lines are always shown. received just as reliably, and there is no inter-
The program offers two possibilities for receiving ference with program upload.
serial data. The command ‘Input Text1’ (com-
Web Links
mented out) uses the normal serial RX input on
D0. This input is connected to the USB interface [1] Roger Leifert, ‘DCF Tester’, Elektor June
on the Uno board via a 1 kΩ series resistor. This 2014, www.elektor-magazine.com/130571
signal can be overridden using a low-impedance [2] Martin Ossmann, ‘AVR Software Defined Ra-
drive, as for example happens when the RX pin dio’, Elektor April 2014,
on the display unit is connected directly to the TX www.elektor-magazine.com/100181
pin of the transmitting Uno (the one carrying out

Advertisement

USB Add USB to your next project.


It's easier than you might think!
DLP-USB1232H: USB 2.0 UART/FIFO
HIGH-SPEED
480Mb/s
On
Multipurpose: 7 interfaces ly $
28.
95!
Royalty-free, robust USB drivers
No in-depth knowledge of USB required
Standard 18-pin DIP interface; 0.6x1.26-inch footprint

DLP-IO8-G DLP-IOR4
8-Channel Data Acquisition 4-Channel Relay Cable
DLP-TH1b
Temp/Humidity Cable
Only
$29.95! DLP-RFID1
HF RFID Reader/Writer
DLP-FPGA
8 I/Os: Digital I/O USB-to-Xilinx FPGA Module
Analog In
Temperature
USB Port Powered
Single-Byte Commands

www.dlpdesign.com

94
www.elektor-magazine.com | September | 39

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Microcontroller
BootCamp (6)
The SPI interface

By Serial communication with each unit of information following the previous one is
Burkhard Kainka
actually the normal situation. That’s how we talk to each other in person or by
(Germany)
phone, read and write text—or in the case of Retronics: send telegrams.
In many cases all you need is a single line to transmit data. However, adding a
clock line makes things more reliable. Let‘s find out.

On the Serial Peripheral Interface (SPI) bus, the


4094 actual data travels bit by bit over one line—for
Nr. 2 example from a microcontroller to a display, an
16 15 14 13 12 11 10 9
EEPROM or an SD card. In most cases it’s also
Q'S
VCC

Q5
Q6
Q7
Q8
OE

QS

desirable to be able to read data, so you need a


+5V 4094
second line to provide a return channel for the
GND
STR

CL
Q1
Q2
Q3
Q4

data. There’s yet another part to the picture: a


D

1 2 3 4 5 6 7 8
clock line. The clock signal always clearly indi-
28 27 26 25 24 23 22 21 20 19 18 17 16 15 cates when the next bit is available on the data
line. That eliminates the need for precise agree-
GND

AVCC
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
AREF

ATmega328p ment on data timing, which both parties have


to supervise with timers. With these three lines,
GND
VCC
RES
D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2

1 2 3 4 5 6 7 8 9 10 11 12 13 14 data transmission is fairly bombproof.

16MHz
Port extension with a shift register
100n
The first thing we want to try out is actually not
Figure 1. 22p 22p
an SPI interface, but instead something entirely
140245 - 11
Connecting a type 4094 shift different. Shift registers have been around for
register. a long time (before microcontrollers were even

95
30 | October 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

invented) and are good for understanding how terminal emulator. This makes it easy to com-
serial data transfer works. They can also be put pare the output levels of the shift register to the
to good use in combination with a microcontrol- digital value being output.
ler. That’s because port lines are always scarce, If you need more than eight outputs, you can
especially on Arduino boards. A port extension use the Qs output of the 4094 IC. Each bit that
with a shift register can help ease the scarcity. is clocked into the shift register appears at the
With a type 4094 8-bit shift register, you need
three lines to talk to it and you end up with
eight new outputs. You can increase this to 16 Listing 1. Output using a shift register.
by connecting a second shift register, or even
'------------------------------------
80 if you connect ten shift register ICs in series. 'UNO_shift.BAS Shift Register 4094
If you need a lot of outputs, that’s an especially '------------------------------------
low-cost way to meet the requirement. $regfile = "m328pdef.dat"
$crystal = 16000000
Figure 1 shows the connections to the Uno board. $baud = 9600
The 8-bit shift register has a clock input (CL)
and a data input (D). The data is applied to the Dim Dat As Byte
D input one bit at a time, starting with the most Dim D As Byte
significant bit, and a rising edge is applied to the Dim N As Byte
clock input CL for each bit. The data is shifted Dim B As Bit
through the individual flip-flops of the register
step by step with each clock pulse. There is also
the strobe input STR. When a pulse is applied Sr Alias Portb.4 '4094 pin 1
to the strobe input, all the data present in the Da Alias Portb.3 '4094 pin 2
shift register is transferred to the type-D flip- Cl Alias Portb.2 '4094 pin 3
flops connected to the output pins. You could Config Portb = Output
also tie the strobe input to the supply voltage
...
Vcc, but then all the intermediate results of each
shift operation would appear on the outputs. By
Dat = 0
contrast, if you apply a strobe pulse after all the
Do
bits have been shifted in, you only see the final
Cls
result on the outputs.
Lcd Dat
Lcd " "
The software for all this (Listing 1) is simple. To Print Dat
output a byte D, the code first copies the most D = Dat
significant bit to the bit variable B (B = D.7) For N = 1 To 8
and puts it on the corresponding port pin. It B = D.7
then generates a positive clock pulse on CL with Da = B
a length of 1 millisecond. A microsecond would Waitms 1
also be sufficient, but the slower output is easier Cl = 1
to see on an oscilloscope. After the clock pulse, Waitms 1
a shift instruction (Shift D , Left) causes all Cl = 0
bits of D to be shifted left by one position. This Waitms 1
puts what used to be bit 6 on the output. This Shift D , Left
process is repeated until all eight bits have been Next N
shifted out. At the end comes the strobe pulse, Sr = 1
and then all eight bits are present at the outputs Waitms 1
of the 4094. Sr = 0
The code continuously increments the data byte Waitms 1
Dat = Dat + 1
to be transferred so the outputs of the shift regis-
Waitms 500
ter change while the program is running. The
Loop
current value is shown on the LCD if the Elektor
End
Extension shield is fitted, and it is output to the

96
www.elektor-magazine.com | October 2014 | 31

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Qs output eight clock pulses later. The D input of see the difference. There both parties have to
the next shift register can be connected to this agree on the transmission rate, and no breaks are
output. In this way you can connect as many allowed within an information unit. For example,
4094 ICs in series as desired, with the clock and if a radio operator wants to send an “X” (dash
strobe lines connected to all of them in parallel. dot dot dash) and stops in the middle to scratch
Of course, the software will have to be modi- his head, the two characters “N” (dash dot) and
fied accordingly. First it shifts out all of the bits “A” (dot dash) are sent instead. The situation is
necessary to fill the chain of shift registers (e.g. exactly the same with an asynchronous serial data
16 with two ICs or 80 with ten), and then it out- interface, where both parties have to agree on
puts the common strobe pulse. the baud rate. After the transmission of a byte
has started, all of the bits must be sent within
Manual data transmission a precise time frame. By contrast, with SPI the
Although you only need one line for the data, you timing is not critical and any desired delays are
also need a clock line when you use a clocked allowed. The additional clock signal makes the
serial interface, as in the above example with a transfer entirely independent of the speed. No
shift register or with the SPI bus. If you compare matter whether the data rate is just one bit per
this with Morse telegraphy, for example, you can minute or a million bits per second, the data will

Listing 2. SPI master and slave (very slow).


'------------------------------------- Led1 = 1
'UNO_spi1.BAS Shift in/out Waitms 200
'------------------------------------- Led1 = 0
$regfile = "m328pdef.dat" Waitms 500
$crystal = 16000000 Shift D , Left
$baud = 9600 Next N
Led1 = 0
Dim D As Byte Led2 = 0
Dim B As Bit Waitms 2000
Dim N As Byte Cls
Print
S1 Alias Pinc.0 D = 0
Portc.0 = 1 Do
S2 Alias Pinc.1 Loop Until S1 = 1
Portc.1 = 1 For N = 0 To 7
Led1 Alias Portc.2 Shift D , Left
Ddrc.2 = 1 Do
Led2 Alias Portb.2 Loop Until S1 = 0
Ddrb.2 = 1 If S2 = 0 Then B = 1 Else B = 0
D = D + B
... Lcd B
Print B;
Do Waitms 100
D = Rnd(255) Do
Cls Loop Until S1 = 1
Lcd D Waitms 100
Print D Next N
Locate 2 , 1 Print
For N = 0 To 7 Locate 2 , 1
B = D.7 Lcd D
Lcd B Print D
Print B; Waitms 2000
Led2 = B Loop
Waitms 300 End

97
32 | October 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

be transferred properly. On an SPI bus there is


Clock Data
always an SPI master and an SPI slave. Data can LED1 LED2

travel in both directions, but the master ways


generates the clock signal. S2 S1

1k

1k
Data Clock
You can try this for yourself manually, where you +5V
(as the user) assume the role of master. You can
transmit a byte by pushing the two buttons S1
and S2 (Figure 2). This is not the usual way of
28 27 26 25 24 23 22 21 20 19 18 17 16 15
doing things, but it helps you understand exactly

GND
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
AVCC
AREF
how it works. One of the buttons is for the data,
ATmega328p
and the other is for the clock. Aside from that

GND
VCC
RES
there’s nothing new you have to learn, since you

D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2
1 2 3 4 5 6 7 8 9 10 11 12 13 14
already know how a byte is put together. Here’s
how it works: First you send bit 7. If it is a ‘1’, 16MHz
you press and hold button S2; otherwise you
don’t. Then you press button S1 briefly without 100n

changing the state of S2. The receiving end (the 22p 22p
140245 - 12 Figure 2.
slave, which in this case is the Arduino board) Manual input and output.
then knows when it should read the bit from the
data line. Now you repeat the process for bit 6,
bit 5, and so on until bit 0. marked by a clock pulse. It may not have been all
that easy, but the microcontroller had no problem
The program in Listing 2 displays the data in reading the data. You can regard this as a test
both directions. At first the microcontroller is of your concentration, and if the LCD shows the
the master and you are the slave. A byte with a right result, you pass the test.
random value is sent, with the clock signal indi-
cated by LED1 and the data indicated by LED2. If you look closely at Listing 2, you will see that
If you watch carefully, you can read the trans- the bits are inverted when they are read. That’s
mitted byte. However, that’s not easy, so the because pressing the data button yields a zero
byte is also shown on the LCD and sent to the bit value. This is not especially intuitive, so the
terminal emulator. The individual bits also appear result is inverted when the bit is read to make
one after the other on the LCD and the terminal things easier for you. Another interesting aspect is
emulator screen: using the instruction D = Rnd (255) to generate
a pseudo-random number. In fact, this always
83 generates the same sequence of numbers, but
01010011 the Bascom Help gives some suggestions for what
you can do about this.
Then the roles change. Now you are the master,
and your job is to send exactly the same byte From microcontroller
back to the microcontroller. Here you can see that to microcontroller
the ability to send data at any desired speed is a In this example, data is sent over the SPI bus
big advantage, since you can take all the time you from one microcontroller to another. The data
want to decide which bit value to send next. For is this case consists of 10-bit readings from the
example, suppose you want to send the decimal A/D converter. This shows another advantage of
number 100. Bit 7 corresponds to decimal 128, SPI, which is that the data width is not fixed. No
which is more than 100, so it is ‘0’. Next comes matter whether you send 8, 10, 12 or 16 bits,
bit 6 with a value of 64, so it’s a ‘1’, and you’re the procedure is always the same. If the only
left with 36 still to send. This means that bit 5 objective were to connect two microcontrollers
(32) is a ‘1’, which leaves 4. The next two bits together, it would actually be less effort to use
(bit 4 = 16 and bit 3 = 8) are ‘0’, bit 3 (4) is a an asynchronous serial interface with the TXD
‘1’, and the last two bits are ‘0’. Now you have and RXD lines. The SPI bus, by contrast, is better
sent the binary number 01100100, with each bit for controlling and communicating with external

98
www.elektor-magazine.com | October 2014 | 33

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Listing 3. SPI master.


'------------------------------
'UNO_spi2.BAS SPI Master Cls
'------------------------------ Cursor Off
$regfile = "m328pdef.dat"
$crystal = 16000000 Waitms 200
$baud = 9600 Do
Dim B As Bit Dout = Getadc(3) 'Pot
Dim Dout As Word Locate 1 , 1
Dim N As Byte Lcd Dout
Dim I As Byte Lcd " "
Cs = 0
Sck Alias Portb.5 Waitms 20
Ddrb.5 = 1 For N = 1 To 10
Mosi Alias Portb.3 Mosi = Dout.9
Ddrb.3 = 1 Waitms 1
Cs Alias Portb.2 Sck = 1
Ddrb.2 = 1 Waitms 1
Sck = 0
Cs = 1 Waitms 1
Mosi = 0 Shift Dout , Left
Sck = 0 Next N
Cs = 1
Config Adc = Single , Prescaler = 32 , Waitms 100
Reference = Avcc Loop
Start Adc End

Listing 4. SPI slave.


'----------------------------- Portb.2 = 1
'UNO_spi3.BAS SPI Slave ...
'-----------------------------
$regfile = "m328pdef.dat" Do
$crystal = 16000000 Do
$baud = 9600 Loop Until Cs = 0
Din = 0
Dim Addr As Byte For N = 1 To 10
Dim B As Bit Shift Din , Left
Dim Dout As Word Do
Dim Din As Word Loop Until Sck = 1
Dim N As Byte Din = Din + Mosi
Dim I As Byte Do
Loop Until Sck = 0
Next N
S1 Alias Pinc.0 Do
Portc.0 = 1 Loop Until Cs = 1
S2 Alias Pinc.1 Locate 1 , 1
Portc.1 = 1 Lcd Din
Sck Alias Pinb.5 Lcd " "
Portb.5 = 1 Print Din
Mosi Alias Pinb.3 Loop
Portb.3 = 1 End
Cs Alias Pinb.2

99
34 | October 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

MOSI
SCK

MISO 1 2 VCC MISO 1 2 VCC


Master SCK 3 4 MOSI Slave SCK 3 4 MOSI
RESET 5 6 GND RESET 5 6 GND
10k

ICSP ICSP
CS

+5V +5V

28 27 26 25 24 23 22 21 20 19 18 17 16 15 28 27 26 25 24 23 22 21 20 19 18 17 16 15
GND

AVCC

GND

AVCC
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1

C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
AREF

AREF
ATmega328p ATmega328p
GND

GND
VCC

VCC
RES

RES
D0
D1
D2
D3
D4

D5
D6
D7
B0

D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2

X1
X2
1 2 3 4 5 6 7 8 9 10 11 12 13 14 1 2 3 4 5 6 7 8 9 10 11 12 13 14

16MHz 16MHz

100n 100n
Figure 3.
22p 22p 22p 22p
140245 - 13
An SPI connection between
two microcontrollers.

hardware. Here the main purpose of the exercise is no chip select line, but the Reset line has the
is to illustrate the transmission protocol. same effect because programming takes place
As previously with the 4094 shift register, a third with the Reset line pulled low. Now we want to
line is involved here—in this case the chip select use these lines exactly as intended. This has the
line /CS. The slash (/) means that the signal on advantage that we can use the hardware SPI unit
this line is active Low. The chip select line allows of the microcontroller, if it has one. With hard-
you to connect several slave devices to a single ware SPI we do not have use program code to
master. In that case they share the data and clock put each bit individually on the data line as in the
lines, but each one has its own chip select line. previous examples, and everything is a lot faster.
When that line is low, the corresponding slave However, we still need a chip select line, and in
knows that it is selected. There’s also another this case we use the B2 line for this purpose.
benefit from using a chip select line. If there is The master uses the MOSI line as the output
any delay in enabling the slave, there may be and generates the clock and chip select signals
some confusion about which bits have already (Listing 3). The process is slowed down a bit by
been transferred. However, if the slave waits until three 1-millisecond delays so that all the signals
it sees a falling edge on its CS input (high to low can easily be seen on the oscilloscope. Besides,
signal transition), it knows that the transfer is we don’t want to make things too difficult for the
starting. And if a noise pulse is read as a clock slave. If you wish, you can test the boundaries
signal, the rest of the data for that transfer is by reducing the delays until transmission errors
trash, but on the next access everything is again start to occur.
as it should be. The three lines are inputs for the slave device
(Listing 4). It constantly waits for specific signal
The ATmega328 also uses the SPI bus for pro- edges on the /CS and SCK lines and then reads
gram download from an external programming in a bit from the MOSI line. Since everything is
device. The following lines are therefore avail- handled by software here, the code must wait for
able on the six-pin programming connector on each edge in a Do loop. This takes a bit of time,
the Arduino board and on the Elektor Extension so data transmission must be slower than with a
shield (ICSP in Figure 3): the clock line Serial hardware SPI implementation. The received data
Clock (SCK) on B5, the write data line Master is shown on the display and on the terminal emu-
Out Slave In (MOSI) on B3, and the read data lator. When you turn the potentiometer on the
line Master In Slave Out (MISO) on B4. There master board, the change is visible on the slave.

100
www.elektor-magazine.com | October 2014 | 35

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

SPI EEPROM 25LC512 realm, but SPI types are generally preferred in
There is a wide range of ICs available with an the professional realm because they offer espe-
SPI interface, including A/D converters, memory cially high operational reliability.
devices and display drivers. Serial EEPROMs from Figure 4 shows the connections to the Uno board.
Microchip and other companies are available at The pins of the original SPI interface (2x3 pin
low cost and are widely used. The 25LC512 (not header) are again used here. That makes it easy
to be confused with the 24C512, which has a I²C to build a convenient plug-in memory module
bus interface) has a capacity of 64 KB, and it is a by fitting the IC in a socket soldered to a small
good solution when the 1-kilobyte capacity of the 6-pin socket header. You only have to connect
ATmega328’s internal EEPROM is not sufficient. one additional line. This is the chip select line,
I²C EEPROMs are more widely used in the hobby which is again assigned to B2 because the Reset
line present on the connector cannot be used for
this purpose.
8 7 6 5
Here there are two data lines. MOSI (Master Out

HOLD

SI
VCC

SCK
Slave In) is the data output line and is connected
25LC512
to the Serial Input (SI) pin of the EEPROM, while

GND
WP
SO
CS

MISO (Master In Slave Out) is used to read data


1 2 3 4
from the Serial Output (SO) pin. The microcon-
troller is always the master, and it generates the
clock on the SCK line. To go with this exercise, we
MISO 1 2 VCC have written a subroutine (subroutines are called
SCK 3 4 MOSI
RESET 5 6 GND
“Sub” in Bascom; see the inset) that transfers
+5V data in both directions in a single go (Listing 5).
ICSP
Before the subroutine is called, the data to be
sent must be placed in the global variable Dout,
28 27 26 25 24 23 22 21 20 19 18 17 16 15 and after the call the received data is located in
the variable Din. Of course there are situations
GND

AVCC
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
AREF

ATmega328p in which data is only written, but in that case


zero bits are usually sent in the other direction.
GND
VCC
RES
D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2

1 2 3 4 5 6 7 8 9 10 11 12 13 14
The relatively complex data sheet for the 25LC512
tells you what has to be sent to the device, as well
16MHz
as when and how. After the chip select line has
100n been pulled low, the memory chip first receives a
Figure 4. 22p 22p simple byte command that specifies what action
140245 - 14
Connecting a serial EEPROM. is to be performed. To read data from the mem-
ory, you have to send a ‘3’ command followed
by two address bytes forming the high-byte and
Listing 5. Reading and writing data over MOSI and MISO.
low-byte portions of the address. After that as
Sub Spioutin many data bytes as desired can be read out with
Din = 0 automatic address incrementing (see Listing 6).
For N = 0 To 7 The program displays the sequential addresses
Shift Din , Left and the data bytes that are read out. A brand-new
Din = Din + Miso or fully erased EEPROM always delivers only the
If Dout.7 = 1 Then Mosi = 1 Else Mosi = 0 value 255. Now let’s try to program some data.
Waitus 3 For that we use the byte command ‘2’. However,
Sck = 1
a bit of preparation is necessary first. Writing
Waitus 2
must be enabled by sending the command ‘6’
Sck = 0
(Listing 7). To check whether writing is enabled
Waitus 2
you can read the EEPROM status register, which
Shift Dout , Left
requires sending the command ‘5’. Each action
Next N
is only effective if you pull /CS low at the start
End Sub
and then return it to the high level at the end.

101
36 | October 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

Listing 6. EEPROM readout (excerpt). Subroutines


Cs = 0 Subroutines are called “Sub” in Bascom, and they are used to allow
Dout = 3 'read
a block of code to be called repeatedly from different locations in a
Spioutin
Dout = 0 'A8...A15 program. To make this possible, each subroutine must be declared at
Spioutin the start of the program. This way the name of the subroutine is known
Dout = 0 'A0...A7 to the compiler, so the it can be called using this name in the same way
Spioutin as Bascom functions.
I = 0
Do
Declare Sub Spioutin()
Locate 1 , 1
Lcd I …
Print I; Dout = 6
Print " "; Spioutin
I = I + 1 …
Spioutin
Locate 2 , 1
Lcd Din
Print Din Sub Spioutin
Waitms 200 Din = 0
Loop …
Shift Dout , Left
End Sub
If the value in the status register is 2, the IC is
enabled for write operations. Complicated? Yes,
You always have to be very careful with the variables used by a
but that makes it especially foolproof.
subroutine. In the case of the Spioutin subroutine, all of the variables
Now we are allowed to write data to the mem-
ory, but even then there’s something we have it uses are “global” variables, which are dimensioned at the start of the
to consider. The memory space is divided into main routine and are therefore valid in the entire program. However,
pages, which in the case of the 25LC512 have you could do things differently and transfer the data to the subroutine
a size of 128 bytes. Each transfer is limited to when it is called:
a maximum of 128 bytes of data, or as many
bytes as it takes to reach the next page bound- Declare Sub Spioutin (Byteout as Byte)
ary. After this you switch /CS high and then give
the EEPROM enough time to actually store the
In that case the variable Byteout would not be valid globally, but only
data. According to the data sheet, 5 ms is enough
within the subroutine. The subroutine call would then take the form:

Listing 7. Enabling write access Spioutin 6


(excerpt).
Cs = 0 This saves one line compared to the previously shown call.
Dout = 6 'write enable
You can also transfer a group of several variables to a subroutine in a
Spioutin
subroutine call, as can be seen from the example of the Bascom Spiout
Cs = 1
Waitms 20 subroutine:
Cs = 0
Dout = 5 'read status Spiout Dout , 1
Spioutin
Spioutin
For novice programmers, it’s generally safer to use only global
Cs = 1
variables in your own subroutines. For advanced programmers, on
Locate 1 , 1 'status
Lcd Din the other hand, selecting the optimal form of data transfer is a major
Print Din consideration.

102
www.elektor-magazine.com | October 2014 | 37

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Listing 8. Using the software SPI (excerpt).


Config Spi = Soft , Din = Pinb.4 , Dout = Portb.3 , Dout = 0 'A0...A7
Ss = None , Clock = Portb.5 , Mode = 0 Spiout Dout , 1
Spiinit I = 0
Do
Cs Alias Portb.2 Locate 1 , 1
Ddrb.2 = 1 Lcd I
Cs = 1 Lcd " "
Spiin Din , 1
Cs = 0 Locate 2 , 1
Dout = 4 'write disable Lcd Din
Spiout Dout , 1 Lcd " "
Cs = 1 Print I ;
Waitms 1 Print " ";
Cs = 0 Print Din
Dout = 3 'read Waitms 200
Spiout Dout , 1 I = I + 1
Dout = 0 'A8...A15 If I >= 65535 Then Exit Do
Spiout Dout , 1 Loop

time for storing the data. If you exceed the page data is read back, that’s exactly what you see.
boundary (I tried it), the result is chaos. Then As usual, the entire program code (UNO_spiEE1.
the data you find in memory is totally different bas) can be downloaded from the Elektor website
from what you wanted to write to memory. For [1]. It performs the following actions in sequence:
this reason, the example program carefully obeys
the rules and writes 128 bytes to the first page • Command 6, write enable
from address 0 to address 127, with the data val- • Command 5, read status register; display for
ues in ascending order from 0 to 127. When the 1 second

Listing 9. Data storage in the timer interrupt routine (excerpt).


Tim0_isr: Dout = 3
'4000 µs Addr = High(seconds)
Timer0 = 6 Dout = Addr 'A8...A15
Ticks = Ticks + 1 Spiout Dout , 1
If Ticks = 250 Then Addr = Low(seconds)
Ticks = 0 Dout = Addr 'A0...A7
U = Getadc(4) Spiout Dout , 1
U = U / 4 End If
Addr = Seconds Dout = U
Addr = Addr And 127 Spiout Dout , 1
If Addr = 0 Then 'start of page Addr = Seconds
Cs = 0 Addr = Addr And 127
Dout = 6 'write enable If Addr = 127 Then 'End of page
Spiout Dout , 1 Cs = 1
Cs = 1 End If
Waitus 100 Print Seconds
Cs = 0 Seconds = Seconds + 1
Dout = 2 'write If Seconds = 0 Then Seconds = 65535
Spiout Dout , 1 End If
Waitus 100 Return
Cs = 0

103
38 | October 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

• Command 2, write 128 bytes starting at fer a lot of data during a single active chip select
address 0 phase. Consequently, this line (on port pin B2)
• Command 3, read memory starting at will still be operated “manually”. The Mode = 0
address 0; endless loop setting is also important, because there are four
different SPI modes.
Data logger The program excerpt in Listing 8 shows how the
One practical application for the 64-KB memory software SPI is used to read data from the serial
is a data logger. The objective here is to acquire EEPROM. The instruction Spiout Dout , 1 sends
measurement data from the ADC4 analog input exactly one byte, which is transferred in the vari-
once per second and store the data. The memory able Dout. In the other direction, the instruction
will be full in approximately 18 hours. Spiin Din , 1 reads one byte, which is then
available in the variable Din. The entire program
You don’t always have to program everything reads all the data from the EEPROM and shows
yourself, since Bascom has a lot of ready-made the contents on the display and on the terminal
functions for many situations. In this case you emulator screen.
have the option of configuring an SPI interface as As usual, the entire program code (UNO_spiLog-
a software interface using any desired port pins or ger.bas) can be downloaded from the Elektor
as a hardware interface using the microcontroller website [1]. It is too large to be listed fully here.
pins designated for this purpose. The hardware Pressing S1 starts a measurement run. It can be
SPI is especially fast and is commonly used for stopped at any time by pressing S2, after which
tasks such as driving graphical displays. However, the stored data can be read out.
this involves a whole lot of parameters that must
be configured for each specific application, which A timer interrupt routine (excerpt in Listing 9)
requires a detailed study of the ATmega328 data is used to control the timing during data acqui-
sheet. Things are a bit easier with the software sition. The voltage on ADC4 is measured and
SPI function, and it provides a reasonably high stored once per second. The 128-byte block size
transmission rate. Although writing your own SPI of the EEPROM is taken into account. At the start
procedure from the ground up is not a bad idea of each block, a write access is started and the
because it allows you to implement the timing current address is transferred, followed by 128
diagrams in the data sheets very clearly, the bytes of data. At the end of the block, the /CS
ready-made software SPI is more convenient and line is pulled high to allow the EEPROM to store
faster, which is why we use it here. the entire block. Since the /CS line is connected
The interface configuration specifies which lines to port pin PB2, LED2 on the shield is lit when the
are to be used. For Din, Dout and Clock we use line is high. The LED therefore flashes each time
the familiar MISO, MOSI and SCK lines, which a block of data has been transferred to memory.
are already available on the ICSP connector. The (140245-I)
SS line corresponds to the /CS line. In this case
Web Link
this line should not be operated automatically by
Bascom because it is usually necessary to trans- [1] www.elektor-magazine.com/140245

Tip for using the Arduino programmer in Bascom


Many readers who are using the original Arduino boot loader have encountered the following problem: if a program
performs serial output, the Arduino programmer in Bascom does not work properly the next time and hangs. Some readers
have discovered that this problem can be resolved by using the Arduino IDE before using the programmer again. Simply
transferring the Blink program, for example, is sufficient.
However, there’s an easier solution. After you launch the programmer in Bascom, briefly press the Reset button on the Uno
board three times (or more) at roughly 1-second intervals. After this the programming function will work again, even when
the previous program included a Print output. This has been discussed intensively in various topics on the Elektor forum
(now at forum.elektor.com).
If you use the MCS boot loader on the Uno board, this problem does not occur. Another alternative is to use an external
programmer.

104
www.elektor-magazine.com | October 2014 | 39

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Microcontroller
BootCamp (7)
The I²C bus
By Burkhard Kainka If you are running short of I/O lines on an Arduino Uno board, a remedy is
(Germany)
available. The I²C bus needs only two port pins and can address up to 127
external ICs. There are countless devices available with I²C interfaces, including
simple port expanders, EEPROMs and a wide variety of sensors. In the final
instalment of our Bascom course series, we show you how the I²C bus works. As
usual, the main focus is on interesting demo applications.

The Inter-IC bus or I²C bus (barring code, also The I²C bus can work with 5 V microcontrollers
sloppily written as I2C) is a two-wire data bus and ICs as well as 3.3 V devices. You can even
consisting of a data line and a clock line, origi- connect both types to the same bus. The two
nally developed by Philips (not: Phillips) for con- pull-up resistors, which typically have a value of
sumer electronics applications. Most television 2.2 kΩ, hold the bus lines at 3.3 V or 5 V (logic
sets or video recorders have a central processor High level) when the lines are not pulled low by
that controls a large number of modules. With a any of the pull-down transistors in the devices
data bus consisting of just two lines, connecting connected to the bus. Any 5 V devices on the
all these modules to the processor is easy. The bus also see 3.3 V as a High level because it is
processor is the bus master, as with the SPI bus, significantly higher than 2.5 V (half of the supply
and the peripheral devices are the slaves. A par- voltage), and of course 0 V is logic Low in any
ticular feature of the I²C bus is that every slave system. This means that you can easily connect
device has a 7-bit address. That allows a large the Arduino Uno board to a 3.3 V slave device.
number of ICs to be connected to the bus with- That’s handy because many recent ICs are only
out interfering with each other. Along with RAMs, designed to operate at 3.3 V.
EEPROMs, port expanders, real-time clocks, A/D The ATmega328 on the Uno board has an inte-
and D/A converters, there are a large number grated hardware I²C interface connected to pins
of special-purpose I²C devices such as display PC4 and PC5. However, Bascom also has spe-
drivers, PLL ICs and many others. An excellent cial commands that can be used to implement
reference book on I2C is available from Elektor, a software I²C interface using any desired port
see Further Reading [a]. pins, and of course you can also write your own
functions to set the lines High or Low using indi-
Data transfer and addressing vidual code lines. Here we only use the Bascom
The I²C bus consists of a serial data line (SDA) software I²C interface, but with the same port
and a clock line (SCL). One bit per clock pulse pins as used by the hardware I²C interface inte-
(as in a shift register) is transferred on the data grated in the microcontroller.
line. Usually the address bits are sent first, fol- These port pins are also used on the Elektor
lowed by the data bits. Each line has a pull-up Extension shield [1] for the Arduino Uno. There
resistor, and each line can be pulled low by any they are routed to the EEC/Gnublin connector K2,
device on the bus. Figure 1 shows the basic which can be used to connect Gnublin modules
bus architecture. The master generates the clock with an I²C interface over a flat cable, such as a
signal. The data can come from the master or module with eight relays [2]. The bus lines also
from the slave. have 330 Ω series resistors, which can be omit-

105
34 | November 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

ted if desired. However, they provide protection by the addressed slave. Then the master sends
against false signals resulting from reflections on the data byte, which is also acknowledged. The
long bus lines, and they can help avoid problems connection can be ended now by generating the
that may occur on buses with devices operating stop condition, or another byte can be sent to
at different supply voltages. For example, the the same slave.
input currents of 3.3 V peripheral devices could
exceed the maximum rated value if one of the I²C bus address with data direction
bus lines is accidentally set to a 5 V high level A6 A5 A4 A3 A2 A1 A0 R/W
for a prolonged period. The series resistors limit
the input current to a safe level. If the master want to read data from a slave, the
The I²C bus protocol defines several specific address must be sent with the data direction bit
states that allow every device on the bus to detect set to 1. The master then generates eight clock
the start and end of a transfer: pulses and receives eight data bits. If reception is
confirmed by an acknowledgement on the ninth
• Quiescent state: SDA and SCL are high and clock pulse, it can receive another data byte. At
therefore inactive. The Bascom instruction the end the master terminate the transfer with
I2cinit puts both lines in the quiescent a stop condition when no acknowledgement is
state but without internal pull-up resistors, received.
since they are located externally. Every I²C device has a fixed address. Part of the
• Start condition SDA is pulled low by the address is specific to the device type, and the rest
master while SCL remains high (Bascom can be configured by the user with the address
instruction: I2cstart). lines A0, A1, etc. fed out from the device. These
• Stop condition: SDA changes from low address lines are tied high or low in the circuit
to high while SCL remains high (Bascom to set the address bits. If the device has three
instruction: I2cstop). address lines fed out, such as the PCF8574 port
• Data transfer: The current sender places expander, up to eight different addresses can be
eight data bits on the data line SDA, which set. This means that up to eight devices of the Figure 1.
are shifted out by clock pulses on the clock same type can be connected to one bus. This I²C bus connections
line SCL generated by the master. The trans- port expander provides eight digital outputs, and between master and slave
fer starts with the most significant bit (Bas- the signal levels on the outputs are determined devices.
com instruction: I2cwbyte Data).
• Acknowledge (Ack): The currently addressed
receiver acknowledges reception of a byte +3V3/+5V
by holding the SDA line low until the master ATmega328
2k2

2k2

has generated a new clock pulse on the SCL Master, VDD = 5V

line. This acknowledgement also means that PC4 SDA


330R
another byte is expected to be received. If
the device wishes to end the transfer, it must PC5 SCL
330R
indicate this by omitting the acknowledge-
ment (Nack).
The transfer is terminated by the stop con-
dition (Bascom instruction: i2crbyte Data,
Ack or i2crbyte Data, Nack). Slave, VDD = 3V3/5V

SDA
Addresses are transferred and acknowledged in
the same way as data. In the simplest case of a
SCL
data transfer from the master to a slave, such
as an output port, the following procedure is
used. The master generates the start condition
and then transfers the address of the port IC
in bits 1 to 7 and the desired direction of the
140293 - 11
data transfer in bit 0 – in this case, 0 for writ-
ing to the device. The address is acknowledged

106
www.elektor-magazine.com | November 2014 | 35

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Many ICs allows the user to set the last three


Listing 1.
address bits. The PCF8583 real-time clock IC has
Polling for active I²C addresses.
the same base address as a RAM because it also
'------------------------------------ contains a RAM. If you want to use a RAM and
'UNO_I2C1.BAS Test for valid Adresses
a real-time clock on the same bus, you have to
'------------------------------------
give them different addresses.
$regfile = "m328pdef.dat"
Incidentally, there are two different notations
$crystal = 16000000
for the address, which sometimes cause confu-
$baud = 9600
sion and laborious troubleshooting. Some data
sheets only give the 7-bit address without the
Dim Addr As Byte
read/write bit. In that notation the base address
...
Config Scl = Portc.5 of the PCF8574 would be 20hex (decimal 32) By
Config Sda = Portc.4 contrast, in Bascom this IC has a write address
I2cinit of 64 (40hex = &H40) and a read address of 65
(&H41).
For Addr = 2 To 254 Step 2
I2cstart To learn the addresses of the devices connected
I2cwbyte Addr to the bus, you can use the small Bascom pro-
If Err = 0 Then gram shown in Listing 1 (downloadable from
Print Addr [3]). It polls every possible bus address to see
Locate 2 , 1 whether a device responds. After a device address
Lcd Addr is output, the Bascom system variable ERR (which
Waitms 1000 does not have to be declared with Dim because
End If Bascom has already done this for you) is set to
I2cstop 1 if no acknowledgement is received or to 0 if
Next Addr an Ack signal is received. The latter case means
End that the address is valid. All even addresses from
2 to 254 are tested, since the odd addresses are
the corresponding read addresses of the same
by the eight bits in the data byte sent to the IC. devices. For the circuit shown in Figure 2, the
The base address of the port expander is 40hex program reports the addresses 64, 144, 160 and
(decimal 64). The base addresses of some typical 162 just as expected.
first-generation Philips I²C devices are: There’s another special feature of the I²C bus
protocol: every device on the bus can halt the
• PCF8591 A/D converter: 90hex (decimal 144) master for a while if it needs a bit more time. To
• RAMs and EEPROMs: A0hex (decimal 160) do so it pulls the clock line Low, which forces the
• PCF8583 real-time clock: A0hex (decimal master to wait until the line is released again.
160) Bascom follows this convention faithfully. How-

VCC

Master
2k2

2k2

SDA

SCL

SCL SDA SCL SDA SCL SDA SCL SDA


A0 A0 A0 A0
A1 PCF8574 A1 PCF8591 A1 24C512 A1 PCF8583
A2 Adr. 64 A2 Adr. 144 A2 Adr. 160 A2 Adr. 162
Figure 2.
140293 - 12
A master and four slaves.

107
36 | November 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

ever, this means that a program that uses the


I²C bus will hang if no pull-up resistors are con-
nected. From other projects you may be used to +5V/+3V3

the idea that you can sometimes test software


without connecting the associated hardware. As 16 15 14 13 12 11 10 9
a result, you might find yourself staring at an 2k2

SCL

P7
P6
P5
P4
VCC
SDA

Int
oscilloscope while checking out your software to Device
2k2 PCF8574 under
see whether there are any signals at all on the
Test

GND
SCL and SDA lines, while the cable to the Gnub-

A0
A1
A2
P0
P1
P2
P3
1 2 3 4 5 6 7 8
lin board is not yet connected. What you have
overlooked is that the I²C bus pull-up resistors +5V

330R
330R
are on the Gnublin board. Since no pull-ups are
present on the host board, everything remains
in suspended animation and there are no signals
28 27 26 25 24 23 22 21 20 19 18 17 16 15
on the I²C bus.

GND

AVCC
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
AREF
The PCF8574 port expander ATmega328p

The PCF8574 is a port expander IC with eight

GND
VCC
RES
D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2
bidirectional port pins. It does not have a data 1 2 3 4 5 6 7 8 9 10 11 12 13 14

direction control function. Instead, the port pins


have internal pull-up resistors that cause a high 16MHz
level to be present in the quiescent state. This
means that after booting you will initially read 100n

the port status 255 (binary 11111111). You will 22p 22p
140293 - 13
only see low values (logic 0) if the port pins are
actively pulled to ground by an external device.
It is possible to use some of the port pins as may be necessary, which means you will need Figure 3.
outputs and the others as inputs. This requires different test software. Using the PCF8574 port
first configuring all of the input pins in the high expander.
state, the same as the output pins. PCA9555 16-bit I/O port
Figure 3 shows the bus connections and a poten- Sometimes eight more lines are not enough. The
tial application of the port expander as a digital Gnublin port expander module [2] provides 16
tester. The port expander can be powered from I/O lines using an NXP PCA9555 IC. The board
3.3 V or 5 V according to the operating voltage can be plugged directly into the EEC connector
of the item under test. Any desired digital circuit on the Elektor Extension shield. There is also a
with four inputs can be driven using the output Gnublin relay board that uses the same IC.
port pins P0 to P3. For example, you could apply NXP is the successor to Philips, and the PCA9555
an incrementing digital value to these four pins to is the rightful successor to the PCF8574. That’s
obtain all possible combinations of signal levels why the two devices have the same bus address:
on the circuit inputs. Cables and connectors can 64 (&H40). This sort of address recycling makes
also be tested the same way. Every open circuit sense because the address space is limited. In
and short circuit can be detected. any case, why would you need a PCF8574 when
Listing 2 shows an example of how to use a you have a PCA9555? Along with twice as many
mixed set of inputs and outputs. Here pins P0 I/O pins, the new IC has additional functions
to P3 output a continuously incrementing digital such as data direction control and inversion of
value. Pins P4 to P7 are used as inputs and must the input data.
therefore be set high in the write operation (Or Figure 4 shows how the IC can be connected to
&B11110000) The IC is addressed twice: first in the Elektor Extension shield using the EEC con-
the write direction (address 64) and then in the nector. The I²C bus lines and supply voltage lines
read direction (address 65). Incrementing the are connected using a flat cable. The two pull-up
value on the four outputs is the simplest possi- resistors on the Gnublin board are connected to
ble type of test stimulus. Depending on the item the bus lines by a pair of jumpers. These jump-
under test, a completely different test sequence ers must be fitted if only one board is connected.

108
www.elektor-magazine.com | November 2014 | 37

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Listing 2. Accessing the PCF8574 ports.


'------------------------------------ Print " ";
'UNO_I2C2.BAS input/output PCF8574 Locate 2 , 1
'------------------------------------ Lcd N
$regfile = "m328pdef.dat" Lcd " "
$crystal = 16000000
$baud = 9600 I2cstart
I2cwbyte 65 'read
Dim N As Byte I2crbyte D , Nack
Dim D As Byte I2cstop
... Shift D , Right , 4
Do Print D
For N = 0 To 15 Locate 2 , 5
I2cstart Lcd D
I2cwbyte 64 'write Lcd " "
D = N Or &B11110000 Waitms 100
I2cwbyte D Next N
I2cstop Loop
Print N;

If you use several boards, perhaps connected That yields a bus address of 64. A total of eight
using the Gnublin distributor board [2], make boards can be connected, with addresses from
sure that the pull-up resistors are only enabled 64 to 72. With 16 I/O pins per board, that gives
on one board. It is possible to use several port you a grand total of 128 I/O lines.
expander boards because each board has jump- Listing 3 shows an application for the PCA9555,
ers for configuring address lines A0 to A2. In the which can also be used for testing other circuits.
default state, all three lines are tied to ground. As in the previous example, the port pins are

Listing 3. Using the PCA9555 port expander.


'------------------------------------ I2cwbyte N
'UNO_LCD1.BAS input/output PCA9555 I2cstop
'------------------------------------ Print N;
$regfile = "m328pdef.dat" Print " ";
$crystal = 16000000 Locate 2 , 1
$baud = 9600 Lcd N
Lcd " "
Dim N As Byte
Dim D As Byte I2cstart
... I2cwbyte 64 'write
I2cstart I2cwbyte 1
I2cwbyte 64 'Gnublin port expander I2cstart
I2cwbyte 6 I2cwbyte 65 'read
I2cwbyte 0 'Port 0 output I2crbyte D , Nack
I2cwbyte 255 'Port 1 input I2cstop
I2cstop Print D
Locate 2 , 5
Do Lcd D
For N = 0 To 255 Lcd " "
I2cstart Waitms 100
I2cwbyte 64 'write Next N
I2cwbyte 2 Loop

109
38 | November 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

divided up with half of them used for outputs


+3V3
and the other half used for inputs. Since things
are a bit more complicated here, a command
byte has to be sent after each address [4]. The
command selects a register address in the IC.

2k2

2k2
After that you can send or receive one or two 24
VDD
bytes of data. For example, if you want to con- 2 1 I/O0.0
4
5
figure port 0 (with eight pins) and port 1 (with I/O0.1
SDA 23 6
SDA I/O0.2
the other eight pins), you first send the com- 22 7
SCL I/O0.3

PORT 0
SCL
mand ‘6’ after the address and then write two I/O0.4
8
9
data bytes, which are placed in registers 6 and 7. I/O0.5
1 10
INT I/O0.6
Zero bits in these bytes mean that you want to 3V3 GND 11
I/O0.7
14 13
configure the corresponding pins as outputs. One EEC PCA9555D
13
bits stand for inputs. In our example, all pins of I/O1.0
14
I/O1.1
port 0 are configured as outputs and all pins of 15
I/O1.2
port 1 are configured as inputs. Incidentally, pins I/O1.3
16

PORT 1
21 17
configured as inputs have integrated high-imped- 2
A0 I/O1.4
18
A1 I/O1.5
ance pull-up resistors (approximately 100 kΩ), 3 19
A2 I/O1.6
so open inputs are read as logic 1. You can use I/O1.7
20
VSS
the following command byte values: 12

Figure 4.
0 Input Port 0 140293 - 14
The PCA9555 on the Gnublin
1 Input Port 1 board.
2 Output Port 0
3 Output Port 1 for each command. In order to read a port, the
4 Polarity Inversion Port 0 IC must also be addressed again with the read
5 Polarity Inversion Port 1 bit set (address 65). If you examine the code
6 Configuration Port 0 closely, you may wonder why there is no I2cstop
7 Configuration Port 1 instruction. That’s because the code implements a
‘repeated start’ without a previous stop condition,
The commands 2 (Output Port 0) and 1 (Input since the two accesses always belong together:
Port 1) are used iteratively in the data loop of the writing the command to select the register to be
sample program. The IC must be addressed anew read and reading the register contents.

Other interesting I²C components


Anyone who reads Elektor regularly is always running into interesting ICs with an I²C interface.
They often form the inspiration for new projects. Some particularly significant types are:

• I²C EEPROMs up to 64 KB (for example, the 24C512). These can be used to build data loggers
and lots of other things.
• The CY27EE16 is a crystal clock generator that can be programmed over the I²C bus. It is
used in the Elektor Software Defined Radio project. Software control with a microcontroller
opens the door to new possibilities.
• The SI4735 is a complete AM/FM receiver and has already been used in several Elektor
projects along with Bascom. Any desired frequency can be set using just a few I²C commands.
• High-resolution A/D and D/A converters often have I²C ports. One example is the ADS1115
16-bit A/D converter recently described in Elektor.
If you want to delve deeper into this subject, you can even build your own I²C bus IC. A Bascom
library for programming I²C slave devices is available for this purpose. That is a bit more
difficult than programming a bus master because the slave device must be able to handle the
bus speed set by the master. The Mastering the I2C Bus book has all the details.

110
www.elektor-magazine.com | November 2014 | 39

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Analog I/O with the PCF8591


The PCF8591 contains an 8-bit A/D converter with
four inputs along with an 8-bit D/A converter in
+5V the same package. You probably won’t need the
A/D converter by itself because the Arduino Uno
16 15 14 13 12 11 10 9
already has enough analog inputs and higher
2k2
resolution for A/D conversion. However, a real

OSC

SCL
VCC

SDA
AGND
Ref
A0

Ext
A/D converter can come in handy. Unlike a PWM
PCF8591
2k2 output, it delivers a true DC voltage. You can use
DUT

GND
this to build a simple diode tester that measures
Ai0
Ai1
Ai2
Ai3
A0
A1
A2
1 2 3 4 5 6 7 8 the forward voltage at a defined current level (see
+5V Figure 5). The circuit operates at 5 V so that it
330R
330R

can also be used to measure the relatively high


forward voltage of LEDs.
The IC has a control register that must be writ-

1k
28 27 26 25 24 23 22 21 20 19 18 17 16 15
ten right after the bus address is sent. A control
GND

AVCC
C5
C4
C3
C2
C1
C0

B5
B4
B3
B2
B1
AREF

byte value of 64 enables the D/A converter and


ATmega328p selects input channel 0. The following byte is put
into the D/A register and results in an output
GND
VCC
RES
D0
D1
D2
D3
D4

D5
D6
D7
B0
X1
X2

1 2 3 4 5 6 7 8 9 10 11 12 13 14 voltage in the range of 0 to 5 V, corresponding


to a data range of 0 to 255. With this 8-bit res-
16MHz
olution, the output voltage increment is approx-
imately 20 mV. The demo program in Listing 4
100n generates a rising voltage ramp and measures
22p 22p the voltage across the 1 kΩ sense resistor at the
140293 - 15
same time. The PCF8591 has to be addressed
again in the read direction (address 145) to read
the measured voltage. The read byte value rep-

Figure 5.
Listing 4. A diode tester using the PCF8591.
A diode tester using the
PCF8591. '------------------------------------- I2cstart
'UNO_I2C4.BAS AD/DA PCF8591 I2cwbyte 145 'read
'------------------------------------- I2crbyte D , Nack 'Ain0
$regfile = "m328pdef.dat" I2cstop
$crystal = 16000000 Print D
$baud = 9600 Locate 2 , 5
Lcd D
Dim N As Byte Lcd " "
Dim D As Byte Waitms 100
Dim U As Word N = N + 1
... If D >= 50 Then Exit Do
N = 0 Loop
Do Cls
I2cstart Locate 1 , 1
I2cwbyte 144 'write Lcd " 1 mA"
I2cwbyte 64 'DA enable U = N - D
I2cwbyte N U = U * 20
Print N; Locate 2 , 2
Print " "; Lcd U
Locate 2 , 1 Lcd " mV"
Lcd N End
Lcd " "

111
40 | November 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Microcontroller Bootcamp

resents the voltage on input Ai0. A reading of 50 elektor-labs.com and http://forum.elektor.com


indicates a voltage of 1 V, which corresponds to (Microcontrollers section). Relatively small proj-
a diode current of 1 mA. At this point the ramp ects or applications still in the development stage
is stopped. Now the forward voltage of the diode are especially welcome.
can be calculated from the difference between (140293-I)
the output voltage and the input voltage. It is
displayed in millivolts. With a sample blue-green
Web Links
LED, the following results were displayed at the
end of the measurement cycle: [1] www.elektor-magazine.com/140009
[2] www.elektor.com/tools/gnublin
1 mA [3] www.elektor-magazine.com/140293
2920 mV
[4] www.nxp.com/documents/data_sheet/
PCA9555.pdf
Future prospects
This is the last installment of our Microcontroller
BootCamp series, but there will be other articles
Further Reading
on Bascom applications for the Arduino Uno and
the Elektor Extension shield from time to time. [a] Mastering the I2C Bus, Vincent Himpe,
We hope we have aroused your enthusiasm for Elektor International Media Publishers,
developing your own programs. If so, we encour- ISBN 978-0-905705-98-9.
age you to share the results of your efforts with Also available as an E-book.
other members of the Elektor community at www.
Advertisement

Create Complex Electronic Systems


in Minutes Using Flowcode 6
Design Simulate Download

Flowcode is one of the World’s most advanced


graphical programming languages for micro-
controllers (PIC, AVR, ARM and dsPIC/PIC24).
New in Version 6:
The great advantage of Flowcode is that it allows • Component Library Expansion;
those with little experience to create complex elec- • Improved Simulation;
tronic systems in minutes. Flowcode’s graphical • New Test Features;
development interface allows users to construct a • 3D Design Environment;
complete electronic system on-screen, develop a • Third Party Instrument Support;
program based on standard flow charts, simulate • Dashboard HMI Components;
the system and then produce hex code for PIC • And More!
AVR, ARM and dsPIC/PIC24 microcontrollers.

Further Information and Ordering at www.elektor.com/flowcode

112
www.elektor-magazine.com | November 2014 | 41

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Motion-Detector
Camera Trigger
using Arduino

A night light that flashes on


when someone walks past, an
IR-LED, a few resistors, a capacitor and an
Arduino with a bit of software: that’s all you need
to take pictures using motion detection.

By Rolf Blijleven I consider the Arduino to be very similar to Lego: siderable advantage of the Arduino, compared
(Netherlands) you can make all manner of things with it. This to other embedded platforms, is that there is a
is useful and instructive to do, and it results in tremendous wealth of firmware to be found, just
something useful. You can then use it for a while, free from the Internet.
and whenever you feel like it, you can take it After this, I wanted to trigger the remote control
apart again and use it to make something else. using a motion detector. There are many nice
A while ago, I made an infrared remote control for solutions to be found for this on the DIY market
my Nikon D80 using an Arduino. Not because such and on the internet, but these usually require
a remote control is that expensive, but because an AC power adapter. I didn’t want that, it had
making one yourself is much more fun and using to work without any wires. By chance, I spotted
an Arduino it offers many more possibilities. More- at the supermarket a night light powered from
over, it turned out to be child’s play: An IR-LED, batteries, with a motion sensor, for a couple of
a resistor and a piece of software that I found dollars (Figure 1). That won’t break the bank.
on the internet, nothing else is required. A con- It just went with the weekly groceries.

113
24 | April 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Motion-Detector Camera Trigger

Night light hacking


The first thing you do, naturally, is look what is
inside it. This tuned out to be much better than
expected. No difficult SMD parts or—worse—COBs,
but instead an IC with legs, normal resistors and
capacitors, a PIR-sensor and a photo diode.
The part number printed on the IC was TL0001.
A quick Internet search and sure enough there
appears to exist a datasheet [1]. In Chinese,
but that is not a problem: just copy the text and
paste into Google Translate. This results in an
horrendous translation but is still good enough
so that you can get the gist of it. There was even
Figure 1.
an Application Note in there, that although it was
Available from your Walmart
not exactly the same is my night light, it was
or discount store: a super
nevertheless very close. cheap night light with
The night light did three things that I didn’t want: motion detector.
it only operated in the dark; it gave a pulse that
was several minutes long, while I needed a much
shorter pulse and a turned on three bright LEDs
when you walked past.
The latter was easily solved. The three LEDs
shared one series resistor. I removed two and
replaced the series resistor with one that has a
higher value (2.2 kΩ, A in Figure 2), so that the
remaining LED would still switch on with each
trigger, but not as bright.
Then the inhibit-function during daylight. In the
example schematic (Figure 3), R3 is an LDR. This
I couldn’t find anywhere, but I did find a photo
diode, also a device that exhibits a lower resis-
tance as the amount of light on it increases. So
I replaced that with a reasonably large resistor
(220 kΩ, B in Figure 2). That worked too: Even Figure 2.
in bright light the lamp turned on when motion The same night light after a
was detected. few modifications.

Figure 3.
A sample schematic from
the datasheet for the
TL0001 made by the Chinese
company Treasure Link
Technology. Although it
looks very similar, it does
not correspond completely
with the actual circuit in the
night light.

114
www.elektor-magazine.com | April 2014 | 25

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

somewhat resulted in a modest improvement. The


gain stage comprises two steps. 1IN+, 1IN- and
1OUT in the IC are an opamp (see datasheet),
the gain of which is about equal to R7/R8. Using
1 MΩ/12 kΩ this became 84 (was 40 with the
original 2 MΩ/47 kΩ). The makes the PIR-sensor
not more sensitive, of course, but it does amplify
small signal more. A consequence was that larger
signals would hit the power supply rails. The sec-
ond stage is also an opamp with a gain equal to
R6/R5, originally 100, but with 15 kΩ for R6 this
became 67. This solved the clipping problem.
The result is that the sensor is able to detect
movement indoors over a somewhat larger dis-
tance than before, but that doesn’t mean much
Now the pulse duration. The light turns on for by itself. PIR-sensors are especially sensitive at
Figure 4.
The complete circuit with
about 5 seconds. That will be an RC-time con- seeing heat differentials. A cat walking past on
Arduino, IR LED and stant somewhere, but which R and which C? I had a frosty day is detected from many meters fur-
PIR-board (formerly a already observed that it was not possible to turn ther away compared to the same cat on a warm
night light). the light back on immediately after it had turned summer’s day.
off. So there had to be another RC-time constant The output of the IC is on pin 2, which is soldered
to suppress new triggers for a while (trigger-in- to a wide copper track. It is therefore very easy
hibit). Now I really had to resort to reading the to attach a wire to it. With another two wires for
datasheet. And sure, it was all there. Machine +5 V (after the switch) and ground the night light
translated from the Chinese: “Output delay time had become a PIR-board. Not bad for an invest-
Tx R9 and C7 by an external sizing, value Tx ≈ ment of € 2.65 and some time figuring it all out.
24576xR9C7; triggered by an external blocking I fully expect that in your part of the world the
time Ti R10 and C6 resizing is Ti ≈ 24xR10C6.” type of motion detector or night light that you
That’s clear, isn’t it? can buy will be entirely different. But the above
story has at least shown a method you can use
Time for some reverse engineering: not design- to figure out how it operates and adapt some of
ing a printed circuit board from a schematic, the features of the circuit to your needs.
but the other way around: drawing a schematic
based on the circuit board. This is a little easier Work horse Arduino
when you can see both sides of the circuit board It turned out that connecting the PIR-board to an
side by side. A photocopy of the copper side is analog input of the Arduino was more convenient
very helpful. than using a digital input. One digital output of
After a little drawing, calculating and soldering the Arduino is used for the IR-LED with a series
I had identified R9/C7 and R10/C6 and replaced resistor, which is used to operate the camera. The
them with ‘improved’ values. That’s what I three AA-batteries for the night light also serve
thought. However, it wasn’t right. At any rate, as the power supply for the Arduino. The circuit
the light had completely lost the plot. While I was is otherwise simplicity itself (see Figure 4).
checking everything again, my eye caught some The timing for the IR-pattern for the camera
text in the datasheet: “BISS0001 chip it is fully trigger is borrowed from [3] and [4]. Movement
compatible with”. And sure enough, the datasheet a few meters from the PIR-sensor generates a
for the BISS0001 had the correct formulas: Tx ≈ trigger for the camera, which, in turn, could also
24576xR10C6 and Ti ≈ 24xR9C7. In the Chinese be a few meters away from the IR LED. This also
datasheet R10 and C6 where swapped with R9 works through glass, so you can keep your cam-
and C7! With R10C6 = 1 kΩ x 100 nF and R9C7 = era inside and the sensor/remote control outside.
270 kΩ x 1 nF resulted in Tx ≈ 24 ms and Ti ≈ I have mounted the IR-LED on a piece of thick
0.5 s (C in Figure 2). Right on the money. C7 electrical wire, so that the LED can be bent into
could have remained unchanged. a different direction compared to the direction
An attempt to increase the gain of the PIR-sensor of the PIR sensor.

115
26 | April 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Motion-Detector Camera Trigger

My camera, a Nikon D80, turned out to have some if (val > 200 || timeCounter == quarter
unexpected characteristics. When you switch this ) {
camera into IR Remote mode it waits a while for timeCounter = 0;
an IR-command. If that does not happen it will
takePicture();
switch out of IR-mode by itself. Any command
delay(500);
after that interval is ignored. For my application
}
(nature photography) this was undesirable. The
waiting time can be adjusted in the camera up
to a maximum of 15 minutes. The source code for the firmware for this project
That is why the firmware will give the IR-com- is a free download from the Elektor website [5].
mand ‘stay awake’ if there has been no motion The binary file is only 4 KB, so with an Arduino
detected for 14 minutes. In this way you can with 32 KB flash memory there is plenty of spare
leave the camera for days, waiting for that one space for to add your won features. A trigger
rare animal to go by. based on sound would be another possibility.
This interval can also be made shorter. Without (130265)
the PIR-board you can then also use it to make
Internet Links
time-lapse movies of, for example, flowers that
grow and open. [1] www.treaslink.com/Upload-
Files/2010531152721141.pdf
To allow this interval to be changed in the code in [2] www.e-ele.net/DataSheet/BISS0001.pdf
a more obvious way, requires a little bit of com- [3] www.bigmike.it/ircontrol
putation. We are using Timer1, this is a 16-bit
[4] http://luckylarry.co.uk/arduino-projects/
timer, so counts from 0 to 65536. If we let the
arduino-ir-remote
timer start from a timerPreload of 3036 it will
count 65536 - 3036 = 62500 clocks and give an [5] www.elektor.com/130265
interrupt. The Duemillenove runs at 16 MHz; with
a prescaler at 1024 this becomes 15625 Hz, so
we will have a Timer1-interrupt exactly every
62500/15625 =4 seconds (ignoring any inac-
curacies of the clock). In the code this is imple-
mented as follows:

#define four_sec 1 Figure 5.


#define twelve_sec 3 * four_sec Arduino and PIR-board with
battery housing, mounted
#define minute 5 * twelve_sec
back-to-back on a piece
#define quarter 14 * minute
of L bracket.
This is a quarter of an hour that lasts only 14
minutes, because at 15 my camera would just
leave IR-mode. With timeCounter we keep
track of the time. In the interrupt service routine
we give the intial value timerPreload (=3036)
and incerment timeCounter. The counter value
times four is the time elapsed in seconds.

ISR(TIMER1_OVF_vect) {
TCNT1 = timerPreload;
timeCounter +=1;
}

In the main loop we take a picture when there is Figure 6.


a trigger from the PIR-sensor or when a quarter The entire circuit housed in
of an hour has gone by. a splash-proof enclosure.

116
www.elektor-magazine.com | April 2014 | 27

Personal Download for Petar Crnojevic | copyright Elektor


•Labs

Intel Galileo-Arduino
Engineering sample hits E-Labs desk
By Thijs Beckers (Elektor Labs)

One of the privileges of working at a


publishing house is that you get sneak
previews of things in manufacturers’
pipelines. Recently we were delighted
to have a look at the new Galileo-Ardui-
no. Here’s some intel on a new board.

The Intel Galileo is a co-production between The prominent Intel chip is flanked by two Micron
Ivrea, Italy-based Arduino and big-gun chipmaker MT41K128M8JP-125:G 1-GBit DDR3L memory
Intel Corporation. Arduino’s new Arduino Certi- chips. The ample amount of 0402-shaped capac-
fied family starts off with the Intel Galileo board itors and resistors are all accounted for in the
and is supposed to address beginners and next fairly large schematic circuit, which—as cus-
level developers. With a 400-MHz 32-bit Intel tomary with all Arduino boards—is available for
Pentium® instruction set architecture compatible downloading [1] and comprises a whopping 27
processor, the latter group seems to identify the pages! BTW, the 3.5-mm audio connector is not
target market better than the former. But let’s used for audio, but rather represents the legacy
have a quick look at the engineering sample on RS-232 interface.
our desk. After unpacking, reading the Quick Start Guide
and downloading the development tools from Intel
Looking at the type, appearance and sheer [2]—we used Intel Galileo Arduino SW v1.5.3 for
amount of electronic components, this Arduino Windows v07.5—we unzipped the software and
family member sure looks like the Big Daddy of copied it to the root of our hard drive, as sug-
them all. Compared to the Uno it plays in a far gested in said guide. Using a different location
higher league and even the Yún doesn’t seem to could result in errors due to path length prob-
come close. Besides the standard Arduino pin- lems. And it did after we tried to run it from a
header configuration, we see a lot of other I/O, different location.
like a JTAG interface, an ICSP header, RS-232, The power supply must be connected prior to
and a USB client as well as a USB host interface. the USB cable. Otherwise the board might get
And of course an RJ-45 network port. damaged. The included wall wart is rated at a
hefty 5 V, 1.5 amps, which suggests this Arduino
matriarch is quite power hungry. After the client
USB port on the Galileo is connected to your PC
[1] http://arduino.cc/en/ArduinoCertified/IntelGalileo
or Mac, the driver installation process begins. Fol-
[2] https://communities.intel.com/community/makers/software/drivers lowing the instructions from the Getting Started

117
64 | March 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Intel Galileo-Arduino

Guide ensures the correct installation of the driv-


ers. Now the Intel Galileo pops up as an extra
port in the computer management. We need to
remember the COM port number, as we’ll have
to enter it in the Arduino IDE.
Now we can run the Arduino IDE, load an Arduino
Sketch and start what we set out to accomplish
with this new Arduino Galileo board. The Getting
Started Guide starts off with the Blink sketch. Fol-
lowing this suggestion produces the well-known,
straightforward way to program an Arduino board.
First select the Board and Serial Port from the
Tools menu. Then, after hitting the Upload but-
ton, the little green LED marked GP (General
Purpose?) starts blinking every second. It’s not
too bright though, as it is only a 0603 shape LED,
but it suits its purpose. That was easy!
The Getting Started Guide suggests updating
the board’s firmware using the release-specific
firmware included in the IDE, which shouldn’t
take longer than 15 minutes. So make sure your
board is up to date before you start developing.
The Galileo is able to boot from an SD card. In the
short time available for this review we didn’t try
Download the free Galileo-Arduino
this, but we did try the ReadAnalogVoltage sketch,
Poster, exclusive for Elektor Post and
which seems to work well, faithfully returning the
Elektor Magazine readers, courtesy
measured voltage on analog input A0 via USB to
of Mouser & Elektor! Limited period:
the built-in Serial Monitor (available under the February 21 – March 5, 2014. Get it
Tools tab in Arduino IDE). at: www.elektor.com/galileo-arduino
Using Wi-Fi capabilities of the board mandates
booting from an SD card, as there is too little
storage available in the on-board SPI flash to
incorporate the Wi-Fi driver. Hence we didn’t
get to test that, but the Wi-Fi adapter socket on
the back of the board wasn’t populated anyway.
The Release Notes state that the Integrated Wi-Fi
functionality was validated with an Intel Centrino
Wireless-N 135 adapter—an optional module that
can be acquired separately.

Our final thoughts? It is natural for electronics


to evolve and become more sophisticated with
every new generation, but the Arduino Certified
Intel Galileo sure is a giant leap ahead of the
‘familiar’ Arduino products. Will it play as big a
role in Arduino’s (r)evolution as its namesake
Galileo Galilei did for the Scientific Revolution?
Who knows. Maybe it evolved past its current tar-
get audience and will prove to be too difficult for
the Arduino community? That’s something we’ll
probably find out over the course of this year,
when the board gets released officially.
(130449)

118
www.elektor-magazine.com | March 2014 | 65

Personal Download for Petar Crnojevic | copyright Elektor


•Labs

Arduino Yún
Bridging Two Worlds?

Source: www.arduino.cc

By Clemens Valens The Cloud is where you have to be today. However, to connect to the cloud you
(Elektor.Labs)
need an internet connection, preferably wireless. This is where the new Arduino
Yún board can help. Yún means cloud in Chinese and the board is equipped with a
Wi-Fi module to connect to it. But the Yún is more than Wi-Fi—it also runs Linux.
Arduino on Linux? Linux on Arduino? How does that work?

What’s on board? point (AP) and router platforms. The heart of this
Quite a lot, actually. Let’s start with what we are SoC is a 32-bit MIPS 24K processor, which goes
familiar with: the Arduino part. to show that you don’t always have to use ARM.
Like all Arduino boards the Yún is based on a micro- The SoC communicates with the Leonardo part
controller unit (MCU) from Atmel. In this case it is over a serial link.
an ATmega32u4 from the 8-bit AVR family. This The Atheros chip provides Wi-Fi connectivity, but
is the same MCU as the one on the Arduino Leon- it’s also connected to an Ethernet connector pro-
ardo board, and the Yún can actually be viewed as viding a wired network interface. Furthermore, it
a Leonardo with an on-board Linux co-processor has access to an AU6350 single chip integrated
a.k.a. Wi-Fi/Ethernet/USB/SD-card shield. USB2.0 hub and multimedia card reader controller
This complicated shield is built around an Ath- from Alcor Micro (mounted on the underside of
eros AR9331 chip (we have to trust the Arduino the Yún board—Figure 1). This chip offers the
documentation on this as there is no print on the Yún its USB host connector and micro SD-card
metal shield covering it). According to the data- slot. The AU6350 communicates over a USB con-
sheet of this chip, it’s a highly integrated IEEE nection with the Atheros chip.
802.11n 1x1 2.4 GHz System-on-a-Chip (SoC) Summarizing, the Arduino Yún combines—
for wireless local area network (WLAN) access on a single PCB the size of an Arduino Uno

119
108 | January & February 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Projects

(53 x 69 mm)—three processors, a Wi-Fi inter-


face, the four Arduino shield extension connec-
Specifications
tors, an Ethernet connector, a female USB-A host Arduino Leonardo (ATmega32U4) with
connector, a micro USB-B connector, a micro-SD • 20 digital input/output pins (7 of which can be used as PWM outputs
card connector, a bunch of LEDs and three (3) and 12 as analog inputs)
reset pushbuttons. • 16 MHz crystal oscillator
• micro USB connection
Breaking with traditions • ICSP header
All other Arduino boards have Italian and English Atheros AR9331 running Linino,
names, Yún is Chinese. This is not the only nota- an OpenWRT-based Linux distribution with
ble change; the Yún differs from other Arduino • Ethernet
boards in several ways: • Wi-Fi
• The Yún is a far cry from the simple and • USB-A host connector
easy-to-build Uno and earlier boards. The • micro-SD card slot
only through-hole parts are the connectors; • 3 reset buttons
all other parts are so small you can hardly
see them. Repairing a faulty board will be
grueling;
• I may be mistaken, but the Yún seems to be While researching and writing this article Intel’s
the first Arduino board for which the hard- Galileo board was launched. This Arduino com-
ware CAD files are not (yet?) published, thus patible board is based on a 32-bit Pentium Quark
breaking with the Open Hardware tradi- SoC X1000 Application Processor, yet another new
tion. The schematics are available as a PDF direction for Arduino. Also the Arduino Tre was
document, but I have not been able to find announced, based on the 1 GHz ARM Cortex-A8
any information on the PCB. This is proba- Sitara AM3359AZCZ100 from Texas Instrument.
bly a 4-layer (or more) design, making DIY Let’s hope that Arduino will not implode under
Yún boards difficult anyway—not to mention the pressure of complication and diversification.
assembling them;
• There is no external power supply input—the
Yún can be powered from 5 V only;
• The Arduino shield connectors have nice
labels stuck on them that show which pin is
which. There is not enough space on the Yún
board to print these labels;
• The board sports three tiny reset pushbut-
tons, one for the WLAN, one for the Yún
and one for the Leonardo, so always make
sure you press the right one. Note that the
Leonardo and therefore the Yún too exhibit
different reset behavior compared to the
Uno or related boards. To restart a sketch on
the Yún you have to press the reset button
twice!
• The Yún can be programmed over Wi-Fi and
Ethernet (if you set it up properly);
• It appears that the design has not been done
by the Arduino team but by a Boston-based Figure 1.
Front and rear view of the
company named Dog Hunter specialized in
Arduino Yún showing the SD
home automation control systems. They are
card connector and the Alcor
probably going to notice an increase in traffic Micro AU6350 integrated
on their unfinished website; USB2.0 hub and multimedia
• The Yún is manufactured in Taiwan, not in card reader controller.
Italy. (Source: www.arduino.cc)

120
www.elektor-magazine.com | January & February 2014 | 109

Personal Download for Petar Crnojevic | copyright Elektor


•Labs

USB
Rx Tx Host
ATmega Bridge Linino
Tx Rx
32U4 AR 9331
SD
Card

USB WIFI ETH


Figure 2. Prog. Interface Interface
Overview of the Arduino
Yún showing the board’s
ARDUINO ENVIRONMENT LINUX ENVIRONMENT 130378 - 11
subsystems and the way
they are bridged together.

Getting started ino.local did not work for me). You should now
Breaking with traditions is one thing, but how see a page that asks for a password. The default
does it affect the ease of use of the board? Let’s password is “arduino”. Enter it and click on the
find out. Log In button. On the Welcome page that opens,
First of all, you need a micro USB-B cable to click on the Configure button.
connect the board. I have hundreds of Mini USB Set the time zone and select the Wi-Fi network
cables, but only one Micro USB cable as part of my that you want to use in the future, enter its pass
phone battery charger. While you are looking for phrase, etc. I did not change the default pass-
a suitable cable, download in the meantime the word, because I know I will forget it. I also set
Arduino IDE 1.5.4 or later (I downloaded version the REST API (the API that allows you to issue
1.5.4 r2), it’s only 134 MB and you will need it. Arduino port commands as URLs, see below) to
Install the software before connecting the board. open, but that is of course up to you. When done,
Now connect the board to the computer. On click Configure & Restart.
OSX or Linux Ubuntu 10.0.4 and up everything (Re)Connect your computer to the Wi-Fi net-
should work straight out of the box. On Windows work that you selected for the Yún and start
you may have to install a driver or two. Luckily the Arduino IDE. In the ToolsŽBoard list choose
a Windows installer is available which has the the Yún, in the ToolsŽPort list pick the very last
advantage that it can install the necessary driv- option “Arduino at xxx.xxx.xxx.xxx (Arduino
ers automatically. If you prefer to do it manu- Yún)” where the x’s form a valid IP address
ally, the drivers are in the drivers folder of the (192.168.2.6 in my case).
IDE distribution. Now you can try out a sketch. Open for instance
After connection and installing drivers where the Blink (or BlinkWithoutDelay) example and
needed the board should be operational. On my click the Upload button. After compilation you
board this meant that the red LED L13 started will be prompted for a password. Enter the one
blinking irregularly and the green On LED lit up. you assigned to your board (“arduino” for me
When, on your computer, you inspect the avail- since I didn’t change it). Uploading of the sketch
able wireless networks, you should see a new starts, the board is restarted (you may hear a
network named “Arduino Yun-XXXXXXXXXXXX” USB disconnect/connect sound on Windows) and
(where the X’s represent hexadecimal characters). the sketch is executed. Note that you don’t have
You may now be tempted to upload a sketch to to enter the password every time you upload a
the board, but the Guide to the Arduino Yún (‘The new sketch, you have to do it only once at the
Guide’ from here on) on the Arduino website [1] beginning of a programming session.
suggests that you first set up the Wi-Fi connec- That was not too bad, was it? It seems a bit silly
tion, so let’s do that now. to program a board that is physically connected to
Connect your computer to the Yún Wi-Fi net- your computer over Wi-Fi, but why not? BTW, it
work and open a browser. Point it to the address is also possible to use the Ethernet port to do all
192.168.140.1 (the suggested link http://ardu- this, but I leave that as an exercise for the reader.

121
110 | January & February 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Projects

Linux
So, now you have an Arduino Leonardo that you
can program wirelessly over Wi-Fi or with a cable
over Ethernet. However, that was probably not
the main reason why you decided to invest in an
Arduino Yún board—more likely it was the Linux
part that triggered your interest.
When you look at the circuit diagram of the Yún
you may notice signal labels referring to ‘Hornet’.
Feeding ‘Hornet’ to a search engine together
with ‘AR9331’ takes you to OpenWRT, an open-
source community project that allows commercial
network routers to be used as Linux computers.
The Atheros processor on the Yún runs such an
OpenWRT-based Linux distribution named Linino.
Linino can be configured wirelessly. Enter the
Yún’s IP address in a browser, log in, and then
click on the “advanced configuration panel (luci)”
link. This will open a status page from where you
can access all kinds of parameters. At the top is
a black menu bar with many options. Take your
time to browse around. Have a look at the kernel
log page to see what happened during start-up.
Use the SystemŽSoftware menu to install or I’d suggest entering the Console example sketch Figure 3.
remove software, use the SystemŽStartup to from The Guide. When you compile and upload Welcome to the Linino
see what is loaded during Linux startup. Here you it to the board, you will be able to use the serial command shell.
can also add commands to be executed at the monitor included in the Arduino IDE to communi-
end of the boot sequence. Clicking the “Arduino cate with the board (as if it was a normal Arduino
Web Panel” link at the bottom of each page takes board). After receiving the welcome message
you back to the Yún’s homepage. type a capital ‘H’ to switch on the red LED L13.
Typing an ‘L’ will switch the LED off.
Take me to the bridge To make things a bit more complicated, you can
According to The Guide, you can access the do this also from a terminal like Tera Term or
Arduino pins (or ports) from the browser by typ- PuTTY. I used Tera Term and here is how to do it:
ing in the right URL (through the REST API). For Open Tera Term. In the New Connection dialog
example, it is possible to make the URL (replace select TCP/IP; for the Host enter the IP address
the first “arduino” by the name of your board) of your Yún. Set the Service to SSH and the Port
to 22. Click OK. (You may get a warning about
http://arduino.local/arduino/digital/13/1 the Host not listed in your cache or something;
simply allow whatever the program wants.) Now
set digital output pin 13 as if you called the a new dialog window is opened where you are
Arduino API function required to enter a user name (“root”) and a
Passphrase (the password you set for your board,
digitalWrite(13,1); “arduino” by default). If all goes well you should
now see the screen from figure 3 meaning that
You can also go the other way around and con- you are connected.
trol Linino Linux from within a sketch. This is
made possible by the Arduino library “Bridge” At the prompt (“root@Arduino~#”) type “telnet
that allows you to access the USB, Ethernet, localhost 6571” and hit Enter. Nothing will hap-
Wi-Fi and SD card devices in a sketch as well as pen. Nothing? Try typing ‘H’ or ‘L’. With these two
run scripts and communicate with web services commands you can control LED L13. Cool, right?
on the Linux module (Figure 2). The Guide gives an example sketch that runs a
To familiarize yourself a little with the Bridge, little Linux program named “curl”. Before trying

122
www.elektor-magazine.com | January & February 2014 | 111

Personal Download for Petar Crnojevic | copyright Elektor


•Labs

Feeling lost?
Raspberry Pi I don’t know about you, but all this leaves me
Looking at the Arduino Yún one cannot help thinking of Raspberry Pi (R- with a rather strange feeling. On the one hand I
Pi), the $35 Linux board. So how do the two compare? have the familiar and extremely simple Arduino
The RPi has been available for over a year now, a large user community IDE running on my PC while on the other I have
has developed and many RPi to Arduino projects have been published access—through a browser on the same PC—to
together with lots of projects that accomplish the same tasks as those a web interface with tons of Linux options. Both
targeted by the Yún. The RPi does not have on-board Wi-Fi, but you programs target the same little blue board lying
can stick a cheap Wi-Fi dongle in its USB port. The RPi has support for next to my PC.
graphical displays, the Yún does not. The RPi requires Linux knowledge
whereas the Yún does not. The R-Pi does not need a host computer The Guide almost starts with Python and other—
to develop applications on, the Yún does. However probably the most to me unfamiliar—Linux concepts, and I cannot
important difference: Yún will cost you twice as much as an RPi help feeling a bit lost. Why would I use a little
microcontroller to run a Linux script if I can run
the script also directly on the on-board Linux
the sketch you may want to see its result in the system? What does the Arduino interface add
Linux console. At the prompt, type for the Linux programmer? Arduino is targeted
at people with little to no programming experi-
curl http://arduino.cc/asciilogo.txt ence, yet the user is supposed to know how to
control Linux from the command line?
Press Enter and wait a few seconds. You should
see appear the Arduino logo in ASCII (Figure 4). It is not that bad. For starters, you can skip the
The point of this demonstration is to show that whole Linux bit and just be happy with how the
whatever you can do in the Linux console, you Arduino team configured it for you. Using the
can also do it from within an Arduino sketch. REST API you can control the Arduino board from
a web application through URLs that you process
To be honest, I have tried the example sketch and in your own sketch. Thanks to the Temboo [2]
it compiles and uploads without problems, but I library you can easily interface an Arduino sketch
have not succeeded in making the result visible. with Twitter, Dropbox, Gmail, MySQL and many
I must have missed something here. more web services. For the more adventurous
there is Spacebrew [3], a software toolkit based
on Websockets to interconnect interactive things.
Once you master the Yún’s built-in Cloud support
you can go further and install your own programs
and utilities on the Linux module to enhance its
capabilities and your options.

Steep
The Arduino Yún is not for beginners. For exam-
ple, connecting the board to the Arduino IDE is
not Plug ’n’ Play at all. And once you get it going
you are supposed to use it for client-server web
applications. However, once you master all this,
the Yún can be an excellent tool to create fun
applications.
(130378-I)

[1] Guide to the Arduino Yún:


http://arduino.cc/en/Guide/ArduinoYun
Figure 4. [2] Temboo: https://temboo.com/arduino
The Arduino logo in ASCII as
[3] Spacebrew: http://docs.spacebrew.cc/
fetched by curl.

123
112 | January & February 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Numitron Clock &


Thermometer
Developed on the Arduino platform

The idea for this project was to take


the Arduino world off of its Shields
and Breadboards and out into a
world of Elektor DIY projects
while also hopefully appealing to
the diehard AVR hackers. These
worlds are so close but are
so often treated as separate.
The project happily combines
today’s microcontroller tech-
nology with 1950’s Soviet
tubes now available ‘NOS’
from Ebay.

By Paul Court (UK) For the clock I decided against the traditional So here we have the project, a Numitron bulb,
7-segment LEDs in favor of something much more clock & thermometer built on a single board. The
beautiful in the form of ex-Soviet Numitron tubes. project is based on the Arduino UNO, meaning the
Numitrons are cousins of the Nixie tubes featured UNO and its IDE were used as development tools
in several Elektor projects, but run on about 4 only. In the final project there are no shields, no
volts rather than >150 volts, hence are more modules and no plugins—just an ATMega328 with
suited to experimentation. Just like the Nixies, peripheral hardware devices around it, although
Numitrons are readily available on sites such as that may be oversimplifying the build ahead, as
eBay at very reasonable rates. we’ll see.

The next ‘tron’: Numitron!


Features Dekatron, Klystron, Thyratron, Magnetron,
Trochotron, Whatever next, Annoyatron? the
• Four IV-9 Numitron tubes
low-voltage generation may ask, and everyone
• Date/Time/Year/Seconds/Temperature readout
invariably ending up at www.radiomuseum.org for
• ATmega328 microcontroller
a glimpse at more baffling, –tron suffixed vacuum
• Developed on Arduino platform
tube devices from the dark pre-Internet ages.
• On-board adjustable SMPSU for optimal Numitron brightness setting
• Powered from 9-12 VDC 500 mA power adapter
You don’t have to master classic Greek to fathom
• No high voltage used
that a Numitron does something with numbers.
• All development code freely available
And indeed a Numitron tube is capable of dis-
• Design powered by Elektor.Labs
playing numbers 0 through 9 and a few letters,

124
30 | October 2013 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


NumiTron Clock & Thermometer

using seven discrete segments, which are actually


little incandescent bulbs. On many Numitrons, a
sort-of-comma (decimal symbol, ds) is included
as an ‘eighth segment’ in the right-hand bottom
corner. The segments in a Numitron share a com-
mon positive supply line, and their other ends
are brought out to wires—not pins. Like many
Nixies, Numitrons are wire tubes.

Numitrons are the ‘warm-light’ variants of the sol-


id-sate 7-segment LED display. Originally devel-
oped in the Cold War period, i.e. in the tube era,
they are still available as NIB (new in box) a.k.a.
NOS (new old stock) items, particularly from Rus-
sian suppliers—mostly Ukrainian—active on the
Internet. The type IV-9 Numitrons Luc Lemmens
wanted in order to replicate the project at his
desk in the Elektor Labs were ordered through
EBay (a US company for sure) and arrived from
Russia intact despite rudimentary but amusing
packaging methods applied by the 5-Kstar rated
seller. See the photo story in Figure 1 triggered
by your Retronics Editor: LOL.

The main technical specs of the IV-9 numitron


used here are given in Table 1. As we men-
tioned in the article on the Nixie VU Meter using
the IN-9 [1], what we like to think of as “design
data“ on these Sovjetisk tubes is subject to (1)
wide interpretation, (2) even wider tolerance,
and (3) stencil printing in Cyrillic.

Circuit description
Looking at the circuit diagram in Figure 2, you
might be surprised to see that no multiplexing
is applied to the display elements. Instead, each
of the four digits of the clock has its own driver
IC type SN74LS47D. You can’t really multiplex
the IV-9, being a tungsten filament bulb it’s just
too slow and either flickers, or is too dim. Each
channel therefore has its own driver and a set
of four BCD drive lines, except V1, the highest
clock digit, which needs only two. While using
four 74LS47’s and no latch or multiplexer uses
up more Atmega pins, it is easier to understand
when it comes to coding. Each tube having its Figure 1.
own BCD lines, it can be directly addressed by Hey, the Numitrons have
arrived all the way from
toggling the pins High or Low.
Dot-ua Land. And a good
read included free! Paid for
On supply voltages, the circuit has two inter-
in US$ using a credit card,
nally: +5 V from an ordinary 78L05 regulator and cleared by customs, the
(IC1) and +4.00 V (adjustable on P1) from a little little tubes came all the way
switch-mode supply around the familiar MC34063 from the Ukraine.

125
www.elektor-magazine.com | October 2013 | 31

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Table 1. IV-9 Main Specifications (attempt @)


Type IV-9 (ИВ-9)
Brand Reflector/ Sovtec
Substitute(s) -
Displayed symbols 7 segment, ds
Symbol height (length) 10 mm (0.400 ")
Overall dimensions 11 mm (0.433 ") dia. x 35 mm (1.38 ")
Pin diameter 0.5 mm (0.020 ")
Figure 2. Typ. (max.?) supply voltage 4.5 V
Schematic of the Numitron Typ. current per segment 19.5 mA
Clock & Thermometer. Note
Base TO-100, pin 1 in front
that each Numitron V1-V4
has individual drive, rather Socket Njet. Wires—no socket needed
than multiplexed.

+5V

R1 P1 MOD1

18
17
16
6

VCC
+3V3
+5V
0R18

K1
VCC

-VIN

8
DRVC IC2 R3
6
RESET RI
13
IC1 7 C16
DCD
10k

7 MC34063AP 8 RES
L1 V+ 78L05
IPK +5V DSR
9V 1
SWC SWE
2 1 3 1
CBUS4 DTR
9
100n
18uH 2 10
TCAP

GND

CBUS3 RTS JP1


3 11 RxD
CBUS2 TXD
2

R2 4 12
3

C3 C4 D1 C5 C1 C2 CBUS1 RXD
5 14
GND
10k

CBUS0 CTS
220p 22u 100n 100n TxD
100u 25V 1N5819 16V BOB-FT232
15

+5V

C6 C7
+5V +5V
+5V +5V +5V 100n 100n
20
21

C8
7

R4 S1 S2
AVCC
VCC

AREF

C9
23 4A 100n
8

R7 R5 R6
4k7

PC0
24 4D
VCC

Vbat

IC9 10u 16V ADJUST SET PC1


3
4k7

4k7

RxD RxD 2 25 4C 7 1
10k

PD0 PC2 OUT X1 BT1


VDD TxD TxD 3 26 4B IC4 X1
PD1 PC3
2 4 27 5 DS1307 3V
DQ PD2 PC4 SDA
1B 5 28 6 2
R8 R9 PD3 IC3 PC5 SCL X2
GND 1A 6 1 RES RES 32.768kHz
GND

PD4 PC6
1
10k

10k

2B 11
DS18S20 PD5 ATmega328-PU
2C 12 14 2A
4

PD6 PB0
2D 13 15
PD7 PB1
16 3A
PB2
17 3D
PB3
18 3C +5V
PB4
19 3B K2
PB5
GND

GND
PB6

PB7

3C 1 2
3B 3 4 3D
9

8
22

10

X2 RES 5 6

C10 C11 AVR ISP

22p 16MHz 22p

V+ V+ V+
2A
2B

4A
1A

2C

V+
3A

4B
1B

2D

4C
3B
3C

4D
3D

+5V V1 +5V V2 +5V V3 +5V V4


7
1
2
6

7
1
2
6

7
1
2
6

7
1
2
6
A
B
C
D

A
B
C
D

A
B
C
D

A
B
C
D

16 13 5 16 13 5 16 13 5 16 13 5
VCC Y0 a 1 VCC Y0 a 1 VCC Y0 a 1 VCC Y0 a 1
12 3 CA 12 3 CA 12 3 CA 12 3 CA
IC5 Y1 b IC6 Y1 b IC7 Y1 b IC8 Y1 b
3 11 4 3 11 4 3 11 4 3 11 4
C12 LT Y2 c C13 LT Y2 c C14 LT Y2 c C15 LT Y2 c
4 10 8 4 10 8 4 10 8 4 10 8
BI/RBO Y3 d BI/RBO Y3 d BI/RBO Y3 d BI/RBO Y3 d
100n 5 9 9 100n 5 9 9 5 9 9 100n 5 9 9
RBI Y4 e RBI Y4 e 100n RBI Y4 e RBI Y4 e
15 6 15 6 15 6 15 6
Y5 f Y5 f LA1 Y5 f Y5 f
8 14 7 2 8 14 7 2 8 14 7 2 8 14 7 2
GND Y6 g dp GND Y6 g dp GND Y6 g dp GND Y6 g dp
SN74LS47D SN74LS47D SN74LS47D SN74LS47D
IV-9 IV-9 IV-9 IV-9
V+ 120740 - 11

126
32 | October 2013 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


NumiTron Clock & Thermometer

(IC2). The IV-9’s filament voltage range is actu- plus this delay gives time for the RTC to recover
ally 3.15-4.50 volts and you want to set P1 to a between reads. If you read too often you get rub-
level that best suits your viewing. Each filament bish back! BTW La1 is a “grain of wheat” (GOW)
draws about 19.5 mA. The whole clock requires a style miniature light bulb as used in dollhouses
DC input of 7.5 V unregulated at about 500 mA. and model railways.
The internal supply voltages were chosen as On each cycle the code starts by checking if the
5 volts and 4 volts (3.00 V-4.50 V), and not set button (S2) has been pressed and if not then
3.3 V only, because updates the indicator bulb. At this point the RTC
is read and, using some basic Integer division
• the higher voltage allows the Atmega to math, the hours and minutes are each split into
work at 16 MHz; Tens and Units, each value is then sent to the
• 3.3 V is too low considering the 74LS47D correct Numitron digit.
LS-TTL ‘open collector’ outputs powering the For simplicity of the code each digit has its own
filaments from the V+ do not quite pull down routine but they all work in a similar way with the
all the way to 0 V when On. only exception being the ‘Hour Tens’ that only has
two binary bits (on IC5/V1). Finally using another
The heart of the clock is an ATmega328P, which useful math trick (Bitwise AND) we then convert
is the chip used in the UNO and Duemilanove the decimal number into Binary ready for the
series of Arduino boards. If purchasing or using 74LS47’s. More info on Bitwise operations may be
a chip with an Arduino Boot Loader pre-installed found at [2]. While it looks a little long winded
the Duemilanove version is preferred. it’s actually very simple, and a really useful way
Programming of the ATmega328P is via the stan- to convert Decimals to individual Binary digits.
dard 6-pin ISP header and AVR Studio, or via the We have two extra functions to add value and
optional Elektor FT232 BOB, the BOB being used interest. The first is called on the 10-second and
by the Arduino IDE software (V1.0 or greater) 30-second points, reading and displaying the tem-
with the Duemilanove Bootloader pre-pro- perature in degrees Celsius. This works as above
grammed on the ATMega. As far as the Arduino using Mod and Bitwise math to take the reading,
IDE knows it’s talking to a standard ‘Arduino convert it to binary and display it via the 74LS47s,
Duemilanove w/ ATmega328’ Board. the exception to this being the lowest digit that
The real-time clock (RTC) is a DS1307, and the is sent a decimal ‘10’ which makes the 74LS47
temperature sensor, a DS18B20—both compo- on that digit (V4) to display a ‘c’ thus complet-
nents are well supported in the Arduino and AVR ing the display to show for example ‘22.5c’. The
communities. Their ‘One-Wire’ data is read by 74LS47 is unable to display ‘f’, hence a Fahren-
the ATMega controller on the last two available heit readout is not supported.
port lines, PD2 (temperature) and PC4 (RTC). Lastly on the 50th second the showdate() rou-
The expected ISP (in-system programming) con- tine is called that displays the date, month and
nector is available (K2) to allow the ATmega chip then year.
to be programmed without removing it from its
socket. The code is very basic and I’m sure you could
MOD1, an Elektor BOB-FT232 (break out board), find other functions for the clock (Egg timer?),
is optional. It provides USB connectivity and is so why not join the project at Elektor.Labs [4]
useful to have if you are keen on working on the and show us your code/updates/tweaks, or just
clock software within your Arduino environment. share your ideas and suggestions.

The software Build it, use it


The source and hex files for the ATmega328 are Being SMD-free the project should be easy to
available from the Elektor website [1]. Ready build at home, at school, at TechShop San Jose
programmed ICs are also available: Elektor Store CA, or in a small lab. The circuit board shown in
# 120740-41. Figure 3 tallies with the Component List. Fig-
ure 4 shows the benchmark you’re up against as
The code is written to loop every 500 ms (½ far as tidiness, component selection and proper
second)—this is most obvious by the indicator soldering are concerned. Initially, set preset P1
bulb La1 that flashes on and off once per second, for +4.00 volts on the V+ rail.

127
www.elektor-magazine.com | October 2013 | 33

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

r p c bs
to
COMPONENT LIST

er
.e l e k

v i c e.c
Resistors C4 = 220pF

ww
R1 = 0.18Ω 3W C5 = 22µF 25V radial om
R2,R3,R7,R8,R9 = 10kΩ C9 = 10µF 50V radial w
R4,R5,R6 = 4.7kΩ C10,C11 = 22pF
P1 = 4.7kΩ preset, top adjust
Figure 3. Inductors
The double sided printed Capacitors L1 = 18uH choke, 3.4A, 0.036Ω (Panasonic type
circuit board designed for C1,C2,C6,C7,C8,C12,C13,C14,C15,C16 = 100nF ELC10D180E)
the project by Elektor Labs. C3 = 100µF 25V radial
Semiconductors
D1 = 1N5819
IC1 = 78L05
IC2 = MC34063
IC3 = ATmega328-PU, programmed, Elektor Store #
120740-41 [2]
IC4 = DS1307
IC5,IC6,IC7,IC8 = 74LS47
IC9 = DS1820

Miscellaneous
V1,V2,V3,V4 = IV-9 Numitron tube
JP1 = 2-pin pinheader + jumper cap, 0.1’’ pitch
X1 = 32.768kHz quartz crystal
X2 = 16MHz quartz crystal
MOD1 = BOB-FT232R (optional), Elektor Store #
110553-91
Bt1 = CR2032 battery
S1,S2 = pushbutton, SPST, chassis mount
K1 = power jack, 2.1mm, PCB mount
K2 = 6-pin (2x3) boxheader
La1 = 5V 300mW light bulb, GOW
PCB # 120740 [2]

Small delays in the code de-bounce the buttons


and make everything smooth.

Once the minutes are correct, another press on


set switches to the Hours, then Day, Month and
finally, Year. On completion of this cycle the new
values are written to the RTC and the code returns
to the main Loop.
(120740)

Internet Links
[1] Nixie VU Meter, Elektor November 2012,
www.elektor.com/110744
[2] www.elektor.com/120740
[3] http://playground.arduino.cc/Code/
BitMath#bitwise_and
[4] www.elektor-projects.com/project/nu-
Figure 4. To set the clock, jumper JP1 must be removed
mitron-arduino-clock-and-thermome-
The assembled and tested (‘Run’ mode). Pressing the set button S2 will
board, ready for use. ter-120740.12460.html
cause the setclock() routine to be called, firstly
displaying the Minutes. Pressing the adjust but-
ton S1 counts up by 1 on each press or keeps
adding 1 every ½ second if holding the button.

128
34 | October 2013 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


SPOT THE DIFFERENCE
By Wisse Hettinga In line with a strong trend
in the industry, Renesas
underscore that their latest
GR Sakura board is Ardu-
ino compatible. This over-
view allows you to check for
yourself just how far that
compatibility goes.

Difference #1
Okay, the GR Sakura board
is pink! But then, look at
the specs—Pink is Power!

Difference #2
It’s 8 bit, 16 MHz and lim-
ited memory of the AVR
controller against full 32
bit, 96 MHz and massive
memory capacity of the
Renesas processor.
The real question is, which
applications will actually
unleash GR Sakura’s full
potential.

Difference #3
The USB Host functionality
on the Sakura board shows
potential. It is implemented
with a Mini-B connector,
while a Type-A connector
can be fitted on the back
side of the board.

Arduino Uno GR Sakura


3.3 V processor operating voltage
Supply Voltage(s) 5 V processor operating voltage
5 V board supply voltage

Mini B connector
Type B connector
USB Type A connector provides Host support
Board runs off USB voltage by default.
Board runs off USB voltage by default

Network None Ethernet RJ45

129
90 | July & August 2013 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Spot the Difference

ARDUINO UNO vs. GR SAKURA FULL


Difference #4
You can’t deny that the true
power of the Arduino concept
is due to the huge and eas-
ily accessible program library
(at www.arduino.cc), rather
than the hardware. However,
don’t underestimate the pro-
gramming options available
for the Sakura board either.
It has lots of features that
come to life once you start
using the Cloud Base Com-
piler. Just hook up the board
to your PC, push the right but-
tons—all well documented—
and watch the board appear
as a new drive connected to
your PC. With the new drive a
link is provided that takes you
straight to the website. If you
have an Android phone, have
a look at Gadget Director—an
easy, ‘icon’ based program-
ming language.

Find all the references at


www.designspark.com and
go to the Design Centers.

(130177)

Arduino Uno GR Sakura


ATmega328 RX63N
Processor 8 bit 32 bit
16 MHz operating frequency 96 MHz operating frequency
1 MB Flash
32 KB Flash of which 0.5 KB used by bootloader
RAM: 128KB
Memory SRAM: 2 KB
Data Flash: 32 KB
EEPROM: 1 KB
MicroSD socket

130
www.elektor-magazine.com | July & August 2013 | 91

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Off to the EF Library!


Controlling hardware
using a UART or SPI interface

By Jens Nickel If a suitable protocol is defined, hardware connected to your PC can be controlled
(Elektor Germany Editor)
using a terminal emulator program. The necessary firmware can be rustled up
quickly using Elektor’s ‘Embedded Firmware Library’ (EFL), and the code can be
written without knowledge of whether a UART or some other interface will be used
for the connection. The protocol described here is ideal for experimentation and
development purposes.

In the previous edition we described our modular a code file for the board and a code file for the
‘Embedded Firmware Library’ (EFL), written in microcontroller.
the C programming language. This helps begin-
ners and old hands alike to develop code for However, the idea of modularity is taken even
an embedded project that is independent of the further in the EFL. Protocol libraries allow pro-
underlying hardware and which can therefore grams that communicate to be written without
easily be ported from board to board and from knowledge of the communication channel that will
microcontroller to microcontroller. This is achieved be used: it makes no difference whether com-
using a hardware abstraction layer consisting of mands and data are transferred using a UART and

131
26 | June 2013 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


EFL

RS-232 or RS-485 connection, or using TCP/IP


over Ethernet. Just a couple of lines of the appli-
cation program code need to be changed to use
a different interface. In this article we will look
at this in more detail and present a protocol that
can be used in simple hardware control applica-
tions and for development.

Mini protocol
When trying to get code up and running simple
tests such as turning a LED on and off or reading
a digital input can be very helpful. Often, how-
ever, a microcontroller board will not have any
buttons to help you carry out such tests. One
alternative option is to control the board from
a PC, for example over a serial interface. If the
protocol is restricted to ordinary printable ASCII
characters it is easy to use a terminal emula-
tor program to send commands to the board,
avoiding the need for special-purpose software
on the PC.

Our mini protocol (called ‘BlockProtocol’) is


designed to let us set and clear pins on the {1}
SENSOR [3] RS485
microcontroller from the PC terminal. If there
ADC/2.0 3.0/RXD [4]
is an LED connected to the pin in question, this [5]
(+0) (4)
3.1/TXD {0}
ADC/2.1
(+1) (5)
gives immediate feedback; otherwise a multi- ADC/2.2 3.2
(10)
{2} (+2) (6)
3.3
meter or oscilloscope can be used. There are SENSOR (+3) (7)
ADC/2.3 (11)
ADC/SDA/2.4
also simple commands for obtaining the status (+4) (8)
(+5) (9)
ADC/SCL/2.5 µC (0) [0]
of digital inputs and for reading ADC conversion
3.4 (1)
results from the analogue inputs (see the text MOSI/1.3
3.5
MISO/1.4
box ‘BlockProtocol’). The code in the accompa- 3.6
(2)
SCK/1.5
3.7
[2]
nying library module can of course be extended
[1] (3)
in many ways as required. Perhaps a reader will
(12) (13) (14) (15)
be inspired by the control protocols designed by
Andreas Eppinger [2] and Uwe Altenburg [3], 120668 - 16

which offer a much wider range of facilities.

Map, blocks and board pins The peripheral blocks are shown in the middle, Figure 1.
The BlockProtocol includes the ‘x’ command spe- while on the right is a list of the pins on the board. Dump of the EFL tables
cially designed for use in development with the This is particularly important information for any- as seen in the terminal
emulator. On the left
EFL. The command causes the board to send a one planning to adapt or write an EFL board file
is the map with the
dump of the EFL tables to the PC. The tables are for a new board. More extensive documentation
microcontroller features in
used by the hardware layer to determine the on the internals of the EFL are given in the extra use (red numbers in the
microcontroller pins and registers that need to document that can be downloaded at [1]. board block diagram); in
be changed in response to a function call. The the middle is the block table
entries are specific to the board and any expan- Control via UART (blue numbers); and on the
sion board that might be attached. The screenshot We shall now show by example how easy it is to right are the board pins
in Figure 1 shows what appears in the terminal use the protocol in your own microcontroller appli- (green numbers).
window when the board shown alongside is used. cations. We will use an experimental node, famil-
On the left is the ‘map’ including the features of iar from our series on the ElektorBus. This is a
the microcontroller such as the UART and ADC very compact board based on an ATmega328. As
that are set up by the board initialisation code. usual we will connect the node to the PC using its

132
www.elektor-magazine.com | June 2013 | 27

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

In this case the code is the same as in the EFL


example software from the previous issue, as we
are using the same board and the same microcon-
troller. The ‘Libraries’ directory includes the files
UARTInterface.h and UARTInterface.c, which form
the library for the UART interface on the board.
Here this is our RS-485 driver (corresponding
to the ‘physical layer’ of our communications).
There is also a module implementing our proto-
col (BlockProtocolEFL.c and BlockProtocolEFL.h).
Together these two library modules provide a
defined software interface which we will now
look at.

A little code
In the main source file of the application code
itself we need to include the library header files
as follows.

#include “UARTInterfaceEFL.h”
Figure 2. RS-485 interface and a USB-to-RS-485 converter #include “BlockProtocolEFL.h”
Our small microcontroller (Figure 2). Instead of the ElektorBus protocol
board can be controlled over we will use our new text-based BlockProtocol. The main function in an EFL-based project is
a UART/RS-485 interface always structured in the same way: see List-
with the help of a simple
The necessary firmware for the microcontroller ing 1. In the application set-up function, which
ASCII text-based protocol
can be downloaded at [4]; the application can is called whenever the application starts up, we
and a terminal emulator
program. also be found in the EFL code base at [5]. An initialize the libraries:
overview of the files is given in the extra doc-
umentation mentioned above. Double-clicking UARTInterface_LibrarySetup();
‘ExperimentalUART.atsln’ opens the project in UARTInterface_SetBaudrate(0, 38400);
Atmel Studio: see the screenshot in Figure 3. BlockProtocol_LibrarySetup(UARTInterface_
On the right-hand side is a list of the files in Send, 0, UARTInterface_GetRingbuffer(0));
the project. The files Controller.h, Controller.c,
Board.h and Board.c form the hardware layer. Here the second line sets the baud rate of UART
interface block 0 (which is where we have our
RS-485 driver connected) to 38400 baud. The
Listing: third line needs a bit more explanation. We are
Basic structure of an EFL application. telling the BlockProtocol library that it should use
the function UARTInterface_Send when it wants
int main(void)
to send data from the board. The second param-
{
eter is the number of the UART interface block to
Controller_Init();
be used (even though on the experimental node
Board_Init();
there is only one UART interface).
Extension_Init();
The third parameter is a pointer to a ‘ring buffer’
ApplicationSetup(); (or ‘circular buffer’) to be used to store received
bytes. Here the required pointer is obtained as
while(1) the return value of the function UARTInterface_
{ GetRingbuffer(0), which is also implemented in
ApplicationLoop(); the UARTInterface library.
}
In the main application loop function, which is
};
called regularly when the application is running,

133
28 | June 2013 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


EFL

we need just a single line:


BlockProtocol_Engine();

This is the main function in the BlockProtocol


library. It checks whether characters from the PC
have been received in the ring buffer, and as soon
as a <CR> (ASCII 13) is seen it is interpreted
as the end of a command and the command is
then carried out. A response is assembled, which
is either simply ‘Ok’ or a value such as ‘HIGH’
or ‘LOW’, or information about the EFL variables
in table form.

Let’s try it
Having compiled the code and flashed it into the
board we can try it out using a terminal emula-
tor program such as HTerm [6]. First we have to
specify which COM port to use and the baud rate.
In the ‘input control’ window we have to set the
program up so that the <CR> character is sent
when the Enter key is pressed (see Figure 4). character sequences given above. Figure 3.
Code to control hardware
We will first use the library at its lowest level to Higher-level commands over a UART interface.
demonstrate direct access to to the output port Directly controlling port pins is not the main rai-
pins of the microcontroller. From the circuit dia- son d’être of the EFL. If we want to port our
gram of the experimental node [7] we can deter- device control program to use a different micro-
mine that the red LED on the board is connected controller board with different wiring, we would
to port pin PD4. Port D on the AVR microcontroller have to change the character sequences given
Figure 4.
corresponds to port index 3. And so we simply above inside the PC or Android software.
The HTerm terminal
type into the terminal emulator For this reason the mini-protocol also allows emulator lets you choose
hardware-independent control of digital inputs what is sent when the Enter
p 3 4 + <ENTER> and outputs, just like when writing code to run key is pressed.

and the red LED on the board will light.

As another example, using commands like


‘p 2 0 +’ or ‘p 2 0 -’ we can set and clear pin
PC0 on the expansion connector. If an expan-
sion board, such as the sensor/LED board form
the previous issue or the relay board from the
ElektorBus series [8], is fitted this gives us a
simple way to control external hardware devices
from the PC. Instead of the terminal emulator
program we could run a dedicated program on
the PC to send commands like ‘p 2 0 +’ to the
appropriate COM port in order to switch the relay.

Alternatively we could connect a smartphone to


the experimental node using the Andropod RS-
485-UART bridge board [9] and write a small
Android app. The software at [10] could be used
as a starting point for such a project, replacing
the bytes of the ElektorBus protocol with the

134
www.elektor-magazine.com | June 2013 | 29

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

B 0 0 ? <CR>
on the microcontroller itself as described in the
previous issue.
With the string we can request the status of the test button (but-
ton 0 of button block 0). And with
L 0 1 + <CR>
R 0 0 + <CR>
we can switch on LED 1 in LED block 0 (which
on our board is the yellow LED). With we can turn on a relay.

Three-wire interface
The approach described above assumes that we
BlockProtocol have external access to a UART on the microcon-
troller, for example via RX and TX pins brought
Each command starts with a single character, possibly followed by one
out on the board. We also need a more-or-less
or two decimal values. These specify to the EFL the pin on which the
complete EFL microcontroller description file
command will act. A final character is used to specify any particular
which describes not only the I/O pins and ADC
action to be performed.
functions but also the UART functions that are
available.
x
Outputs the EFL map, block and board pin tables (see additional
When starting out with a new microcontroller (for
documentation at [1]).
example because you want to develop an EFL
microcontroller description file for other read-
p x y +, p x y –, p x y ?, p x y #, p x y *
ers to use) it is probably simplest to start with
For microcontroller pin y on port x: set high; set low; read state; read
the I/O functions. The first major hurdles are
ADC conversion result (if applicable); toggle under timer control.
to study the datasheet to determine how to go
about setting the level on the I/O pins and reading
b x +, b x –, b x ?, b x #, b x *
their status, and to find at least three general-
For board pin with index x in the board pin table: set high; set low; read
purpose I/O pins that are brought out to con-
state; read ADC; toggle.
venient points: fortunately most boards satisfy
this condition. It will then be possible to control
i x y +, i x y -, i x y ?, i x y #, i x y *
the board using the protocol described above,
For pin in position y within the block with index x in the block table: set
over a three-wire SPI interface implemented in
high; set low; read state; read ADC; toggle.
software. One of the wires is a clock signal, the
second carries bytes from the master (the PC)
C x y +, C x y –, C x y ?, C x y #, C x y *
to the slave (the board), and the third carries
For pin y of connector x: set high; set low; read state; read ADC;
bytes in the opposite direction.
toggle.

The SPI specification allows for the further pos-


L x y +, L x y –, L x y ?, L x y *
sibility of having communications over the three-
For LED in position y in LED block x: set high; set low; read state;
wire interface initiated by the slave rather than
toggle.
by the master. In this case each participant takes
its ‘out’ line high and waits for the other partici-
R x y +, R x y –, R x y ?
pant to do the same. Then communication can
For relay in position y in relay block x: set high; set low; read state.
begin, with, as usual in SPI systems, the mas-
ter providing the clock and data bytes flowing in
Bxy?
both directions simultaneously. When there are
For button in position y in button block x: read state.
no more data to send a ‘stop character’ (<LF>,
ASCII 10) is sent. When both participants have
Axy#
sent this byte, the communication is complete.
For ADC in position y in ADC block x: read conversion result.

We have encapsulated this protocol in the EFL


*
module called ‘ThreeWireInterfaceEFL’. With the
Stop timer-controlled toggling.
help of this module it is easy to set up communi-

135
30 | June 2013 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


EFL

cations using the software SPI interface in place


of the UART interface.
The code required in the application set-up func-
tion is now as follows:

ThreeWireInterface_LibrarySetup();

BlockProtocol_
LibrarySetup(ThreeWireInterface_Send, 0,
ThreeWireInterface_GetRingbuffer(0));

These lines tell the BlockProtocol library that we


will be using the three-wire interface to send and
receive data: compare them with the code for
setting up the UART interface above.
In the main application loop we need the Figure 5.
command Communication with an
Arduino Uno over a three-
wire interface.
ThreeWireInterface_Listen(0);

which checks whether the other device has taken inserted in the main application loop the processor
its data line high to indicate a request to send will regularly check whether a string, terminated
data. If so, the communication is set up. When with a <CR> character, has appeared in one of
using the UART for communication we do not the input ring buffers. If so, then its contents
need a listener function like this, as in that case are sent out on the other communication chan-
a microcontroller interrupt can be used to detect nel. Then the other input ring buffer is similarly
when characters arrive and automatically store checked, and so on.
them in the ring buffer.
It should almost go without saying that the gate-
Making contact with an Arduino way module itself is programmed in a manner
To demonstrate the EFL concept we selected an independent of the underlying communication
Arduino Uno board. The code for this board can channels and can therefore easily be used to per-
be found in the project ArduinoUnoEFL [4][5]. We form other similar gateway functions. The func-
decided to use general-purpose I/O pins PB0, PB1 tion OneToOneGateway_LibrarySetup takes two
and PB2 to access the board: these are brought triples of parameters to specify the two com-
out on the ‘digital’ I/O connector as Digital8 to munications channels being connected. In this
Digital10. A simple three-way cable (for exam- example the call appears as follows:
ple using Conrad order code 741221) provides
a practical solution (see Figure 5). OneToOneGateway_
Of course we also need a connection to the PC at LibrarySetup(UARTInterface_Send,
the other end, and that will also need to have a 0, UARTInterface_GetRingbuffer(0),
three-wire interface. We pressed an experimen- ThreeWireInterface_Send, 0,
tal node board into service as a gateway, con-
ThreeWireInterface_GetRingbuffer(0));
verting from three-wire format to RS-485 (and
thence to USB) and back again. The firmware We now just need to plug the cable into the
involved can also be downloaded at [4] or [5]: experimental node’s expansion connector (pins
the Atmel Studio project can be found in the PC0 to PC2, see Figure 6) and flash the appro-
directory ‘ExperimentalSPI’. priate hex file into its microcontroller.
The gateway function has its own library mod-
ule called OneToOneGatewayEFL. With a call to The pins used to form the three-wire interface
have to be specified separately for the two dif-
OneToOneGateway_Engine(); ferent boards. The three-wire interface on each
device is a separate peripheral block: recall that

136
www.elektor-magazine.com | June 2013 | 31

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Figure 6. the board file encapsulates the mapping between (130154)


The experimental node acts peripheral blocks and microcontroller pins. The
as a gateway between the configurations for the three-wire interface, includ-
three-wire interface and the Internet Links
ing these pin assignments, can be found in the
UART/RS-485 interface. [1] www.elektor-magazine.com/120668
Board_Init function in the file BoardEFL.c.
[2] www.elektor-magazine.com/100576
It rocks! [3] www.elektor-magazine.com/120296
In the terminal emulator program we first issue
[4] www.elektor-magazine.com/130154
the ‘x’ command. The Arduino board responds
directly, sending the ELF variables out over the [5] www.elektor-labs.com/efl
three-wire interface, albeit at a rather more lei- [6] www.der-hammer.info/terminal/index.htm (in
surely pace than before (the speed is comparable German only)
to that of a 9600 baud serial port). [7] www.elektor-magazine.com/110258
The command
[8] www.elektor-magazine.com/110428

C 0 13 + <CR> [9] www.elektor-magazine.com/110405


[10] www.elektor-magazine.com/120097
can be used to set pin 13 of the Arduino’s ‘digi-
tal’ connector high: this pin drives an LED on
the Arduino Uno board, and so we get immedi-
ate visual feedback.

In the next instalment we will take the EFL pro-


ject further: suggestions and contributions are
more than welcome.

The most recent version of the EFL code can be


found on the Elektor.Labs pages at [5].

137
32 | June 2013 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Projects

Arduino
AC Grid Analyser
Frequency analysis
on a mini colour display
By Fidelis Theinert A fully fledged spectrum analyser on a basic Arduino board? In this article we’ll
(The Netherlands)
show you how this is possible when the software is tailored to the available pro-
cessing power. A standard Arduino can be turned into an AC line (‘mains’) sup-
ply spectrum analyser with the addition of a filter shield and a display shield. It
uses a Fast Fourier Transform to visualize the ‘pollution’ on the AC grid supply at
home or at the office.

138
28 | December 2012 | www.elektor.com/magazine

Personal Download for Petar Crnojevic | copyright Elektor


AC Grid Analyser

Electrical
Isolation Lowpass 10-bit ADC Window FFT
AC Line Attenuation
50 / 60 Hz Serial
Output
Spectrum

Counter
Arduino
Frequency Display Figure 1.
120546 - 11 Block diagram for the
spectrum analyser.

A simple Arduino board is much more powerful length of the array can usually be freely chosen.
and versatile than many readers realize. In this According to the Nyquist-Shannon sampling
article we’ll use a practical example to show you theorem the bandwidth of the signal may not
what the capabilities are of this small 8-bit micro- be greater than half the sampling frequency. In
controller, but also what its limitations are. We other words, the sampling frequency has to be at
will also explain how the various components of least twice the value of the highest frequency we
the microcontroller can be used efficiently and want to investigate. With a sampling frequency
which free development tools are required to of 800 Hz you can therefore analyse a signal with
set up projects such as these. The software and a bandwidth of 400 Hz, which makes it possible
hardware are of a modular construction, which to show the spectrum of the local AC grid supply
makes it possible to use the individual modules up to its sixth harmonic (60 Hz x 6 = 360 Hz),
in other projects as well. The application was or seventh (50 Hz / 350 Hz).
tested successfully on an Arduino Duemillenova,
UNO R1, R2 and R3. Hardware
The hardware consists of three boards: the
The circuit analyses the AC grid voltage using Arduino board [1], a filter shield developed by
a Fast Fourier Transform (FFT) and shows any the author and an LCD shield [2]. The two shields
harmonics present on the display. This can then can be mounted on the Arduino board (with the
be used to assess the quality of the supplied LCD shield on top, of course), which results in a
(energy) signal. These higher harmonics cause compact and sturdy module without any loose
losses in machines and motors that are converted wires. Figure 1 shows a block diagram of the
into heat, but which you still have to pay for. Fur- complete setup.
thermore, the efficiency of switch mode power
supplies in PCs and other devices is compromised When the Arduino has calculated the spectrum
by a supply signal that isn’t an ideal sinewave. it is also possible to send the result to a PC via
the serial port. The graph can then be plotted
Fourier analysis using a terminal program (Putty, for example).
The Fast Fourier Transform is a mathematical The transmission of the data requires a bit more
algorithm that converts a discrete signal from time since the whole graph is sent to the UART
the time domain into the frequency domain. The of the PC at a rate of only 57,600 baud. This
improvement in execution time of the FFT com- feature will be particularly useful to those of you
pared with the ‘Discrete Fourier Transform’ (DFT) who don’t have an LCD shield.
can be quite substantial for a large number of
samples (N). With an FFT the Fourier transform To make sure that the input signal doesn’t have
on a signal with N samples is split into two trans- any frequency components above 400 Hz, a fourth
forms with lengths of N/2. order Sallen-Key lowpass filter (or anti-aliasing
This results in a much reduced execution time filter) with a bandwidth of 350 Hz is put in front
since there are fewer calculations to be done, but of the input (Figure 2). The two Butterworth
it does mean that the number of samples (N) has sections are made around a TS912 dual opamp.
to be a power of two (64, 128, 256, ... , 4096 This opamp has a rail-to-rail output and a wide
...). In practice this is not a problem since the operating voltage range of 2.7 V to 16 V, which

139
www.elektor.com/magazine | December 2012 | 29

Personal Download for Petar Crnojevic | copyright Elektor


Projects

Power
RESET 1
3V3 2
5V 3
GND 4
R7 GND 5
47k VIN 6
R1 R8
C2 C5

330R
1k
JP1
100n 680n
C10 R5 R6 R3 R4
3 8 5 Analog
3k9 3k9 1k8 1k8
1 7 A5 1
2u2 IC1.A IC1.B
16V 2 6 C7 A4 2
X1 2
4 A3 3
100n A2 4
R10
10k R2 A1 5
C3 IC1 = TS912 C1 C8 C9 C4 LED1
A0 6

1k
1
100n 100n 22u 100u 100n
16V 16V JP3
Figure 2.
Anti-aliasing filter (350 Hz 120546 - 12

Butterworth lowpass filter).

means it can be powered directly from the 5 V the microcontroller (an ATmega328P). The out-
supply voltage on the Arduino board. put of the opamp is also capacitively coupled to
connection A4 of the analog input connector of
The output signal from the filter goes directly the Arduino board, for measuring its frequency.
from pin 7 of IC1 to channel 5 of the ADC on In Figure 3 you can see the shield board designed

FFT tricks
The Cooley-Tukey ‘butterfly’ algorithm implemented here is a would be useful if we could store the samples as ‘single
so-called ‘in-place transformation’; this means that the result precision floating point’ variables instead of integers. (In an
of the transformation is stored in the same buffer where the FFT we don’t just have simple mathematical operations such
original samples of the input signal were stored. The input as addition and multiplication, but also sines, cosines, square
signal is therefore no longer available after the conversion. roots and exponentiation.) However, these require 4 bytes
The advantage of this is that the memory required for each for storage, making the buffer 2048 bytes long, which is
the buffer is halved , which is extremely useful when the as much as the available memory in the microcontroller, and
microcontroller used (ATmega328) only has 2048 bytes of therefore too big for the chosen platform. One way round this
memory available. dilemma would be to halve the number of samples for the
FFT to 128, but this will result in a lower spectral resolution
As was mentioned previously, the number of samples has and is therefore undesirable.
to be a power of 2. This condition is satisfied by the buffer
size of 256 (28) samples. The ADC has a resolution of 1024 A different solution is therefore required if we want to keep
levels, which means that two bytes are required to store working with 256 samples. The real and imaginary parts
each sample, or 512 bytes for all of the samples. During of the complex numbers are still stored as integer values
the calculations there is also a requirement for a buffer to (2 bytes/sample) and converted into a ‘floating point’
hold the imaginary part of the numbers, since the Fourier variable before each mathematical operation and converted
transform is a conversion of complex numbers. This buffer back into integer format afterwards. The extra overhead
obviously needs to be the same size as the buffer for the real for these two conversions obviously makes the system a bit
part and therefore requires 512 bytes as well. In total we slower, but it is acceptable. The rounding error introduced by
therefore need 1024 bytes to store the values for the FFT, the conversion (1/65536) is a factor of 64 smaller than the
which is half of the available memory. quantization error of the ADC (1/1024) and can therefore
be ignored (see the functions ‘FFT_Int2Float ()’ and ‘FFT_
In order to use the maths library of the GCC compiler it Float2Int ()’ in the module fft_lib.c).

140
30 | December 2012 | www.elektor.com/magazine

Personal Download for Petar Crnojevic | copyright Elektor


AC Grid Analyser

for this filter. Note that there are some extra com-
ponents on this board that aren’t used in this
application. The board layout is available from
the associated web page for this article [3].
The AC line voltage is electrically isolated using
a AC power adapter (an ‘old fashioned’ type with
a transformer). The output of the adapter is con-
nected to terminal block X1. Since the filter has a
gain of one, a signal with an amplitude of 2 Vrms
(5 Vpp) is sufficient for the dynamic range of the
ADC in the ATmega. The output signal from the
transformer is not distorted in practice because
the transformer is effectively unloaded, as can
be seen in Figure 5 (the supply for the analyser Figure 3.
comes from a separate adapter or via the USB The PCB layout for the filter
connection). shield.

This way it’s possible to measure all harmonics


in the domestic AC line supply fairly accurately. multimeter to make a note of the line voltage
Potentiometer R10 should be used to reduce the and then adjust R10 so that the voltage shown
output signal from the adapter to about 1.7 Vrms on the display corresponds to that on the multi-
at C10 when the input voltage is at its nominal meter. We recommend that you use an AC power
level, i.e. 115 V or 230 V. You can use a reference adapter with an output voltage of less than 20 V.

In order to use the memory as efficiently as possible, the function can be applied to the real part of the samples (this
samples from the ADC are initially stored in the buffer for window function is necessary in order to satisfy the boundary
imaginary numbers. At that point in time this buffer isn’t conditions for the FFT).
used by the FFT routine.
An important aspect of the FFT implementation is the so-
called ‘bit reversal’ algorithm, which is used for addressing
the samples in the buffers. At first this may look like a simple
7 6 5 4 3 2 1 0 operation (the bits of the value of a register have to be put in
input reverse order, as shown in the figure above), but it isn’t very
easy to implement. Fast implementations use extra hardware
registers for this. Another alternative that is often used is a
table, but this requires a lot of memory and that is in limited
supply in a small microcontroller. The slowest method is to
shift all bits out of one register and shift them into another
output register in reverse order. This requires a loop with a counter
7 6 5 4 3 2 1 0 and a total of 16 shift operations. A combination of these
120546 - 17 methods is used here, which provides a good compromise
between memory usage and processing time. The byte is
Bit reversal algorithm split into two lots of 4 bits. Each of these 4-bit values is
reversed using a table and the results are then combined in
the right order into a byte again (see the function ‘fft_BitRev
The samples are then normalized and scaled, with the results ()’ in module fft_lib.c). The resulting time saved is 3 µs (2 µs
stored in the buffer for real numbers. instead of 5 µs) for each instance this function is called, but it
The imaginary buffer can then be cleared and the window does require an extra 75 bytes for the code.

141
www.elektor.com/magazine | December 2012 | 31

Personal Download for Petar Crnojevic | copyright Elektor


Projects

Figure 4.
The three boards next to
each other.

Development Environment there is also a Linux version available. With both


We haven’t used the standard Arduino program- versions you’ll get scripts that upload the execut-
ming environment for the software development. able to the Arduino. You will have to edit these
Instead, we’ve used the ‘GCC cross-compiler’ for files so that you have the correct serial port for
the AVR microcontroller series. The ‘cross-avr’ communications with the Arduino and the path
compiler can be installed under Linux from the to the executable on the PC.
repositories of the distribution, along with the We also need a program called ‘make’, which
associated ‘bin-utils’. For Windows you can install compiles and links the source code of all mod-
the ‘WinAVR’ [4] package. For both operating ules with the help of a make-file. This program is
systems we’ve used version 4.3.3 of the GCC included with WinAVR as well, and is also avail-
compiler [5]. For uploading the compiled hex file able for Linux.
we’ve used the program ‘avrdude’. This program To edit the source code you can use your pre-
is part of the WinAVR package for Windows, but ferred editor. Eclipse with the CDT plugin is rec-

Table 1. Software modules

Name of Name of associated


Description of functionality
source code file header file
avrfft.c (none) Main source code file
drw_fft.c drw_fft.h High-level draw functions for graph display on LCD
fft_lib.c fft_lib.h Definitions and functions for the FFT calculations
Definitions and functions for data acquisition and
freq_cnt.c freq_cnt.h
frequency measurement

lcd_driver.c lcd_driver.h Low-level functions and definitions for driving the LCD

menu.c menu.h Functions for reading the switches on the LCD shield

High-level functions for sending plots over the serial


plt_fft.c plt_fft.h
port

ser_avr.c ser_avr.h Low-level functions for sending and receiving data

std_avr.c std_avr.h Commonly used standard definitions and functions


Functions for timers and initialization of system
timer_0.c timer.h
timing

142
32 | December 2012 | www.elektor.com/magazine

Personal Download for Petar Crnojevic | copyright Elektor


AC Grid Analyser

Figure 5.
The AC grid voltage at
the primary side of the
transformer (blue) and the
voltage at the secondary
(yellow).

ommended, but Notepad++, Scite or just about Usage and display


any other editor should be fine. The display on the LCD shield used has a resolu-
tion of 131 x 131 pixels, of which a window of 80
Software vertical and 96 horizontal pixels is used to plot
The software has a modular construction and the spectrum. This results in a range of 0 Hz to
consists of a number of source code files (see 300 Hz (96 pixels x 3.125 Hz = 300 Hz) and 10
Table 1). pixels per 6 dB vertical. The FFT routine calculates
the spectrum for 0 to 400 Hz, but frequencies
start
Each C program begins with the function ‘main()’, above 300 Hz aren’t shown, although they are
which can be found in the file avrfft.c. When the sent to the PC via the serial port. The measured
program starts, it first initializes a number of AC line voltage and frequency are shown below init
global system variables and the hardware with the window, whereas the voltage is also shown
the help of the associated init functions. Next, the as an analog bar.
display on the LCD shield is cleared and the sys- sample
tem timer is prepared for later use. The program To the left of the display on the LCD shield are
then comes to an endless loop, where the system three buttons, which are used to configure the calculate
timer is set for a period of 2.5 s. This means that spectrum analyser. Their functions have been TRMS
a new cycle will start every 2.5 seconds. programmed as follows. When the analyser is
All of the steps will always take place in the same switched on it will immediately start its meas- frequency
measurement
order during each cycle. A simplified flow chart urements and will show a logarithmic plot of the
is shown in Figure 6. measured spectrum on its display. With a press
of the top button the display changes to a fre- scaling

Once the timer (timID) has indicated the start of quency plot with a linear scale along the vertical
the next cycle, the 256 samples for the FFT will axis. Another press of this button changes the window
function
be read in via the ADC with a sampling frequency display to the time domain (scope function) and
of 800 Hz. Next, the true effective value (TRMS) the first 96 scaled samples in the input buffer are
of the signal voltage is calculated. In the next shown (see Figures 7 and 8 for the different FFT
step the frequency of the signal at pin A4 on con- displays). Another press of the first button shows
nector ‘Analog In’ is measured using the built-in the complete contents of the input buffer after
display
comparator and Timer1 of the microcontroller. the window function has been applied. A fourth
The next steps (scaling the measured values and press switches back to the frequency domain
120546 - 14
applying the selected window function) prepare with a logarithmic scale, as it was when the cir-
the measured signal for the actual FFT calcula- cuit was first switched on. The bottom button is
tions. At the end the result of the calculations is used to select the type of FFT window function.
sent to the display of the LCD shield to show the When the analyser is switched on the default Figure 6.
spectrum of the signal. window type is Hanning. Pressing the bottom Flow chart of the program.

143
www.elektor.com/magazine | December 2012 | 33

Personal Download for Petar Crnojevic | copyright Elektor


Projects

a b

Figure 7.
Logarithmic (a) and linear
(b) plots of the frequency
domain shown on the
display.

button switches to a Blackman window and the 1372 bytes have been used of the available mem-
next press changes to a Hamming window. The ory (RAM 2048 bytes), of which 1024 bytes are
selected window function is always shown at the for the FFT buffers. This is about 2/3 of the avail-
bottom-right of the display: ‘N’ for Hanning, ‘B’ able memory. Only about 18 KB have been used
for Blackman and ‘M’ for Hamming. of the available program memory (ROM 32 KB).
Bearing in mind that the Arduino bootloader
The middle button turns the serial communica- needs about 2 KB, this leaves more than 10 KB
tion with a terminal on and off. When no data is of ROM for possible enhancements.
sent to the computer, the colour of the indica-
tor for the window function turns from yellow to Conclusions
green and back again after each spectrum has The system described here is a fully functional
been calculated. When the serial communication real-time FFT analyser for the AC grid supply,
is turned on the indicator turns from yellow to red. which uses a 256-point floating-point FFT to cal-
culate a new spectrum every 2.5 s and shows it
Performance graphically on a display. All this is implemented
Depending on the compiler settings, a calcula- on an Arduino platform with only one third of its
tion of the FFT can take up to 1 second in the program memory used.
most unfavourable condition without optimization
(-O0). The size of the compiled program is then This application shows how efficient and powerful
about 26 KB. With optimization turned on (-O2) an 8-bit microcontroller can be when it is used
the length of the executable shrinks to about to perform advanced mathematical calculations
18 KB and the calculation of the FFT takes only and display the results graphically, as well as
700 ms. The time taken to run through a complete including a user-interface and communications
cycle of the program (measuring the frequency, with a PC. But there are also limitations, such as
acquisition, calculating the TRMS, scaling, win- the available memory (which restricts the FFT to
dow function, calculating the FFT, scaling, plot- 256 points) and the time taken to perform the
ting on the display) takes about 2100 ms with calculations, although there is further room for
optimization (-O2). improvement.

A cycle time of 2500 ms was chosen so that the For the development of this project only open-
system has a predictable and constant response. source tools were used and the Arduino platform
This is obviously when the transmission of data to itself is completely open and freely available.
the serial port is turned off. A detailed description The software is modular and it is very easy to
of the ‘-O’ flags can be found in the documenta- use any of the modules in another project. The
tion for the GCC compiler. software has been published under the GPL V3

144
34 | December 2012 | www.elektor.com/magazine

Personal Download for Petar Crnojevic | copyright Elektor


AC Grid Analyser

a b

Figure 8.
Plots of the time domain
shown on the display (96
samples without a window
function (a) and 256
samples with a Hanning
window (b)).

license, which means you can use it in your own Internet Links
projects if you want to. The conditions of the [1] http://arduino.cc/en
GPL are published on the website for the ‘GNU
[2] www.sparkfun.com/products/9363
Operating System’ [6]. The full software package
and the board layout can be freely downloaded [3] www.elektor.com/120546
from the associated web page on the Elektor [4] http://sourceforge.net/projects/winavr
website [3]. [5] http://gcc.gnu.org/onlinedocs/gccint
[6] www.gnu.org/copyleft/gpl.html
Possible enhancements
Despite the extensive functionality that is already Also read: Grid Frequency Meter, Elektor January
implemented, it would be possible to add a cal- 2012.
culation of the THD (total harmonic distortion)
to the analyser.
Another enhancement would be a speech analyser
that calculates the spectrum of a speech signal
with the help of an FFT and shows the result on
the display. This does require that the bandwidth
of the lowpass filter is adapted. The ADC in the
ATmega328 can still operate at its full resolution
of 10 bits at a sample frequency of 15 kHz, which The author
is more than enough for a speech signal with a
After completing his studies in
bandwidth of about 5 kHz.
electric engineering at Berlin
Technical University, Fidelis Theinert
The speed of the system can be improved if the
worked for over 20 years at various
acquisition of new samples happens in the back-
companies in Germany and The
ground via interrupts whilst the information is
Netherlands as a hardware and
being sent to the display. This results in a 0.3 s
software engineer and has also
(256 samples/800 Hz sample frequency) improve-
taught at colleges. He currently
ment. It is also possible to drive the display more
teaches electric engineering at
quickly using the SPI interface of the ATmega328.
Haagse Hogeschool, Delft, The
Another enhancement is to have an elaborate
Netherlands. His expertise is in the
program on the PC to display the graphs, but
field of embedded systems and in
then we would no longer have a self-contained
particular in signal processing of
FFT analyser on an Arduino board.
video as well as audio signals.
(120546)

145
www.elektor.com/magazine | December 2012 | 35

Personal Download for Petar Crnojevic | copyright Elektor


MicroCONTROLLErs

Thou Shalt Communicate!


Wi-Fi/Bluetooth/USB shield
for Platino and Arduino
By Clemens Valens
(Elektor UK/INT Editorial)

Today all & can


also be used
sundry, devices stand-alone as a wire-
less connectivity module for
included, have to a PC. Note that you can’t have both
be “connected”, 24/7, all Wi-Fi and Bluetooth modules mounted on
the same board.
year round. You may have
a Facebook account, but Okay, I can’t deny it; I About the Wi-Fi module
have a reputation for exagger- Wi-Fi modules have been inexpensive, plen-
what about your oscilloscope? ating. Connecting anything to, errm, tiful and easy to find these past few years.
everything is probably a bit over the top. On The problem with many of them however
Does your multimeter tweet
the other hand, the board I’m about to pre- is their manufacturer who refuses to tell
enough? Is your soldering iron sent in this article is quite versatile. It can you how to use the module unless you
be equipped with a Wi-Fi module allowing agree to transfer a substantial amount of
linked in? You may be a non- you to connect an electronic device to the money to the manufacturer’s bank account
communicative nerd but your Internet; or with a serial Bluetooth module in exchange for a few thousand modules
it offers wireless connectivity to other serial or a customised software library for your
bench power supply may be Bluetooth capable devices, and a serial-to- host hardware. Luckily the Korean embed-
USB bridge enables old-skool wired serial ded Internet liberators from WIZnet have
craving for social interaction.
connectivity. decided to be less secretive about their
With the add-on board described products, and sell Wi-Fi modules you can
The board can be used as an add-on board actually use. I managed to get my hands
in this article you can hook up for microcontroller systems with Arduino- on two of their WizFi220 modules, and this
anything to everything, with or style extension connectors (Figure 1), like article is the result.
Elektor’s own Platino [1] (Figure 2), but it
without wires.

28 146 10-2012 elektor

Personal Download for Petar Crnojevic | copyright Elektor


Wi-Fi/Bluetooth/USB shield for Platino and Arduino

The WizFi2x0 modules (there is also a


WizFi210 module) operates with standard
802.11 b/g/n access points at speeds up
to 11 Mbit/s (802.11b), and they support
WEP, WPA, WPA2-PSK and Enterprise secu-
rity standards (802.11i). The modules have
some really cool possibilities. One of them
is the Wi-Fi serial port that’s remarkably
easy to use. Another nice feature is its lim-
ited access point (AP) capability that allows
direct connection to smartphones and tab-
lets like Android-based devices and Apple
gadgets.

The WizFi220 module measures


32 x 23.5 x 3 mm, has an on-board chip
antenna and a Hirose U.FL connector for an
external antenna. The module’s compatible Figure 1. Fully built up Wi-Fi shield on top of an Arduino Uno.
little brother, the WizFi210, consumes less Note the absence of R8 and R10.
power, but cannot provide as much out-
put power and hence has “less range”. 49
connection pads provide enough soldering and a serial terminal program. That’s why system does not have a USB serial port,
points to fix the module on a PCB in such a I decided to throw in a serial-to-USB con- like Platino. In the September 2011 edition
way that it will not easily come off. Most of verter. Since many Elektor readers may we presented BOB [3], a very convenient
these pads are probably not useful for unas- already have a so-called FTDI serial USB USB/serial bridge module, and I thought
suming users like us, being pitched at high- cable [2], I wanted to be able to use it it was a good idea to add it to my design
volume customers. For the others a simple with this module. On the other hand, hav- too. Now if I could add some clever wiring
two-wire serial connection is available to ing such a converter directly on the board it should be possible to connect the USB
transmit and receive data and to configure would also be useful, especially if the host converter to either the Wi-Fi module, the
the module.

As is often the case with such wireless mod-


ules, the WizFi2x0 can be controlled over a
serial link using AT modem commands (or
Hayes commands). Such commands con-
sist of human-readable strings a few charac-
ters long and starting with ‘AT’. The module
powers on in Command mode so you can
configure it. Once the setup is complete the
module can be switched into Data mode
with the O(nline) command (“ATO”). To
get it out of Data mode back to Command
mode three consecutive ‘+’ characters have
to be send (“+++”).

Design considerations
Some of the configuration commands, like
setting the baud rate of its serial port, are
more or less one-time only, and the mod-
ule remembers these settings. Since the
AT commands are human-readable it may
therefore be practical for the initial setup,
but also for experimenting, to be able to Figure 2. Fully built-up Wi-Fi shield on top of Platino,
communicate with the module using a PC also equipped with a 20x4 alphanumerical LCD.

elektor 10-2012 147 29

Personal Download for Petar Crnojevic | copyright Elektor


MicroCONTROLLErs

AD POWER
A5 A4 A3 A2 A1 A0 VIN GND 5V 3V3 RST IOREF
IC1 +3V3
K2 K1
MCP1825S-3302E/AB
+5V +3V3
6 5 4 3 2 1 8 7 6 5 4 3 2 1
2
JP5 *1 +3V3
R7 R11 R9 +5V
S1

1k

1k

1k
C1 C2 C3 C4

10u 100n 100n 10u


* D1 +3V3
LINK
* D3
10V 10V
ANT_BT
OK

+3V3
* D2 PVCC
2 17
VCC
RXD R8 R10 5 37
PIO0 RF_IO
6 3
PIO1 MOD2 AIO0

1k

1k
7 4
PIO2 AIO1
8 20
9 32 33 34 PIO3 USB_DP
VBAT VIN_3V3 VIN_1V8 VDDIO 9 21
PIO4 USB_DN
+3V3 RX 11 31
EXT ANT PIO5 SPI_MOSI
12 32
MOD1 PIO6 SPI_CSB
2 47 ASSOCIATED 13 33
JTAG_TCK GPIO28 PIO7 SPI_CLK
R12 R13 3 45 14 34
JTAG_TDO GPIO30 PIO8 SPI_MISO
4 44 15 22
47k

47k

JTAG_TDI GPIO31 PIO9 PCM_SYNC


5 43 36 25
JTAG_TMS UART0_CTS/GPIO24 PIO10 PCM_CLK
JP4 6 42 35 16
JTAG_NTRST UART0_RX/GPIO0 PIO11 RESET
4 7 41 TX_RADIO 27 28
ALARM1 UART0_RTS/GPIO25 UART_TX UART_RTS
3 37 40 RX_RADIO 26 30
UART1_RTS/GPIO27 UART0_TX/GPIO1 UART_RX UART_CTS
2 25 39 23 24
GPIO21/CLK_11MHZ UART1_TX/GPIO2 +3V3 PCM_IN PCM_OUT C5
1 46 38
GPIO29 UART1_RX/GPIO3 BTM-222
8 36 1 38
RTC_OUT1 UART1_CTS/GPIO26 GND GND 220n
10 35
DC_DC_CNTL EXT_RESET R2 R1 GND GND GND GND
11 30
ALARM2 SSPI_MOSI 10 18 19 29
WizFi220
1k

1k

12 29
ADC1 SSPI_CS JP1
13 28 JP3
ADC2 SSPI_CLK
14 27 +5V

GND
VCC
DTR

TXO

CTS
RXI

MSPI_MISO/GPIO6 SSPI_MISO T2 T1 1 2 3
15 26 R3
MSPI_MOSI/GPIO7 I2C_DATA/GPIO8 TX_MCU
16 24 1k
MSPI_CLKI/GPIO5 GPIO20/CLK_22MHZ 6 5 4 3 2 1
+5V
17
VOUT_1V8 GPIO19/CLK_44MHZ
23 2x VCIO CBUS4
19 22 BC547B +3V3
MSPI_CS0/GPIO4 PWM0/GPIO10 +3V3 CBUS3
20 21 +3V3
MSPI_CS1/GPIO13 I2C_CLK/GPIO9 CBUS2
TX_FTDI
GND GND GND GND TXD MOD3 CBUS1
R4 R5 RX_FTDI
1 18 31 48 RXD CBUS0
BOB-FT232R
1k

1k

RX_MCU 1
K5 *2 CTS RESET
RI DCD
T4 T3 3 4
R6 RTS DSR
3 2 1 5 6
1k DTR
GND
2x ICSP
TX_MCU
RX_MCU

BC547B JP2

1 2 3 4 5 6 7 8 1 2 3 4 5 6 7 8 9 10
K3 K4
0 1 2 #3 4 #5 #6 7 8 #9 #10 #11 12 13
GND
AREF
SDA
SCL

120306 - 11
IOL IOH

Figure 3. Complete circuit diagram of the Wi-Fi/Bluetooth/USB shield.


Refer to the text to find out which parts you need for each configuration.

host system or even disconnect it. Flexibil- rail, like Arduino, I thought it wise to add can be controlled with AT commands over
ity started creeping into the design. a voltage regulator to the system because a serial link; they run from 3.3 V; they have
The Wi-Fi module has to be powered from a the WizFi220 can consume up to 250 mA in similar dimensions and similar require-
3.3 V rail and it is not 5 V tolerant. The main active mode. As an example, the LP2985-33 ments. It is therefore not very difficult to
objective is to connect the Wi-Fi module’s voltage regulator on an Arduino Uno board add Bluetooth capabilities to the system,
serial port to a microcontroller. Such a sys- is specified for 150 mA, which is clearly not all you have to do is wire a usable Bluetooth
tem may run from 3.3 V, but if it is Arduino enough. Platino does not have a 3.3 V rail module in parallel with the Wi-Fi module
or Platino, then the microcontroller runs so this shield could provide it too. A jumper and that is what I did. I chose the Rayson
from 5 V. Level converters on the serial port should allow connection of the 3.3 V as pro- BTM220 module because I am at ease with
would therefore be necessary. The FTDI duced by the shield to the host system. it [4] and it is very cheap. We have used it
serial USB cable comes in two flavours, 5 V In this section you can replace all instances several times in Elektor too. [5][6]
and 3.3 V, and with level converters both of “Wi-Fi” by “Bluetooth” without having to
types would be usable. The BOB was not an change anything else and still have a coher- This completes the reasoning that deter-
issue because it can handle both levels. ent text. Indeed, many Bluetooth modules mined my design. Let’s now have a closer
Although the host system may have a 3.3 V are very similar to the WizFi module: they look at the circuit diagram (Figure 3). If you

30 148 10-2012 elektor

Personal Download for Petar Crnojevic | copyright Elektor


Wi-Fi/Bluetooth/USB shield for Platino and Arduino

COMPONENT LIST
K2 = 6-pin stackable header, 0.1” pitch,
Resistors vertical
R1–R11 = 1kΩ 5% 0.25W K5 = 6-pin (2x3) stackable header, 0.1”
R12,R13 = 47kΩ 5% 0.25W pitch, vertical
S1 = pushbutton, SPNO, through-hole,
Capacitors 6x6mm
C2, C3 = 100nF 50V, 5mm pitch Mod3 = BOB-FT232R USB-to-Serial
C5 = 220nF 50V, 5mm pitch Bridge, Elektor Shop # 110553-91, or
C1, C4 = 10µF 35V, 2.5mm pitch USB-to-Serial cable, Elektor Shop #
080213-71 (5 V) or # 080213-71 (3.3 V)
Semiconductors Mod2 = Rayson BTM22x Bluetooth
D1,D2,D3 = LED, green, 3mm diam. module
T1–T4 = BC547C, TO-92 case Mod1 = WIZnet WizFi2x0 Wi-Fi module
IC1 = MCP1825S-3302E/AB, 3.3 V volt- PCB # 120306-1 [1]
age regulator, TO-220 case

Miscellaneous
JP1 = 6-pin pinheader, 0.1” pitch,
JP2 = 4-pin pinheader, 0.1” pitch, straight
straight
K1,K3, K4 = 8-pin stackable header, 0.1” pitch,
JP3,JP4 = 3-pin pinheader, 0.1” pitch, straight,
vertical
w. 2 jumpers

have grasped my prose up to here, then the tors). For the Wi-Fi module the position of you have to pull it High. Finally, a low level
schematic will have only a few surprises. the LEDs is drawn correctly and you should on pin 7 (Alarm1) will wake up the module
not mount R8 and R10 (although nothing from deep sleep mode.
Putting it all together breaks or blows if you do), only R7 and R9 The level converters (R1-3, T1-2 and R4-6,
On the left side of figure 3 we have the Wi-Fi are needed now. T3-4) are straightforward and have been
module; on the right side we see the Blue- used before in Elektor. Transistors T1 and T4
tooth module. As you can see they share The WizFi module has some pins with spe- do the level conversion, but invert the sig-
the serial RX and TX lines, meaning that cial functions that you may want to use. nal at the same time. T2 and T3 correct this.
you should not mount both. It is either Since I didn’t use them I wired them to a The resistor values are not critical. I chose to
Wi-Fi or Bluetooth, never both. The mod- separate connector JP4. To enable you all use as many 1 kΩ resistors as possible.
ules also share two LEDs (D1 and D2); D3 to stack many shields on top of each other The RX and TX lines connect to JP1 and JP2.
is only used by the Wi-Fi module. A surprise I decided not to wire these signals to the These 3-pin jumpers may be a bit difficult
here may be R8 and R10. Maybe I could have Arduino extension connectors K1 to K4. If to understand at first sight, but when you
drawn a better schematic, but I didn’t, so you need them you can wire them your- follow the lines you should be able to fig-
I have to explain this in writing. It is actu- self. Pin 25 (GPIO 21) allows you to restore ure them out. With a jumper on JP1’s pins
ally very simple. The Wi-Fi module sinks the the module’s factory defaults. Pulsing it 1 and 2 the USB serial converter TX pin
current for the LEDs whereas the Bluetooth Low twice will restore the module to Lim- is connected to the Wi-Fi (or Bluetooth)
sources the current. As a result the LEDs ited Access Point mode, three pulses will module’s RX input. A jumper on JP2’s pins
have to be mounted the other way around restore it to Ad-hoc mode. Pin 46 (GPIO 29) 2 and 3 connects the USB serial converter
as drawn if you use the Bluetooth module. provides a hardware way of switching RX pin to the Wi-Fi (or Bluetooth) module’s
In that case you should mount R8 and R10 between Command (High) and Data TX output. This is the Configure-Module-
and not mount R7 and R9 (mounting R11 mode (Low). Pin 37 (GPIO 27) is needed With-PC mode. In these positions the USB
and D3 is useless unless you connect the when you want to upgrade the firmware serial converter cannot talk to the host MCU
LED to a free I/O pin on one of the connec- of the module (probably never). To do so system and it may be better to disconnect

Elektor Projects & Products


• Platino, a versatile board for AVR microcontroller circuits (October 2011); PCB # 100892-1 from Elektor Shop
• BOB-FT232R USB-to-Serial Bridge (September 2011); module, Elektor Shop # 110553-91
• USB-to-TTL Serial Cable (June 2008); cable, Elektor Shop # 080213-71 (5 V) or # 080213-71 (3.3 V)

elektor 10-2012 149 31

Personal Download for Petar Crnojevic | copyright Elektor


MicroCONTROLLErs

Listing 1.
Example of setting up the WizFi2x0 module as a serial server using AT commands. The commands are in boldface, the module’s responses
are in italic. Comments appear in brackets (). See the WizFi2x0 user manual for more commands.

AT (wake up)
[OK]
AT+NSTAT=? (what is your status?)
MAC=00:08:dc:18:97:76
WSTATE=NOT CONNECTED MODE=NONE
BSSID=00:00:00:00:00:00 SSID=”” CHANNEL=NONE SECURITY=NONE RSSI=0
IP addr=0.0.0.0 SubNet=0.0.0.0 Gateway=0.0.0.0 DNS1=0.0.0.0 DNS2=0.0.0.0
RxCount=0 TxCount=0
[OK]
AT+WPAPSK=germaine,”Philippe Noirette” (set SSID & pass phrase)
Computing PSK from SSID and PassPhrase...

[OK]
AT+NDHCP=1 (request IP number from DHCP server)
[OK]
AT+WAUTO=0,germaine (automatically connect to germaine)
[OK]
AT+NAUTO=1,1,,8011 (setup for auto connect: server, TCP, port 8011)
[OK]
ATA (start auto connect)
IP SubNet Gateway
192.168.2.7: 255.255.255.0: 192.168.2.1
[OK]

(now you can connect (telnet) to the module over Wi-Fi)

the board from the host system. The board because of the shield mounted on top of connectors for K1 to K4 you should mount
will be powered from the USB port. it. This depends on the Arduino board and them on the solder side if you want to stick
If you put a jumper on JP1’s pins 2 and 3 its revision. the board on an Arduino or Platino.
and on JP2’s pins 1 and 2 the USB serial con- K5 is not connected. I only put it on the JP1 and JP2 are positioned in such a way that
verter can be used to talk to the host sys- board to provide access to its signals if the the jumpers should always be in the same
tem. In this case you should not mount the host is Arduino. position, i.e. both to the left, both to the
wireless module (or the level converters) as right or both absent. Actually, you could
this kind of communication may disturb it. Turning practical leave a jumper on JP2 in case you wanted to
This is the USB-Shield mode. To turn a circuit diagram into a real shield listen in on the MCU wireless module com-
Not installing any jumpers will put the or extension board a printed circuit board munications. This can be useful for debug-
board in Wireless mode and the USB serial (PCB) is needed. I designed one and you can ging purposes.
converter has no use. However, you could download the Eagle CAD files from the web JP3 has a few contacts in common with the
leave it on and wire it to other pins on the page that accompanies this article [7]. The BOB serial-to-USB bridge, the idea being
extension connectors. This is for instance PCB is the size of an Arduino Uno except that that you use either a BOB or an FTDI cable,
useful in an Arduino-with-software-UART it is a rectangle without the funny-shaped not both.
configuration or in a host system with more short side of an Arduino Uno. All the compo- For full 3.3 V systems the level converters
than one UART. nents are through-hole types; only the Wi-Fi and voltage regulator can be left off. In this
and Bluetooth modules have surface mount case you have to place two bypasses (wire
Finally some remarks on details. The Reset footprints. JP5 and the Bluetooth module are bridges) from R3-JP1 to R2-T2 and from
button is mainly intended for Platino which located on the solder side of the board; the R6-MOD1 to R5-T3. Resistors R3 & R2 and
doesn’t have one. It is also useful when the other components should go on the compo- R5 & R6 are positioned in such a way that
Arduino reset button becomes inaccessible nent side. Note that if you use non-stackable the wire bridges are very easy to install and

32 150 10-2012 elektor

Personal Download for Petar Crnojevic | copyright Elektor


Wi-Fi/Bluetooth/USB shield for Platino and Arduino

Figure 4. The three main configurations next to each other. The Bluetooth module is not visible (middle board) because it is mounted on
the other side of the PCB. Note that this is an early revision of the PCB that has the same shape as an Arduino Uno board. The final PCB is
rectangular.

span only minimum distance. You will also forget to put a drop of solder on JP1 of host system responds to these. It is up to
have to short JP5 on the solder side of the the BOB to configure it for 5 V or 3.3 V you to provide a host that can communicate
board. operation. Add 3.3 V voltage regula- over a serial link.
As mentioned before, the orientation of the tor and reset push button to taste. The
LEDs depends on the wireless module. The LEDs can be useful too, but you will have Thanks go out to Joachim Wulbeck of WIZnet
component print on the PCB corresponds to wire them to a connector pin. You Europe GmbH (www.wiznet.eu) for providing
to the Wi-Fi module. If you mount a Blue- should short pins 2 and 3 of JP1 and pins the WizFi220 modules and the Wi-Fi antennas.
tooth module you should mount the LEDs 1 and 2 of JP2 with a jumper or a wire (120306-I)
D1 and D2 ‘the wrong way around’. Also, bridge.
only mount R7 or R8 and R9 or R10.
The 3.3 V voltage regulator can be installed Testing
lying on his back or standing up. In case of the Wi-Fi or Bluetooth configura-
tions connect the board to a USB port on the Internet Links and References
Three main configurations are possible (Fig- PC using an FTDI serial converter cable or the
[1] Platino: www.elektor.com/100892
ure 4), but you may have a need for other BOB serial-to-USB bridge. Figure out which
variants: COM port was created by the operating sys- [2] USB-to-TTL serial cable:
tem (OS) of your PC (make sure you have the www.elektor.com/080213
• Wi-Fi shield — no need for the BOB if appropriate drivers for your OS installed. If [3] BOB serial-to-USB bridge:
you own an FTDI cable, although you you haven’t you can get them, including the www.elektor.com/110553
can always install one. JP3 is available necessary documentation, at www.ftdi-
for connecting the FTDI cable. Mount all chip.com) and start a serial terminal pro- [4] Experiments with Rayson Bluetooth
LEDs as indicated on the PCB and do not gram. The WizFi220 module has a default modules:
mount R8 nor R10. Level converters will baud rate of 115 200 bits/s, for the BTM220 http://elektorembedded.blogspot.
be needed and the 3.3 V voltage regu- module this value is 19 200. Both modules com/2010/08/rayson-btm222-btm112-
lator probably too, depending on your use 8 bits, no parity and no hardware flow bluetooth-modules.html
host system. control. In the terminal type ‘AT’ followed [5] Bluetooth with the ATM18:
by the Enter key. If you set up everything the
www.elektor.com/080948
• Bluetooth shield — similar as the Wi-Fi right way the module should respond with
shield except for the LEDs. D3 has no ‘[OK]’ or ‘OK’. If this test succeeds you’re [6] Bluetooth for OBD-2:
function and you should not mount R7 in business. Refer to Listing 1 for a working www.elektor.com/090918
and R9 but mount R8 and R10 instead. Wi-Fi example (don’t forget to adapt the [7] Wi-Fi shield: www.elektor.com/120306
As an antenna you can use a piece of SSID and pass phrase to your network).
[8] Wi-Fi shield on Elektor Projects:
(insulated) wire of 31 mm long. For a BOB serial-to-USB bridge configura-
http://www.elektor-projects.com/pro-
tion the steps are more or less the same
• Serial-to-USB bridge shield — just the except that there is no point in punching in ject/wi-fi-bluetooth-usb-shield-for-ardui-
BOB without level converters. Do not AT commands in the terminal unless your no-platino.12252.html

elektor 10-2012 151 33

Personal Download for Petar Crnojevic | copyright Elektor


blog
shop
news

www app
Laser Projection with Arduino

By G. van Zeijts (The Netherlands)


ON/OFF
+24VDC
This device can project attractive laser
beam patterns on virtually any desired
7805 +5V
surface. The basic idea is to manipulate M1 M2

the path of a laser beam from a source M M


6VDC
such as a laser pointer. The beam is de- 10u
flected by a small mirror fitted to the
end of a motor shaft. The mirror is not +6VDC
10

1 CD+ 18
I1 O1
2 17
I2 O2
3 16
DC IN USB I3 O3
4 15
I4 O4
1 5 14 +5V
AREF I5 O5
MOD1 2 6 ULN2803 13
GND I6 O6
3 7 12
ARDUINO D13 I7 O7
28 4 8 11
RESET D12 I8 O8
27 5 GND 140mA
LASER
3.3V PWM/D11
26 6 9
5V PWM/D10
25 7
15R
GND PWM/D9
DIGITAL INPUT/OUTPUT

24 8
GND D8 25R
1 TIL119
23
VIN 5
9
D7
10
PWM/D6
22 11
AN0 PWM/D5
21 12
AN1 D4 2 4
ANALOG INPUT

20 13
AN2 PWM/D3
19 14 +5V
AN3 D2
18 15
AN4 TX > D1
17 16 10k
AN5 RX < D0
perfectly perpendicular to the axis of
10k
the shaft, so the originally linear beam
10k
path is converted into a cone. This cone
10k
strikes a second mirror on end of the +5V
10k
shaft of a second motor. The beam P1 P2
from the second mirror goes to the 10k 10k
10k

projection surface. 10k

The motor speeds are high enough that 10k


110166 - 11
viewers see a stationary figure instead
of a moving point of light, thanks to the

134 152 Elektor 7/8-2012

Personal Download for Petar Crnojevic | copyright Elektor


Share
bew

golb
pohs
swen

ppa www

persistence of human vision. from a 5-V supply voltage.


A wide variety of fascinat- The current is limited to ap-
ing figures can be created proximately 140 mA by a
by varying the speeds of the 15-ohm resistor. To avoid
motors. problems with pulse noise
from other supply rails, the
All of this is controlled by an Arduino is powered from a
Arduino microcontroller, us- separate 6 V source, such as
ing a program written in C. a rechargeable battery.
The software can be down-
loaded free of charge from The author used the po-
the web page for this article tentiometers to find vari-
[1]. ous combinations of mo-
tor speeds that produce
The speeds of the two motors attractive figures. They have
are set by potentiometers P1 been arranged in sequence
and P2 (which are fitted with to provide a show lasting
the red and blue knobs in the several minutes, with a re-
photo), whose positions are peating series of fascinat-
read by the microcontroller. ing figures in an automatic
The microcontroller converts loop. This is included in the
these two input signals into C code. This loop, as well
PWM outputs that determine as other pre-programmed
the speeds of the motors. figures, can be selected us-
The rest of the circuit dia- ing a set of four switches. A
gram is simple. The outputs short video demonstrating
of the Arduino MCU are fed the projected figures can be
directly to the ULN2803 driv- viewed on Elektor’s YouTube
er IC, which can handle up channel [2].
to 500 mA per channel. The
two motors (scavenged from (110166)
printers) operate at 24 V
with current consumption
Internet links
well below 500 mA. To be on
the safe side, two channels [1]
of the ULN2803 are wired in www.elektor.com/110166
parallel for each motor. [2]
The laser diode is energised www.youtube.com/
by the microcontroller im- ElektorIM
mediately after start-up and
is always on. It is powered

Caution: laser beam!


Always be careful when working with laser beams. The light emitted by the laser diode in a laser
pointer is relatively harmless and does not cause any problems if the beam passes quickly through
your field of vision, but you should never look directly into a stationary laser beam, even if
the laser power is very low.

Elektor 7/8-2012 153 135

Personal Download for Petar Crnojevic | copyright Elektor


AVR MultiTool
Measure, control, experiment
By Dr Andreas Eppinger (Germany)

You’ve just got hold of the latest whizzy IC and can hardly
wait to start experimenting with its functions. It is highly
likely that, like many modern devices, it will be controlled
over an I2C or SPI interface.
What would be useful at this point would be some
kind of versatile hardware tool based on a mi-
crocontroller that could talk to these in-
terfaces, as well as providing a few
digital I/Os and perhaps also a
PWM output. Ideally the tool
should be controlled using
a simple protocol over
a serial port, which
would allow a PC
to be used to is-
sue commands to it for maximum flexibility.
Purists can hack away using a terminal pro-
gram; those more comfortable with a graph- for which function.
ical user interface can easily rustle up something suitable.
In principle we might want to execute a set of commands Using a ready-made module means
in sequence, and this can be achieved using macros to au- that we are free to concentrate more on
tomate things. the software aspects of the project. Quite a lot needs
Most modern microprocessors, such as AVR microcontrollers, to be done in this direction: the firmware running on the Ar-
already include the peripheral interfaces needed to carry out duino needs to configure the Timer/Counter/PWM, I2C, SPI
such experiments. A ready-made processor board with all and UART modules, as well as set up the four analogue chan-
the required pins brought out on header strips would make nels and eight digital ports.
a good basis for all-singing-all-dancing hardware for meas- There are two ways in which the device can be controlled
urement, control and experimenting. For the ‘AVIOM’ (AVR from a PC.
Versatile I/O Module) the author chose an Arduino Nano
board (see photograph). This board basically consists of an - Use a terminal. A simple terminal emulator program suf-
ATmega328P and a USB interface for talking to a PC. In the fices, and the short commands make interactive control of all
lab we have also successfully tested the design using an Ar- functions easy. Sequences of commands can be defined as
duino Uno board. Alternatively, it is easy enough to construct macros, stored and then subsequently played back.
a compatible module with an ATmega328P and a few support
components. If a ready-made USB-to-serial TTL-level cable - Write a program. The hardware can be controlled using a
is used, the corresponding converter chip on the board can program written in Visual C# 2010 with a graphical user in-
be dispensed with. The do-it-yourself approach is made pos- terface, written specifically for this project by the author. The
sible by the fact that Arduino hardware and software is all user interface even allows Python scripts to be created and
open source: the hardware reference design, the program- executed to automate the operation of the hardware.
ming environment and a wealth of software examples are
available for free download from the Arduino homepage [1]. We will now look at the various parts of the software one by
The large figure shows which pin on the board is responsible one. For simplicity the AVIOM operates in one of a range of

96 154 Elektor 7/8-2012

Personal Download for Petar Crnojevic | copyright Elektor


Test

Reset button
RX + TX LEDs ICSP Header
Pin 13 (L) LED

TX Pin VIN Pin


PC RX Pin Ground Pin
Reset Pin Reset Pin
Ground Pin 5V Pin
Digital 2
Digital Digital 3
Digital 4 I 2 C - SCL
T1 Analog I2C
Digital 5 I 2 C - SDA
(Counter) Input
Digital 6 Pins Analog 3
Digital
Digital 7 Pins Analog 2
Analog
Digital 8 Analog 1
PWM Digital 9 Analog 0
Analog Reference
UART
MOSI 3.3V Output
SPI MISO Digital Pin 13 SCK SPI

Microcontroller Mini-B USB Jack 100576 - 11

different modes, such as ‘analogue’, ‘digital’ and ‘wait’. The lower-case letters. Each command consists of letters, nu-
operating mode is selected by sending a full stop character ‘.’ meric values, or a combination of the two. A complete list of
followed by a single letter abbreviation as follows. commands would occupy more space than we have available
here, but is available for download from the Elektor web-
.a Analogue site [2]. As a taster will we show here some of the commands
.d Digital available in analogue, system LED and wait modes.
.c Configuration
.e EEPROM access Analogue mode (.a):
.i I²C ‘1’ Display the value read from ADC channel 1
.l System LED ‘s’ Read all four of the ADC channels and display their
.m Macros values
.r SRAM access
.t Timer/Counter System LED mode (.l):
.u UART ‘h’ Switch system LED on
.w Wait ‘l’ Switch system LED off
‘s’ Read system LED status
In each mode there are three basic commands available:
help (‘?’), status (‘#’) and command line (‘%’). The help Wait mode (.w):
command ‘?’ causes the built-in help system to list the avail- hhh Wait for hhh (hex) milliseconds (hhh = 000 to FFF)
able commands. The ‘#’ command displays status informa-
tion. The percent character ‘%’ introduces a command line: Commands (and this goes also for mode-changing com-
this means that subsequent characters are collected until the mands) can be strung together into sequences, as hinted
end of the line (indicated by a CRLF) and then executed. at above. For example, the following sequence switches on
Within the commands themselves capitals are distinct from the system LED and then reads analogue channel 3: ‘.lh.

Elektor 7/8-2012 155 97

Personal Download for Petar Crnojevic | copyright Elektor


a3;’. A semicolon can be used to mark the end of a command The COM port that is used for communication with the AVIOM
sequence. module is set under ‘COM:Config’ at the upper right. Once a
The sequence ‘.mdA .ll.w100.lh.m’ defines a macro called ‘A’ connection has been successfully established the field turns
which turns the system LED off for 256 ms and then turns green and the rest of the user interface is activated; other-
it on again. The macro can be executed using the command wise the field remains grey.
‘.mA’.
The C# software uses the ‘ALab’ framework developed by
On reset, the system automatically executes the macro the author, which offers a very wide range of basic func-
called ‘0’. This macro tions for using a PC to
can therefore be used control operations in
to store all the com- a microprocessor net-
mands and settings work. Communication
that need to be execut- between the PC and
ed whenever the AVI- network nodes is done
OM system is booted. using messages which
are kept in queues. Re-
As mentioned above, plies received are pro-
the ‘multi-tool’ can also cessed and displayed in
be controlled by a pro- the AVIOM user inter-
gram running on a PC, face. The whole thing is
written by the author of course written with a
using Visual C# 2010. little help from threads.
The screenshot shows One of the most impor-
the graphical user in- tant features of the PC
terface in action. software is scripting. Scripts, written in the Python program-
The ADC values are shown at the top left under ‘Analog’. ming language, can be entered in the script text window. To
Pressing the ‘Scan’ button starts a cyclic reading of ADC val- do this, the AVIOM system uses the freely-available IronPy-

Automation using macros and scripts

ues: below to the left the cycle timing can be set in millisec- thon (‘Python for .NET’) implementation [3].
onds. The scripts are stored as text files in a workspace directory. A
The area marked ‘Digital’ shows the current state of the complete list of the script files found there is shown in the list
digital pins. Clicking on the relevant button switches a pin box in the middle of the screen. The working directory can be
between output, high-impedance-input, and input-with-pull- changed by clicking on the ‘C’ button.
up-resistor modes. Clicking on the display (when in output If a script is selected in the list box, the name of the file will
mode) changes the state of the output. appear in the text box above it and can be edited there if
Radio buttons are used to change settings in the area marked necessary. A copy of an existing script with a new name can
‘Timer Counter PWM’. In ‘Count_R’ mode the counter counts be created by editing the filename suitably and clicking on
rising edges, while in ‘Count_F’ mode it counts falling edg- ‘SaveAs’.
es. Clicking ‘TCN’ reads the current value in the counter and
clicking ‘Z’ resets it. If you have entered or edited a script in the large window at
In PWM or frequency generator mode (‘Fgen’) the ‘Frequen- the bottom right, you can try it out using ‘Exe’ or by double-
cy’ and ‘Duty Cycle’ fields are enabled. Since only integer clicking the script name in the list box. The file will auto-
values are allowed in the AVR’s ICR and OCR registers, the matically be saved first. Text output from the script (from
actual frequency and duty-cycle values are displayed, which ‘print’ commands) and error messages appear in the window
may differ somewhat from the values the user has entered. above. Make sure that ‘scan’ mode is not active when execut-

98 156 Elektor 7/8-2012

Personal Download for Petar Crnojevic | copyright Elektor


Advertisememt
ing scripts.
User script files are automatically provided with a header that USB STC 8051 MCU Programmer
imports a few handy name spaces and defines two special Free For 8051 Developers

objects: ‘s’ for system functions and ‘a’ for AVIOM functions. $0
The AVIOM object ‘a’ is an essential part of any script file. All
AVIOM commands that can be executed by a Python script SEN1060 GPS Module With Antenna
are implemented as methods of this object. (A click on the Small,Low Cost,Easy To Develope
‘Help’ button lists the built-in functions.) In many cases the
$50
methods return ‘true’ or ‘false’ to indicate whether the com-
mand was successful or not. A complete list of the AVIOM
script commands can be found in the document available (HMC5883L) 3 Axis Compass Module
Integrate Compass Easily
from the Elektor website.
The following example shows how commands can be exe- $12.5
cuted.
6P3P 7.5Wx2 Tube Amp Kit
#
CNC enclosure, hifi sound quality, easy to build
# Demo: TIMER COUNTER
# set pwm $136
#
f = 1.0
dc = 7.0
res = a.TCPpwm(f, dc)
print “PWM f = “, res, “ DutyCycle = “,dc,”%”

Further examples can be found in the ‘Demo’ workspace.


Note that the ‘I2C_..._PCA8581’ demonstration scripts only
work when a suitable EEPROM device is connected.

You will doubtless now want to try the system out for your-
self. The first step is to install version 1.0 of the Arduino
development environment [1].
The download from the Elektor website includes a directory
‘AVIOM_1_0’ which should be copied to any convenient place
on the computer. It is now a good idea to create a shortcut to
the file ‘..\AVIOM_1_0\AVIOM\AVIOM\bin\Release\AVIOM. FRONT PANELS & HOUSINGS
exe“. Cost-effective single units and small production runs

The next step is to launch the Arduino IDE and set the ‘sketch-
book’ location to point to the directory ‘..\AVIOM_1_0\AR-
DUINO’. Connect the Arduino board and select the ‘sketch’ Customized front panels can be
‘AVIOM_Arduino_1_0’, compile the program and load the hex designed effortlessly with the Front
Panel Designer.
file into the microcontroller.
The Front Panel Designer is available
A first test can be carried out using a terminal emulator free on the Internet or on CD.
program (with settings 115200 baud, 8N1) or using the au-
thor’s dedicated program, which can be run by clicking on · automatic price calculation
the shortcut. The demonstration scripts should appear in the · delivery in 5 – 8 days
script list. And away you go! · 24 - Hour-Service if r equired

(100576)
Sample price: 34,93 €
[1] www.arduino.cc plus VAT/shipping

[2] www.elektor.com/100576
[3] http://ironpython.net
Schaeffer AG · Nahmitzer Damm 32 · D –12277 Berlin · Tel + 49 (0)30 8 05 86 95 - 0
Fax + 49 (0)30 8 05 86 95 - 33 · Web [email protected] · www.schaeffer-ag.de

Elektor 7/8-2012 157 99

Personal Download for Petar Crnojevic | copyright Elektor


microcontrollers

Arduino on Course (1a)


Part 1a:
Welcome & Arduino 8-bit sound generation

Sound machines
By David Cuartielles (Spain) When talking about interactive
music instruments, I like to refer to them as
Practice makes perfect and in this the first of a series of arti- Sound Machines. They consist of three blocks: the data used
cles I will focus in presenting all the bits and pieces you need to generate the sound, the user interface, and the actual
to understand in order to play 1-bit sound from a digital pin sound engine.
on your Arduino board. We will start by looking at the easiest The data refers to the way the sound is used. It could be
way to create sound by means of a simple piezo buzzer or a generated, we could play back sounds from a sample collec-
speaker. I will then introduce the Arduino Tone Library, as a
simplified way to achieve the same functionality. And I will
close by introducing an advanced technique that allows play-
ing short sounds stored in the form of .wav files.
When it comes to the theory, you will be introduced to a
technique known as 1-bit Delta Sigma Digital to Analog con-
version, but don’t be scared by the name, the methods and
technologies are presented along with examples you can
easily reproduce with a minimal set of parts.

Get out your materials


If you aim at reproducing all the examples in this article you
need to have:
• an Arduino Uno board, though some of the other boards
in the Arduino line using ATmega328, ATmega168, ATme-
ga128 or ATmega256 will work as well;
• a USB cable to connect your Arduino to a computer;
• a piezo buzzer to play tones;
• alternatively a mini loudspeaker or headphones and a
socket to connect them to the Arduino board;
• a computer running the Arduino IDE and a tool called
SoundData for the IDE (check the download links in the
references section). Figure 1. Arduino UNO hooked up to a piezoelectric buzzer.

80 158 Elektor 7/8-2012

Personal Download for Petar Crnojevic | copyright Elektor


arduino on course

This article is going to lay the foundations for creating Interactive Sound Machines using
a standard Arduino Uno board. However, all the knowledge described here as well as
the code can be easily ported to Arduino Mega, Arduino Mini or any other member of
the Arduino 8-bit family. Jump the Arduino bandwagon, this stuff comes straight from a
creator of the platform!

tion, or just perform real-time sound alteration. Data is the we will move into using a proper loudspeaker to increase the
actual sound, the tones in a piano, or the bytes stored inside quality of the sound output.
the channels in a sampler.
The user interface defines the way the sound structures will The piezoelectric buzzer
be manipulated, or the mechanisms to modify the sound The contact microphone, also known as piezo buzzer is an
characteristics. The easiest example is the volume control electronic component made of a combination of two discs
usually implemented as potentiometer or rotary encoder. of different materials. One of them is metallic and the other
The UI is what the user manipulating the instrument has his/ one is usually ceramic, having the piezoelectric properties.
her hands (or mind) on to alter the sound engine’s behaviour. When applying a voltage to the component, the materials will
Finally, the engine defines the way data is displayed. It takes repel each other, producing an audible click. Making the volt-
the data and renders it as sound according to the control par- age difference zero will cause the materials to return to their
ameters introduced by the user through the UI. In our case, original position, again producing a click sound.
the engine is the Digital to Analog converter we are going to By applying a voltage of a sufficiently high frequency, the
implement via software. click produced by the piezoelectric will modulate into an au-
dible tone.
From blink to bee You can test this by connecting a piezoelectric buzzer to Ar-
The “Hello World” example to start using Arduino is making duino by wring its positive pin to, say, Arduino’s pin 8 and the
the LED on pin 13 blink. The code looks like this: negative pin to Arduino ground (GND), see Figure 1. Take
the previous code and modify the line that determines the
/* Blink pin the LED is connected to:
Get the LED on pin 13 to go on/off
http://arduino.cc
*/ int ledPin = 8; // define the pin for
// your Speaker or Piezoelectric
int ledPin = 13; // define the LEDs pin
When running this program you will hear the piezoelectric
void setup()
{ clicking once per second, which is the times when the voltage
pinMode( ledPin, OUTPUT ); changes at its pins. You can modify the code to make the delay
// configure the pin as output between clicks. The smaller the delay, the more the clicks will
}
merge into a modulated tone. Try to change both lines in your
void loop() program affecting the time between clicks to be:
{
digitalWrite( ledPin, HIGH ); delay( 1 );
// turn the pin on
delay( 1000 ); // wait 1sec
digitalWrite( ledPin, LOW ); Now you will be hearing a sound with a frequency of 500 Hz.
// turn the pin off You will also notice the sound to be louder due to a property
delay( 1000 ); // wait 1sec of the piezoelectric components. They resonate in the kilo-
}
hertz range, at least the ones we find commercially available,
as they are designed to be buzzers or contact microphones.
The example is self explanatory. With little changes we can If you want to experiment further in sound production with
use the same example to start playing sound out of our Ar- this technique, I would encourage you to not use the de-
duino. We will be using a piezoelectric buzzer and later on lay() function from Arduino. The reason for this is that you

Elektor 7/8-2012 159 81

Personal Download for Petar Crnojevic | copyright Elektor


microcontrollers

will need a better time-resolution to produce a richer selec- In other words, period is the inverse of frequency and vice-
tion of tones. The function delayMicroseconds() is much versa. In this way, if we want to know the delay needed to
more suitable to sound production, as it is three orders of play say, the A4 tone using Arduino, we need to do a bit of
magnitude more accurate. maths again like:
Adding all these changes to the original Blink program, will 1
give us the Bee program: p= = 0.002272 s = 2.272 ms = 2272 µs
440
/* Bee If we want the program “Bee” to play A4, we need to modify
Make a piezoelectric oscillate
on pin 8 it so that the total time in both calls to delayMicrosec-
http://arduino.cc onds() adds up to 2272 microseconds.
*/
digitalWrite( piezoPin, HIGH );
int piezoPin = 8; // define where the delayMicroseconds( 1136 );
// piezoelectric is connected digitalWrite( piezoPin, LOW );
delayMicroseconds( 1136 );
void setup()
{
pinMode( piezoPin, OUTPUT);
} The different tones within a scale can be mapped to time-
delays so that they can be played using Arduino. Table 1
void loop() shows a full octave.
{
digitalWrite( piezoPin, HIGH );
delayMicroseconds( 1000 ); Table 1. Available musical notes / tone frequencies
digitalWrite( piezoPin, LOW ); Tone Frequency [Hz] Period [µs] Delay [µs]
delayMicroseconds( 1000 );
} C4 261.63 3822 1911
D4 293.66 3405 1703
E4 329.63 3024 1517
Playing tones
According to Fourier’s Law every sound is the result of adding F4 349.23 2863 1432

a series of sinusoidal sound sources having different phases G4 392.00 2551 1276
and amplitudes. We could say that sine and cosine waves are A4 440.00 2272 1136
the fundamental components of sound. B4 493.88 2025 1012
C5 523.25 1911 956
Unfortunately microcontrollers, and the one on the Arduino
Uno is not an exception, cannot imitate the sinusoidal shape
perfectly. We can anyway produce square waves by repeat- Arduino’s tone library
edly switching a pin HIGH and LOW. The tones produced in There is more to sound playing than just the tone. Musical
this way have the same frequency, but are not clean as they scores are expressed in notes, which are the tones played
add components to the pure sinewave. In musical terms, the for just a certain amount of time. In order to simplify the
instrument making square waves has a different tonal char- possibility of playing basic melodies using Arduino, we added
acteristic than the one making sinusoidal ones, although the a library to the system that handles all the math explained
tones proper are the same. so far in this article, as well as note durations. Now that you
The only issue we find here is that sound is expressed in understand how to play a tone at a relatively low level, I think
frequency (hertz or Hz) while microcontrollers work with it is convenient to introduce this abstraction to make easier
time. The total amount of time a HIGH-LOW oscillation lasts for you to create programs playing sound.
is what we call the period (seconds). There is a relationship
between period p and frequency f as expressed in the follow- This library is called tone and brings in a function allowing
ing formula: playing a tone. In the background this is done by controlling
1 1 some of the internal timers in the processor. One timer takes
f = → p= care of the tone itself, while the other monitors its duration.
p f There are two functions to play sound, called the same, but

82 160 Elektor 7/8-2012

Personal Download for Petar Crnojevic | copyright Elektor


arduino on course

with a different amount of parameters.


// assign the note to the speaker
tone( speaker, theTone, time );
tone( pin, frequency ); }
// play a tone
tone( pin, frequency, duration );
// play a note, duration in milliseconds
Chained melodies
It’s “awesome and stuff” to play a short melody at some
point during the execution of a program. A melody consists
You should note how time is measured. The function’s argu- of notes and silences. Here we are going to see how to play
ment ‘duration’ will play the note for a certain number of a melody stored as an array of numbers. Inside the Arduino
milliseconds (ms). If you want to have a function counting IDE there is an example dealing exactly with this. Open the
the time in a way that is closer to how it is made in musical program under File → Examples → 2.Digital → toneMelody:
scores, you will have to decide how long the different notes
/*
/* we define durations as numbers Melody
/ between 1 and 7:
1 – whole note - 1 unit Plays a melody
2 – half note - 0.5 units [...]
3 – crotchet - 0.25 units */
4 - quaver - 0.125 units #include “pitches.h”
5 – semi quaver - 0.0625 units
6 – demi semi quaver - 0.03125 units // notes in the melody:
7 – hemi demi semi quaver - int melody[] = {
0.015625 units NOTE_C4, NOTE_G3, NOTE_G3, NOTE_A3,
*/ NOTE_G3, 0, NOTE_B3, NOTE_C4};
void playNote( int speaker,
int theTone, int duration ) // note durations: 4 = quarter note,
{ // 8 = eighth note, etc.:
// we give for granted that the half int noteDurations[] = { 4, 8, 8, 4, 4,
// note lasts 0.5 seconds 4, 4, 4 };
long time = 500 / pow( 2, duration-1 );
void setup() {
// assign the note to the speaker // iterate over the notes
tone( speaker, theTone, time ); // of the melody:
} for( int thisNote = 0; thisNote < 8;
thisNote++ ) {

will be. The following code assigns durations to the different // to calculate the note duration,
notes considering that the basic note lasts 0.5 seconds. // take one second divided by the
The function above could also be written in a way that would // note type. e.g. quarter note =
// 1000 / 4, eighth note = 1000/8,
make use of the more common variable of the beats per minute // etc.
(bpm). In that way we could make the instrument play at dif- int noteDuration = 1000 /
ferent speeds depending on the desired tempo for the melody. noteDurations[thisNote];
tone( 8, melody[thisNote],
noteDuration );
/* we define durations as numbers
/ between 1 and 7:
// to distinguish the notes, set a
[...]
// minimum time between them.
*/
// the note’s duration + 30% seems to
void playNote( int speaker, int theTone,
// work well:
int duration, int bpm )
int pauseBetweenNotes =
{
noteDuration * 1.30;
// menmotecnic: 120 bpm - - >
delay( pauseBetweenNotes );
// 1000 milliseconds for half note
// source http://bradthemad.org/guitar/
// stop the tone of playing:
// tempo_calculator.php
noTone( 8 );
long time = ( 1000 * bpm / 120 ) /
}
pow( 2, duration );

Elektor 7/8-2012 161 83

Personal Download for Petar Crnojevic | copyright Elektor


microcontrollers

} int duration, int bpm )


} {
// menmotecnic: 120 bpm - - >
void loop() { // 1000 milliseconds for half note
// no need to repeat the melody. // source http://bradthemad.org/guitar/
} // tempo_calculator.php
long time = ( 1000 / bpm * 120 ) /
pow( 2, duration );
You will notice that the melody is stored in two arrays: the // assign the note to the speaker
notes are in one, while the note durations are in a different tone( speaker, theTone, time );
one. Durations are expressed differently from what we saw delay( time*1.30 ); // add 30% for the
earlier. Our previous example was using durations expressed // silence between notes
}
in the way it is done in music.
The first command in the program includes a file called void setup() {
pitches.h that comes as part of the code into a different tab for( int thisNote = 0; thisNote
within the example. The file sadly is too large for printing here. < 8; thisNote++ ) {
playNote( 8, melody[thisNote],
It includes a series of constants representing the frequencies noteDurations[thisNote], bpm );
for each tone. In that way, the constant NOTE_A4 represents }
the numeric value 440, or 440 Hz for the note A4. }

/***************************************** void loop() { // let’s listen


* Public Constants // to it just once
****************************************/ }

#define NOTE_B0 31
#define NOTE_C1 33 Now try including a potentiometer or any other analog sen-
#define NOTE_CS1 35 sor to modify the BPM rate and in that way play the melody
[...]
#define NOTE_G4 392 at different speeds.
#define NOTE_GS4 415 Our next instalment begins with playing 1-bit notes and
#define NOTE_A4 440 culminates in a method to make Arduino play a sound with
#define NOTE_AS4 466 barely more than a single line of code.
[...]
#define NOTE_CS8 4435 The files for this month’s instalment may be found at: www.
#define NOTE_D8 4699 elektor.com/120366
#define NOTE_DS8 4978 (120366)

The above example can be modified to make use of the


The Author
beats-per-minute (BPM), what will allow changing the speed
David Cuartielles (1974,
at which the melody plays. We just need to include the Zaragoza, Spain) is currently
playNote function we made earlier and modify the way we Head of the Prototyping
express the durations to be expressed in the same terms as Laboratory at K3, Malmö
University, Sweden, and owns
in our new function:
a Research Fellow position
in Interaction Design at the
#include “pitches.h” Medea Research Studio. In
2005 he co-authored the
int melody[]= { Arduino prototyping platform.
NOTE_C4, NOTE_G3, NOTE_G3, NOTE_A3, David has a permanent
NOTE_G3, 0, NOTE_B3, NOTE_C4}; interest in embedded
int noteDurations[] = { 2, 3, 3, 2, 2, 2, electronics and education,
2, 2 }; having taught and given lectures at several institutions
int bpm = 120; around the world including: UCLA, NYU, Samsung Art and
Design Institute, Copenhagen Institute for Interaction
void playNote( int speaker, int theTone, Design, Tecnologico de Monterrey, and others.

84 162 Elektor 7/8-2012

Personal Download for Petar Crnojevic | copyright Elektor


Microprocessors

Arduino on Course (1b)


Part 1b: an Arduino sound player
By David Cuartielles (Spain) Sound spectrum
The sound spectrum is a representation of the
energy transmitted by, say, a loudspeaker as a function
1-bit Sound Generation … What?!? of frequency. Looking at the spectrum of sound, you do not nor-
Up to this point, you have been experimenting with code that can mally get a clear view of the sound itself as in Figure 1. Rather, the
be generated directly out of the Arduino language. Now we pro- graph represents the amount of energy for different discrete fre-
ceed with methods of hacking the processor on the Arduino Uno quencies within a certain amount of time. Typically we represent
(the ATmega 328) at a low level, aiming to create a block of code the spectrum for a whole song (see Figure 2).
that will use sound data coming from a WAV file for storage inside Alternatively, we can look at the spectrum of just 0.5 seconds of a
program memory — and playing back of course. song. The smaller the time frame we’re watching, the better the
The method used is not trivial. A good way to start is to look at spectral representation of the sound generated at that very instant.
sound based in terms of its spectrum rather than from any sort of The shape of the wave generating that spectrum can be anything.
representation in time. As a matter of fact, two different sound signals can generate very
similar spectra.
Thus, the size of the time frame determines the similarity of that
signal is to the original one. The human ear is stimulated by the
energy content of the sound, therefore two signals having identi-
cal spectra will be perceived as the same, but only if the time reso-
lution is small enough. This is key to the whole science of sound
compression: the ability of getting signals that are ‘good enough’
for us to understand the sound, even if the sound is very different
from the original one.
This is also the way 1-bit sound generation works [1]. We can gener-
ate sound by having a pulse width modulated (PWM) signal whose
average energy level is similar enough to the one of the original
signal.
This mathematical trick allows generating medium-quality sound
by a microcontroller. The following paragraphs show how to take
advantage of this. We will start from a WAV file that can be recorded
with your computer. Next, we’ll filter it, and transform it into an
Figure 1. Recording of human speech saying “ta-te-ti-to-tu”. array of numbers for storing inside Arduino.

Optimal digitalisation and filtering


Many different tools exist for recording sounds. I can only recom-
mend the use of Audacity [2], an open source and free software tool
that provides most of the options needed to reproduce sound with
microcontrollers (Figures 1 and 2 are screenshots from Audacity).
Before you move on, you should filter the sound. I use a low-pass fil-
ter with a 4 kHz roll-off frequency. The Arduino sound player shown
here uses a sampling frequency of 8 kHz (i.e. 8000 samples per sec-
ond), which means that if there were sound components above
4 kHz in your original file, you would hear artefacts in the sound.
With microcontrollers it is possible to reproduce reasonable quality
sound, however these chips are limited in terms of memory space.
Consequently you need to use sound formats of lower quality that
will allow generating several seconds of sound without the use of
external memory chips.

A sound format that can be of great use is the 8-bit PCM WAVE (also
called Microsoft unsigned 8 bit). This sound format is of sufficient
quality to reproduce, for instance, recorded human voice. Thus,
the file you’ll need in the following step of the process should be
Figure 2. Spectrum of human speech saying “ta-te-ti-to-tu”.

54 163 09-2012 elektor

Personal Download for Petar Crnojevic | copyright Elektor


Arduino on Course

exported as:
mono (1-channel),
8-bit, PCM WAVE.

Converting sound to text Figure 3. Dialog Window to import WAV files into your Arduino
Let’s look at importing your sound file as a header file that you can sketches as header files.
add to your Arduino sketch. Since the ATmega 328 microcontroller
has 32 KB of Flash memory space, you can use part of that space to
store the sound file. You can store large chunks of data into memory Playing back a sampled sound is not obvious, since it requires
arrays by using the Progmem library from Atmel’s toolchain. 8-bit changing some of the features of the Arduino core works. There
exist libraries for Arduino Uno that hide all of the complexity of mak-
const unsigned char sounddata_data[] PROGMEM = {128, ing this type of sound player. However, I want you to take a chance
128, 128, and see how this is done at low level, like in Figure 4.
[...] The trick that can get Arduino to play a sound sample is the so-
69, 62, 59, 57, 52, 50, 56, 65, 74, 86, 96, 109, 116, }; called Fast PWM, a feature of Atmel’s Atmega family (other brands
have it as well, but Arduino Uno runs on Atmel chips). There is a reg-
sound is nothing but a stream of numbers between 0 and 255. It can ister that allows running PWM at the amazing rate of up to half the
be declared like: clock speed. This allows nice things to be done like playing sound
I have created a tool for Arduino’s IDE that enables you to open WAV with 1-bit outputs. The only limitation of Fast PWM is that it oper-
files and import them directly as part of your code. You can down- ates at a resolution of 8 bits only. That’s why you should encode
load it from the link mentioned in the reference list, and add it to your sound files at 8 bits.
your sketchbook folder. Place the file into your Arduino sketchbook
folder and uncompress it there. To get it all to work, you use two out of the three internal timer reg-
It will add the following folder to your sketchbook: tools/SoundData istries inside the processor:
After rebooting the IDE, you will see a new item under the Tools
menu called SoundData. Clicking on it produces a dialog window
enabling you to select a WAV file (see Figure 3). The second but-
ton, titled Generate Code will open the WAV file, check whether
it is properly encoded, and add a new tab to your code titled

// soundData for your Arduino sound project


// automatically generated data
// - original sound file:/development/tmp/matis.wav
// - sampleRate:8000
// - encoding:8 bits
// - channels:1

const int sounddata_length = 7969;

const signed char sounddata_data[] PROGMEM = {127, 127,


127, 127, 127, 127,
[...]
69, 62, 59, 57, 52, 50, 56, 65, 74, 86, 96, 109, 116, };

sounddata.h. This new file contains everything you need to play


your WAV file as a 1-bit sound. The file will look like this:
But keep on reading before pressing the Generate Code button on
the dialog window, because there is more to it!
Figure 4. View of the “ta-te-ti-to-tu” sound file within the Arduino
The Sound Player IDE after importing it with the SoundData tool.

elektor 09-2012 164 55

Personal Download for Petar Crnojevic | copyright Elektor


Microprocessors

// this is the condition of reaching the last


sample
stopPlayback();
} else {
// Ramp down to zero to reduce the click at
the end of playback.
OCR2A = sounddata_length + lastSample
- sample;
}
}
else {
// OCR2A is the register in memory that will
push
// PWM at high frequency to pin 11
// pgm_read_byte reads data out arrays stored in
Figure 5. Screendump of the basic sound player after automatically program memory
generating the code. OCR2A = pgm_read_byte(&sounddata_data[sample]);
}

• The first clock operates at SAMPLE_RATE and is used to read the // increase the sample count
next value from the computer generated sounddata_data array. ++sample;
This value sets up the duty cycle for the PWM stream being out- }
put through pin 11.
• The second timer ticks at 62500 times per second (16000000 /
256), i.e. much faster than the playback rate (default SAMPLE_ low level commands in order to override the timers. I will describe
RATE is 8 kHz). As explained earlier, this generates a digital sig- the functions one by one. Let’s start with TIMER1:
nal whose spectrum is very similar in shape to that of the origi- ISR is the name for the interrupt handling function inside the micro-
nal sound file. In other words, by means of increasing the PWM controller. An interrupt is an event that will tell the chip to stop
frequency, the generated signal gets a spectrum that resembles doing anything it is into at the time and attend a certain event. Pro-
the one of the sound. In many applications this is more than cessors can have both internal and external interrupts. The internal
enough to play sound at a low price. ones are timers, while the external ones happen when certain pins
change from HIGH to LOW or vice versa.
Note: by adding this code to your Arduino sketch you will be over- This one instance of the ISR function is taking care of the arrival of
riding some of the basic commands of the Arduino language. E.g. internal TIMER1 events. Every time TIMER1 ticks, this function will
the PWM will stop working at some of the pins, and the delay() func- do the following:
tion will not operate as expected. This will only affect this sketch.
The first time this technique was shown in the Arduino world was • increase the counter used to address the sound data;
back in 2008. Michael Smith published an example on the Arduino • check whether the end of the sound data array is reached;
playground that would play the sound of a MAC computer boot- • if not at the end, load the next sample from the array;
ing up, upon reset of the Arduino Diecimila board. Michael’s code • if at the end, fade the sound to zero.
was based upon the work of many others which I have included as
references [3].
void startPlayback()
Just to make it easy, the SoundData tool will not just generate the {
sound information, but also include the code to the basic sound- pinMode(speakerPin, OUTPUT);
playback example inside your sketch. Beware, make sure your
sketch is empty when calling the tool, as it will overwrite anything // Set up Timer 2 to do pulse width modulation on
on your IDE. the speaker
The basic program to play 1-bit sound (Figure 5) includes a lot of // pin.

ISR(TIMER1_COMPA_vect) { // Use internal clock (datasheet p.160)


if (sample >= sounddata_length) { ASSR &= ~(_BV(EXCLK) | _BV(AS2));
if (sample == sounddata_length + lastSample) {

56 165 09-2012 elektor

Personal Download for Petar Crnojevic | copyright Elektor


Advertisement
PicoScope ®

// Set fast PWM mode (p.157)


4-CHANNEL
TCCR2A |= _BV(WGM21) | _BV(WGM20);
TCCR2B &= ~_BV(WGM22); PC Oscilloscope
// Do non-inverting PWM on pin OC2A (p.155)
// On the Arduino this is pin 11.
TCCR2A = (TCCR2A | _BV(COM2A1)) & ~_BV(COM2A0);
TCCR2A &= ~(_BV(COM2B1) | _BV(COM2B0));

// No prescaler (p.158)
TCCR2B = (TCCR2B & ~(_BV(CS12) | _BV(CS11))) |
_BV(CS10);

// Set initial pulse width to the first sample.


OCR2A = pgm_read_byte(&sounddata_data[0]);

// Set up Timer 1 to send a sample every interrupt.


cli();

// Set CTC mode (Clear Timer on Compare Match)


(p.133)
// Have to set OCR1A *after*, otherwise it gets
reset to 0!
TCCR1B = (TCCR1B & ~_BV(WGM13)) | _BV(WGM12);
60 - 200 MHz bandwidth
TCCR1A = TCCR1A & ~(_BV(WGM11) | _BV(WGM10)); 128 MS deep memory
// No prescaler (p.134) 1 GS/s real-time sampling
TCCR1B = (TCCR1B & ~(_BV(CS12) | _BV(CS11))) |
_BV(CS10);
Advanced digital triggering
200 MHz spectrum analyzer
// Set the compare register (OCR1A).
// OCR1A is a 16-bit register, so we have to do this Function generator or AWG
with
// interrupts disabled to be safe.
OCR1A = F_CPU / SAMPLE_RATE; // 16e6 / 8000 =
2000

// Enable interrupt when TCNT1 == OCR1A (p.136)


TIMSK1 |= _BV(OCIE1A);
Spectrum analyzer. Serial decoding
lastSample = (CAN, FlexRay, Lin, SPI, I2C, UART)
Full SDK and advanced triggers
pgm_read_byte(&sounddata_data[sounddata_length-1]);
sample = 0;
sei();
}

Both timers TIMER1 and TIMER2 are initialized as part of the startPlay-
back function. Let’s see how what looks like: Mask limit testing, Colour persistence modes,
measurements and math channels all as standard and free updates
Although the sequence of low level commands is explained in the
ALL MODELS INCLUDE PROBES, FULL SOFTWARE AND 5 YEAR WARRANTY.
code, a summary of it may be useful for the non-expert:
• turn the pin for the speaker into an output;
• configure the board to use the internal clock for this;
• initialise Fast PWM mode;
www.picotech.com/PS164
elektor 09-2012 166 57

Personal Download for Petar Crnojevic | copyright Elektor


Microprocessors

from a program to play sound this way. In this case, the example by
default will call startPlayback() within setup. In this way the sound
will be played just once.

Closing words
This article is an introduction to different ways of producing sound
using Arduino. You have seen how to play tones by means of basic
Arduino functions. Libraries have been described that simplify the
way basic melodies can be played using inexpensive piezo buzzers.
Finally you got a sneak peek at the programming behind Fast PWM
to generate 1-bit sound.
Figure 6. Arduino Uno is perfectly capable of driving a small
loudspeaker directly.
All code chunks and tools discussed here are packed into a ZIP file
[4], including properly formatted sound files for you to try all the
examples. I also created a new tool for the Arduino IDE that will
• configure TIMER2 to run the PWM that will play the sound, the help you with the importing of short WAVE files into Arduino’s pro-
way to set the duty cycle to the PWM is by changing the value gram memory. The tool enables you to load sounds and play them
of the register called OCR2A; back, change their sample rate, play them backwards or scratch
• load the first sound sample into OCR2A; the sound. In terms of hardware, you connect your loudspeaker as
• stop the interrupts for a second – cli()– so that we can config- shown in Figure 6.
ure the TIMER1 without breaks;
• configure TIMER1 to tick for picking up the next sample; But don’t stop here! There is a lot to explore — for instance using
• load the last sound sample; pin 3 in parallel with pin 11 to produce stereo sound. Or create 8-bit
• restart the interrupts – sei(). synthesizers with the ability of mixing four sound lines on a single
channel. What about transforming your Arduino board into a MIDI
void stopPlayback() activated soundcard?
{
// Disable playback per-sample interrupt. Happy hacking. See you in a month.
TIMSK1 &= ~_BV(OCIE1A); (120427)

// Disable the per-sample timer completely.


TCCR1B &= ~_BV(CS10); References
[1] 1-bit Sigma Delta DA Converters:
// Disable the PWM timer.
www.digitalsignallabs.com/presentation.pdf
TCCR2B &= ~_BV(CS10);
[2] Audacity, the free and open source sound studio:
digitalWrite(speakerPin, LOW); audacity.sourceforge.net
} [3] Various references from the example by Michael Smith:
Arduino reference on the use of the tone library:
arduino.cc/en/Reference/Tone
In a similar fashion, you need to have a function that will stop the Original article on the Arduino Playground:
timers of counting this way once the end of the sound is reached.
arduino.cc/playground/Code/PCMAudio
This leaves you with a series of functions you can call anywhere
www.uchobby.com/index.php/2007/11/11/arduino-sound-
part-1/
void setup() www.atmel.com/dyn/resources/prod_documents/doc2542.pdf
{
www.evilmadscientist.com/article.php/avrdac
startPlayback();
} http://gonium.net/md/2006/12/27/i-will-think-before-i-code/
http://fly.cc.fer.hr/GDM/articles/sndmus/speaker2.html
void loop() www.gamedev.net/reference/articles/article442.asp
{ [4] Example files for this article:
// do nothing www.elektor.com/120427
}

58 167 09-2012 elektor

Personal Download for Petar Crnojevic | copyright Elektor


Microprocessors

Arduino on Course (2)


Part 2: read (awfully) remote sensors
using GSM / GPRS
This month we’ll explore the
possibilities offered by GSM
and GPRS communication for
your projects. We will
link concepts like the
Internet of Things (IoT)
or the Machine To Machine [1] last year where
they envisioned that
(M2M) business in order to by 2020 there would be 50
billion connected devices. That
understand what you can achieve
would mean that most of our home
all by yourself in a short time. appliances are connected to the Internet:
fridges and microwaves, alarm clocks and TVs,
the elevator and the stove. But also all the other devices that
By David Cuartielles (Spain) surround us like cars, streetlights, or shopping carts (the push-
able type, not the icon or applet).
M2M (machine-to-machine) is concerned with the connectivity
Shopping list between devices using wireless, wired or hybrid communication.
In terms of hardware, here’s what you need to be able to replicate In a sense, M2M makes IoT (Internet-of-things) possible as it offers
the experiment discussed in this instalment: the infrastructure for devices to gather data and transmit it through
a network to a remote location. For some people M2M is a synonym
• Arduino Uno board; of telemetry in whatever form, but in recent years the concept has
• Arduino GSM shield (made in collaboration with Telefonica I+D); mutated to refer mostly to wireless communication and to be more
• a SIM card for the GSM/GPRS network; specific it is mostly referring to the use of cellular (mobile) commu-
• a cellphone (‘mobile’) with its own SIM card; nication for remotely controlling devices.
• TinkerKit shield;
• TinkerKit LED module (x3); For the sake of simplicity, when talking about the IoT I mean the
• TinkerKit Slider module. connection of devices to the Internet, while M2M will be a way to
make this possible through the cellular telephony network. You
The last three items in the list can be substituted by a breadboard will find many articles and videos on the Internet that follow the
and a combination of various components. However, to keep the same approach, the reason being that the most extended net-
focus on the operation of the GSM library for Arduino, I have opted work right now is the one called GSM (global system for mobile
to use pre-assembled parts. communications).
Now, before you read on, I strongly recommend you download all I assume that you are reading this article because you plan on mak-
the code used this month. Due to the length of the example pro- ing a connected device. Imagine that you create an object that’s
grams, only excerpts are printed here. going to connect to the Internet and send data back to you from
anywhere in the world — what, do you think, is the best way to do
Introduction to M2M and IoT so? The answer is obvious: cellular telephony. GSM is a great alter-
Putting it in easy terms, IoT is a computing paradigm that is being native as it allows you contact your device almost anywhere in the
explored lately by many research laboratories and universities world knowing that it will work, basically like at home.
around the world. It tries to bring to life the idea that everything can
be connected to the Internet: your microwave and your car, passing The Arduino - GSM/GPRS Shield
by your door lock and your bike at the gym. All those objects should From Arduino we want to simplify as much as possible the way
be able of talking to each other in some way and exchange data to you build prototypes and learn about technology. Therefore we
offer people better ways to handle different situations. have spent quite some time thinking about how to help you get-
Ericsson, the Swedish communication giant, presented a memo

48 168 10-2012 elektor

Personal Download for Petar Crnojevic | copyright Elektor


Arduino on Course

ting hooked to this trend of IoT in many ways. One of them is don’t see the library named ‘GSM3’ in the list, you will have to down-
through M2M and for that we teamed up with Telefonica’s Physi- load it from the official Arduino website hosting this project [4] and
cal Internet Laboratory. install it as explained under the ‘Library’ link. Essentially, adding a
We have been collaborating in making an official Arduino shield that new library to the IDE is done by creating a folder called ‘libraries’
easily handles GSM/GPRS (also known as 1G and 2G) communication. inside your sketchbook and uncompressing the file you got from the
We also wrote a library that simplifies the process of texting (SMS website [4] directly there. After that, you should restart the Arduino
transmission), setting up calls or publishing some data on a website. IDE and the library will then show up in the above mentioned menu.
The design is open source and the software can easily be ported With the library you will be installing not only the code to execute
to support other shields (with potentially other series of AT-Com- different commands on the modem, but also a series of examples
mands; more about this later). Finally, the shield comes with a SIM that will allow you to:
card, courtesy of Telefonica, that will offer you the possibility to
hook up to send/receive text (SMS), set/get voice calls, and con- • test whether the modem is working properly;
nect to the Internet through the GPRS network. • text, i.e. send/receive SMS;
• place/get phonecalls (voice);
Note: This shield is not locked to the accompanying SIM; you could • open a TCP/IP connection and exchange data over the Internet,
use any other GSM/GPRS SIM card available in your country. The using GPRS;
SIM is optimised for data communication; if you wanted to make • post/collect sensor information to/from Cosm (an online data
something controlled over Text (SMS), you should consider a SIM service);
card operating on your preferred network. If you were about to use • collect and show twitter messages.
the card coming with the board, you should follow the online acti-
vation instructions that come with it. The way to access the examples is simple: just use the menu to navi-
gate through “File / Examples / GSM3”.
Controlling a modem - AT commands
Modems are the devices behind the expansion of the Internet. In Checking your status
order to automate the way they would operate, a company called Likely, the first thing you want to do is checking whether your board
Hayes [2] invented in 1981 what would later be called the AT-Com- is working properly and whether your SIM card can be used by the
mand Set. The idea behind it all is for modems to change between shield for you to experiment with. To do so, open the example under
Command and Data operation modes. The Command mode would
allow performing operations on the modem itself like calling a cer-
// libraries
tain number, changing the baud rate (the speed at which the data
#include <GSM3ShieldV1ModemVerification.h>
would be transferred), etc.
The Hayes Command Set became a de-facto standard for the way
// modem verification object
devices should communicate over a serial port. That standard is still
GSM3ShieldV1ModemVerification modemTest;
operating inside many devices. When in Command mode, devices
start the communication sending the string “AT” which stands for // IMEI variable
“attention”. That would be followed by other strings that would String IMEI = “”;
translate in different operations to be performed at the other side.
On the other hand, when in Data mode, the data will just be proxied // serial monitor result messages
to/from the Internet through the modem. String oktext = “OK”;
The GSM/GPRS shield has a radio modem manufactured by Quec- String errortext = “ERROR”;
tel [3] that can be operated using a series of AT commands. Most of
those commands are specific to the modem on the board, but the void setup()
library that controls the shield has been written in a way that makes {
very easy to port it for other modems made by any manufacturer. // initialize serial communications
Also, the library hides all the complexity behind this mode of opera- Serial.begin(9600);
tion. Therefore, we are not going to refer to them in the rest of the
article. However, if you happened to use the GSM library in debug // start modem test (reset and check response)
mode, you would be prompted with many of those commands. Serial.print(“Starting modem test...”);
modemTest.begin();
Installing the GSM Library for Arduino Serial.println(oktext);
At the time of writing this article the Arduino IDE had reached revi- }
sion 1.0.1 and did not include the GSM library we’re about to dis-
cuss. Thus, when checking the menu ‘Sketch / Import Library’ if you

elektor 10-2012 169 49

Personal Download for Petar Crnojevic | copyright Elektor


Microprocessors

void loop()
{
// get modem IMEI
Serial.print(“Checking IMEI...”);
IMEI = modemTest.getIMEI();

// check IMEI responsed


if(IMEI != NULL)
{
Serial.println(oktext);
// show IMEI in serial monitor
Serial.println(“Modem’s IMEI: “ + IMEI);
// reset modem for check booting
Serial.print(“Reseting modem...”);
modemTest.begin();
// get and check IMEI one more time Figure 1. Positive answer from the TestModem example using the
if(modemTest.getIMEI() != NULL) Serial Monitor.
{
Serial.println(oktext);
Serial.println(“TEST COMPLETE!”);
}
else
{
Serial.println(errortext);
}
}
else
{
Serial.println(errortext);
}
while(true);
}

the menu: “File / Examples / GSM3 / Tools / TestModem”. Figure 2. Configure your GPRS connection using the Serial Monitor.

This code example allows you to check whether Arduino can detect
your radio modem. It also opens a connection to the radio modem
on your GSM shield and attempts to read the IMEI (International It is specific for the operator providing you with connectivity
Mobile Equipment Identity) from it — that’s a unique number for through the shield;
every device capable of connecting to the GSM/GPRS/3G/4G net- • login: some operators require a login;
work. For example, your cell phone identifies itself via the IMEI. • password: some operators require a password;
Every device on the GSM network has a unique ID. If everything goes • proxy: this is the address to a server that will channel all your
fine, after uploading the example on your Arduino Uno, and opening communication inside the operator’s network. Most likely it
the Serial Port Monitor, you should see something like in Figure 1. won’t be used.
If your modem was working correctly, the next thing is to check
whether you can connect to the GPRS network. To do so, we will The way this example works is by asking you for the information the
open the example: File / Examples / GSM3 / Tools / TestGPRS. I will not shield needs to connect to the network.
show the code here, as it is very similar to the previous one. This
example is used for testing that your SIM card allows connecting to Tip: remember activating the option ‘Newline’ in the dropdown
the GPRS network (the one provided with the shield does), but also menu at the bottom of your Serial Port monitor. In this way, when
to test your settings. clicking on ‘Send’ on the monitor, the system will add an end-of-line
(EOL) character that is needed for the modem to know the informa-
Note: this shield is using GSM/GPRS technology and not 3G. 3G and tion package came to an end.
GSM SIM cards look the same, but remember that some of the mod- I everything goes fine, you will see a window like in Figure 2. Those
ern operators do not offer 2G (the way we call GPRS) services. messages mean that your shield can connect to the Internet using
Connecting to the GPRS network calls for a tad more configuring your SIM. Please note that even if you couldn’t connect to the Inter-
than just texting (sending an SMS) or placing a call. There are four net, it may still be possible for you to text-out, get text (send/receive
parameters that need to be configured: SMS) and set up calls.

• APN: acronym for Access Point Name or the name of the Texting (sending an SMS)
domain the shield will connect through to reach the Internet. Texting or receiving text (sending or receiving SMS) with the GSM

50 170 10-2012 elektor

Personal Download for Petar Crnojevic | copyright Elektor


is going to read the first character sent in the SMS and turn on the
corresponding light: R for red, G for Green and B for blue. This pro-
gram is, as you can see, very simple. It doesn’t execute huge parsing
operations; it simply reads the first character in the text message
(SMS) and decides what to do. After that, the text message (SMS)
will be erased from the memory using the command sms.flush().

// If there are any SMSs available()


if (sms.available())
{
Serial.println(“Message received from:”);

// Get remote number


sms.remoteNumber(remoteNumber, 20);
Serial.println(remoteNumber);

// This is just an example of message disposal


// Messages starting with # should be discarded
if(sms.peek()==’#’)
{
Serial.println(“Discarded SMS”);
sms.flush();
}

// Read message bytes and print them


int count = 0;
Figure 3. Screenshot of my phone after I was texted. while(c=sms.read()) {
if(!count) {
digitalWrite(pinR, LOW);
digitalWrite(pinG, LOW);
digitalWrite(pinB, LOW);
// send the message
sms.beginSMS(“0755442200”); switch(c) {
sms.print(“hola caracola”); case ‘R’:
sms.endSMS(); digitalWrite(pinR, HIGH);
break;
shield couldn’t be any easier. The following lines of code could be case ‘G’:
part of a program sending a string to a certain number. digitalWrite(pinG, HIGH);
Note that I am using a fictitious cell phone number! And the result break;
on the screen of my phone would be like shown in Figure 3. case ‘B’:
The library comes with examples covering both sending and receiv- digitalWrite(pinB, HIGH);
ing. For example, the code at File / Examples / GSM3 / Tools / SendSMS break;
will be sending an SMS (texting out) from the board to a phone via }
interaction through the Serial Port Monitor. It will first ask you for }
count++;
the phone number to text to (SMS) and then for the string to send.
}
Try it out!
Serial.println(“\nEND OF MESSAGE”);
Remotely controlling a device via Text (SMS)
Controlling a device remotely implies receiving messages, parsing
// delete message from modem memory
the data, and operating actuators depending on the different com-
sms.flush();
mands. In this case we are going to build a quick prototype includ- Serial.println(“MESSAGE DELETED”);
ing three LEDs: one red, one green and one blue. You can imag- }
ine that instead of using LEDs we could be attaching relays, and we
could be controlling any kind of device on distance. The program

elektor 10-2012 171 51

Personal Download for Petar Crnojevic | copyright Elektor


Microprocessors

Figure 4. All in hand: Arduino Uno + GSM/GPRS shield + Figure 5. Information being displayed on a browser as sent from
TinkerKit shield + TinkerKit LED. the GSM shield.

The following is a part of the example DecodeSMS you can find at once you are done trying out the example.
the download link [5] for this article. The only thing left to do is uncompress the code of the PHP mem-
The actual circuit boards are shown in Figure 4. ory cell in the given file [5] at the root folder, to your http server.
Make sure the file has read-write-execute permissions to allow it to
Device working over GPRS rewrite itself. You can then type the URL to your server (for example:
Let’s now see how to use an analogue sensor (a slider in this case) and http://server.com/path/index.php) in a browser to see the informa-
send data from it to a website. On the server side I am using Apache tion update every 10 seconds. Like in Figure 5.
and a very simple PHP script that will be taking the data sent by the
board and will update a part of the script containing plain HTML. This Closing words
is what I like to call a simple ‘online memory cell’. It is a PHP script I hope you found this brief introduction to the use of GSM/GPRS
that can take the data and display it. It will be possible to access that technology in your projects both educational and fun. I want to
same page using a browser to see the data changing over time. You highlight how relevant it is that we, as makers, can benefit from
will need to use the same APN/login/pass combination you used in the existence of an omnipresent wireless network. If you don’t need
very data-hungry devices, you could start controlling lots of things
over the cellphone network. As long as there is a way to power up
void loop() your board, you can gather and process data from almost anywhere.
{ (120506)
client.connect(server, 80);
Serial.println(“sending data...”); Internet Links
client.print(“GET “);
[1] Ericsson’s memo on 50 billion connected devices:
client.print(path);
client.print(query); www.ericsson.com/res/docs/whitepapers/wp-50-billions.pdf
client.print(analogRead(A0)); // take the value [2] on the AT-Command set:
// on A0 and send it http://en.wikipedia.org/wiki/Hayes_command_set
client.println(“ HTTP/1.1”);
[3] Quectel AT-Command description:
client.print(“HOST: “);
client.println(server); http://datasphere.eu/en?t=/documentManager/sfdoc.file.
client.println(); supply&fileID=1285079825955
client.stop(); [4] Arduino website hosting information about the GSM shield:
delay(10000); http://labs.arduino.cc/GPRS/Index
}
[5] Compressed file with all the examples and images:
www.elektor.com/120506
the previous GPRS example for this code to work properly. Here’s how
to send an analogue value to a server every 10 seconds:
You need to have a server to run the php code that will be reading
Acknowledgements
from your Arduino board. The server needs to be publicly accessible
My sincere thanks are due to the whole Physical Internet Laboratory
as you want your Arduino board to post information to it and to read
that data using a browser, a phone or any other web-enabled device. team at Telefonica Research and Development, for their support in
Important: keep in mind that this code is just a proof of concept, it is making this new Arduino shield possible. Special thanks go out to F. J.
not safe in any way and you should probably disable the PHP script Zorzano for being there debugging code until late many nights.

52 172 10-2012 elektor

Personal Download for Petar Crnojevic | copyright Elektor


Microprocessors

Arduino on Course (3a)


Part 3a: Connect the physical world
to your Android phone
By David Cuartielles (Spain) and This month you will start experimenting with
Andreas Goransson (Sweden) the Arduino Mega ADK board, exploring its
capability to connect to Android phones
and tablets. Android is an Operating
System (OS) for mobile and
embedded devices
that aims at reaching
almost every
device in the
connected world.
According to
independent sources
[1], Android reached
about 50% of the market
share during 2011.

The Android OS allows anyone to create physical add-ons for smart- Tip: before continuing reading the article, we strongly recom-
phones. This article provides an introduction into setting up your mend you download all the code used in it, as we are only showing
system for developing add-ons and Apps connected to them. excerpts, due to the length of each one of the examples.

Hardware list-o-mania Introduction to Android OS


Here’s a shopping list for our experiments: Android is an operating system (OS) meant for mobile and embed-
• Arduino Mega ADK board (pictured above) or Arduino Uno ded devices. It is based on Linux and runs a Java-like virtual machine
board with USB Host Shield; called Dalvik. As in other OSs used in the market of mobile tele-
• Android smartphone with Android OS 2.3.4 or newer; phony, Android presents a number of differences when compared
• USB cable and microUSB cable. to Linux.
First of all, as this OS is meant to be used in cellphones, the typical
Note: in this article we will concentrate in how to prepare your sys- phone operations will have a high priority in the system. For exam-
tem to start developing Arduino applications that will connect to ple, unless configured otherwise, a phone call from the missus will
your smartphone. We will give you some pre-made Apps (source stop your device from doing anything else.
included) for you to read/write data from/to the board and for use Also, all the devices sport a series of pre-assembled sensors like
by, or supplied by, the smartphone. accelerometers, temperature sensors, light sensors, etc.

36 173 11-2012 elektor

Personal Download for Petar Crnojevic | copyright Elektor


Arduino on Course

They offer multiple ways to access the Internet or other devices.


Android offers multiple possibilities to do so: GPRS/3G/4G, Wi-Fi,
Bluetooth, USB cable, etc.
Finally, by default you will not program native applications, but
programs that will run on top of the Dalvik virtual machine. In this
way, in terms of syntax your programs will be equivalent to Java. In
many cases you can import Java libraries (from source) straight into
your phone apps. Android assures a certain degree of portability
between ‘terminals’ from different manufacturers. In other words,
the same app, once compiled, will most likely work fine for all the
different phones as long as they run the same version of the OS.
Figure 1. : Arduino Uno connected to a USB Host Shield.
Android h/w add-ons
Android development team introduced in 2011 the possibility of
creating accessory devices (add-on devices) using a series of open
source tools. The famous Accessory Development Kit [2] consists of device will connect to the Internet and offer you a website where it
a series of hardware reference designs and the Android Open Acces- will be possible for you to download the App used in this example,
sory Protocol (AOAP). as is being done in Figure 2.

The hardware designs are derivatives of different Arduino boards. Note: For this automatic App installation to work, you need to acti-
For this article, we’ll focus on using an Arduino Mega ADK, which is vate the option that allows your phone to install applications from
compatible with the first version of the AOAP. The code presented outside the official Google Play Market. Follow Settings à Applica-
in this article should work with later ADK compatible boards (like tions and make sure the option “Unknown sources” is active. Also
Arduino Due and the like). It should also be possible to replicate the make sure your phone has a data connection either over Wi-Fi or the
experiments shown in here using an Arduino Uno and a USB Host phone network to download the App from our servers.
Shield for Arduino like the one in Figure 1.
One of the main features the AOAP brings into play is ‘App Wakeup’ Installing the USB Host library for Arduino
upon accessory detection. When an accessory is plugged to the At the time of writing this article the Arduino IDE did not include the
phone or tablet, it triggers a call to an application whose name is USB Host library we are presenting. Therefore when you examine
determined by the accessory. In case the App wasn’t installed in the the “Sketch / Import Library” menu you don’t see the library named
device, the accessory would also inform about a URL from where to ‘USB Host’ in the list — you will have to download the library from
download and install the application. the official Arduino website hosting this project [3] and install it.

At the time of writing this article, there were a whole series of


boards compatible with the Google ADK besides the Arduino Mega
ADK. On the other hand there were no compatible boards with
Google ADK2 besides the Arduino Due.

Experimental setup @ the Arduino side


For the sake of simplicity, let’s start by configuring our experimental
setup preparing the Arduino IDE enable it to compile AOAP com-
patible source for the Arduino Mega ADK. Besides having the right
hardware, you will need to install:

• Arduino 1.0.1 or newer


• The UsbHost library for Arduino (includes the AndroidAccessory
class). If you never installed a library for Arduino before, a
how-to follows in the next section.

Thanks to the way AOAP works, once you have the right code run-
ning on the Arduino Mega ADK, even if you have no applications in
your phone ready to take advantage of the accessory, your Android Figure 2. Arduino Mega ADK connected to a PC and to a phone.

elektor 11-2012 174 37

Personal Download for Petar Crnojevic | copyright Elektor


Microprocessors

Essentially, adding a new library to the IDE phone’s screenshot is the same one as in
is done by creating a folder called ‘libraries’ code listing 1. In other words, you deter-
inside your sketchbook and uncompressing mine in your Arduino code, where the App
the file you got from the website [3] directly is located on the Internet. In this case, we
there. After that, you should restart the have set up a website for you to check all
Arduino IDE and the library will then show the examples from your phone. You should
up in the above-mentioned menu. open the browser in your Android device
If you had a previous version of this library or and see the site as in Figure 5.
one obtained from a different website than You will have to download it and install the
the Arduino one, we strongly recommend App by clicking the link underneath the
you uninstall it before bringing in this new image It will first get downloaded and then
version, as they might be incompatible. effectively loaded into your device. Next you
With the library you will be installing not need to click on the file (called “Elektor_
only the code to execute different com- Figure 3. Screenshot from the Serial Port MIAU.apk”) which will install it. If the App
mands on the modem, but also a series of Monitor when linking an Android device to is already in your phone, you will instead
examples that will allow you to: your Arduino Mega ADK. get an invitation to load the right applica-
tion when plugging in the accessory again
• test whether the ADK mode is working (Figure 6).
properly;
• send digital/analogue values from the board to the phone; Once you have given permission for the App to boot, it will present
• receive values from the phone into the board; a GIF image as part of a loop (Figure 7). We thought it would be fun
• debug the different types of USB devices connected to the to show that you can actually use some graphic capabilities on your
Arduino Mega ADK board. Android terminal and stay clear of the corny “Hello World” text on
the screen. However, this App is not using any information from
The way to access the examples is very simple, just use the menu the Arduino board, nor is it sending anything back to it — all it does
to navigate through: “File / Examples / USB is allow you to check whether your phone/
Host”. tablet supports Accessory Mode.

Boot an App — prep work Note: It should be mentioned here that it


To check whether things are working fine is possible to have more than one App to
for you, let’s make the easiest example pos- handle the data produced by an accessory.
sible. You are going to upload a program In that case, the dialogue window will offer
to your Arduino board that will make your more than one option to choose from.
phone download a very simple App called
Elektor_MIAU, as well as show something on Experimental setup @
the screen. (code listing 1) the Android side
Building Android Apps can be complex. It
Once you load this code into your Arduino requires installing a long list of different
Mega ADK, you should open the Serial Port software packages coming from different
Monitor in your IDE to monitor what is hap- locations. We wrote a Getting Started Guide
pening. When connecting your phone via revising all the different packages you need
the micro USB cable to the Arduino board, for getting the easiest experimental setup
the Serial port will register something simi- possible [3].
lar to what is shown in Figure 3. Probably the easiest way to develop a simple
Android application implies using the open
At the same time, the phone will detect it source software tool called Processing [4] by
has a compatible accessory hooked up and, C. Reas and B. Fry. This software offers a sim-
since you will have no application installed plified IDE that allows Java applications to be
in it for it to handle the data, you will get a compiled. The latest version also compiles
message indicating where you can get the code for Android phones, and Javascript for
proper App from the Internet. You should websites. We have developed an Add-on
get something similar to Figure 4. Figure 4. Screenshot taken from an Android tool for the Processing IDE that compiles
phone showing the warning about missing and uploads code to your Android device
You will notice the URL mentioned in the an App to handle an accessory. for controlling accessories.

38 175 11-2012 elektor

Personal Download for Petar Crnojevic | copyright Elektor


Arduino on Course

(code listing 1) void setup()


// libraries {
#include <AndroidAccessory.h> // initialize serial communications
Serial.begin(115200);
AndroidAccessory acc( Serial.print(“\r\nStart”);
“Arduino, SA”,
“Miau”, // initialize the accessory object
“Arduino Mega ADK”, acc.begin();
“1.0”, }
“http://labs.arduino.cc/ADK/
ExamplesElektor#HelloCat”, void loop()
“0000000012345678”); {
if (acc.isConnected() && !wasConnected) {
// variable to detect whether the Android device was Serial.print(“Accessory connected. “);
plugged recently wasConnected = true;
boolean wasConnected = false; }
}

Let’s summarise what you need to have in place for you to replicate • The Arduino ADK Tool for Processing;
the experiments discussed in this article. • Eclipse [5] + ADT plugin (both optional and not used here).

• Android SDK with all the updates up to the latest version of the As with almost everything within the world of software, there are
APIs; many possible tools to write your applications in. The Android SDK
• Processing 2.0a8 or newer; is an external tool to your preferred code-editor that will compile,

Figure 5. Android phone showing Figure 6. Your Android phone asks for Figure 7: The MIAU App running on Android.
information about the App. confirmation before loading an App to
handle an accessory.

elektor 11-2012 176 39

Personal Download for Petar Crnojevic | copyright Elektor


Microprocessors

(code listing 2) void draw() {


void setup() { // draw from the center of the shape
// make sure the screen will have rectMode(CENTER);
// fixed orientation
orientation(PORTRAIT); // make a 50x50 pix square using the
} // default color scheme
rect(width/2, height/2, 50, 50);
}

(code listing 3) “Arduino Mega ADK”,


AndroidAccessory acc( “1.0”,
“Arduino, SA”, “http://labs.arduino.cc/ADK/
“Elektor_Rectangle”, ExamplesElektor#Rectangle”,
“0000000012345678”);

link libraries, simulate, compress and sign data captured by the Arduino Accessory.
your Android applications for a specific ver- (code listing 2)
sion of the OS. Processing is a tool aimed at graphic art-
On the other hand, Processing is a really ists and therefore it uses a paradigm where
good tool if you are starting to program, instead of having a ‘loop’, the main function
and therefore we created an Add-on for it in the program happens to be called ‘draw’.
as explained in the Getting Started Guide [3]. The code you write inside Processing’s IDE is
But if you really want to use a professional Java, but it hides all the complex operations
set of tools to write Android Apps on, you behind it. To check whether you have eve-
should consider Eclipse [5], the open source rything installed properly, follow the menu
IDE, and the associated tools. Android’s Sketch à Run on Device, as in Figure 9, this
developer site [6] explains how to install the should compile the code and upload it auto-
whole Eclipse-based toolchain step by step. matically to the phone.
I will assume you managed to install Pro- Once the App boots, you should see an
cessing and all the other tools without much image like Figure 10 on your phone’s
trouble. All of them are cross platform and screen. The App will boot directly and it will
should work for virtually any version of remain there. You will be able to look for it
your OS. So now we will write the code for on your App menu and run it as many times
Android using Processing. as you want to.

Your first App Figure 8. Screenshot of Processing running Note: At the time of writing, Processing
Android mode; note the Mode button in the
Before even thinking of making an App to didn’t allow signing Apps. The process of
upper right corner.
control your accessory, let’s make a very signing an App is what validates it for dis-
simple App using Processing to show some- tribution to other devices. Any Apps cre-
thing on the phone’s screen. For you to start ated with Processing will only work on the
writing Android Apps you will need to have devices you upload them to directly. If you
the Android SDK installed and the Process- wanted to send your Apps to a friend, you
ing software configured to compile Android should compile them using Eclipse, which
applications (Figure 8). Your IDE should is much more complicated at this point and
have a green colour scheme. will not be explained here. For example, the
“Elektor_MIAU” application is signed, allow-
Let’s start by making an App and running it ing anyone to download it from the Internet.
on the device straight away. The following
bit of code will show a square in the centre Make your App boot upon
of the screen. We will later add the code for Figure 9. Running the App directly on your accessory connection
the square to change depending on sensor phone. Now you made a very simple application

40 177 11-2012 elektor

Personal Download for Petar Crnojevic | copyright Elektor


Arduino on Course

Figure 11. Screenshot of the Tools menu


for Processing’s IDE.

Figure 10. Screenshot App active on the Figure 12. Dialogue window to configure Figure 13. Dialogue window showing the
phone. the App to be booted for the accessory. notification for opening your Rectangle App.

that runs on your phone, it’s time to make it boot when you plug Acknowledgements
an accessory to it. Here is when the Arduino ADK Tool for Processing
Our thanks are due to the team at Circuits@Home for their first work
comes into play. If you installed it as explained at [3], no problems
on the USB Host Library for Arduino and Philip Lindsay for his work on
arise if you just call it from the Processing IDE. The new tool needed
for uploading accessory code to your Android device should show debugging the initial collection of official Arduino Libraries for Android.
up under the Tools à Arduino ADK menu as shown in Figure 11.
About the co-author
When choosing that option from the menu, the IDE will open a dia-
logue window allowing you introducing the name of the app and Andreas Goransson is an interaction designer based in Malmö.
the manufacturer of the accessory (Figure 12). That is what Android Currently he is teaching software at Malmö University and he is writing
Accessories need to identify the App to connect to. You will have a book about Android and Arduino together with David Cuartiellies.
to make this match with the code on Arduino, as shown below in
code listing 3.

You could now modify code listing 1 where we were calling the Hel- Internet Links & References
loCat application to call this new one. [1] Worldwide smartphone market, by operating system:
(code listing 3)
http://mobithinking.com/mobile-marketing-tools/
latest-mobile-stats/a#smartphoneos
Note that this is just a snippet of code to modify code listing 1 to
make it call your first Accessory App for Android. [2] Accessory Development Kit: http://developer.android.com/tools/
Having done that and uploaded the code to your Arduino Mega adk/index.html
ADK, whenever you plug your phone to the board, it will boot your [3] Arduino with Android at Arduino.cc: http://labs.arduino.cc/ADK/
drawing rectangle App, as pictured in Figure 13.
AccessoryMode

Next month [4] Processing Project: http://processing.org


This was a brief introduction to creating accessories for Arduino [5] Eclipse: http://eclipse.org
and Apps on Android that connect to them. However, this is just an
[6] Android Guide to installing the Android SDK using Eclipse: http://
introduction. Follow us next month to see how to send data from
developer.android.com/tools/index.html
Arduino to Android and vice-versa.
(120539)

elektor 11-2012 178 41

Personal Download for Petar Crnojevic | copyright Elektor


Projects

Arduino on Course (3b)


Part 3b:
Sensors talk to Android phones
By David Cuartielles Last month we introduced a series of tools for working with Android and Arduino
(Spain)
and Mega ADK. This month we go one step further in that process,
Andreas Goransson showing you how to read sensors connected to Arduino, into the
(Sweden)
phone. With all development tools in place, running code in your
phone and making it talk to your Arduino will be very
easy, you can start by following the examples com-
ing with the ADK libraries!

Android phone to test how things work. We have


made an extra effort in making sure the code
is compatible with the latest version of Android
OS, at the time of writing it was version 4.1,
code Jelly Bean.
Tip: download the code shown in this article
from Elektor’s website, as we are only showing
excerpts in the article.

Where we are now


At this point you have a certain understanding of
Android devices are about Google’s Accessory mode and how accessories
everywhere. There are many ways how to tell Android devices to boot a certain app when
approach the creation of applications for those. connecting. You are familiar with Processing, the
In our case, we will continue exploring the use Java learning tool, and have created and uploaded
of Processing [1] as a way to write, compile and small apps to your phone or tablet.
upload code for/to Android phones. The next step is moving into creating new apps
that will take advantage of the connectivity
Materials between Arduino — as an accessory — and your
Continuing with the experiments performed last Android.
month, the materials for making the upcoming
experiment are going to be: The USB Host Library
The Android Open Accessory Protocol (AOAP) is
• Arduino Mega ADK board or Arduino Uno what determines how your Android device and
board with USB Host Shield your Arduino board can talk to each other. The
• Android phone with Android OS 2.3.4 or Arduino board is technically a USB Host, while the
newer (the newer OS the better) phone becomes a USB Client. Android devices,
• USB cable and microUSB cable like most of the state-of-the-art devices out there,
• TinkerKit Shield (this is optional, you could carry a peripheral that performs the so-called
use a breadboard and jumper wires) USB On The Go functionality. According to it, the
• TinkerKit Modules: Potentiometer and Push- same USB connector (currently micro USB con-
button (also optional) nector) can become a USB client (like a mouse
or a keyboard) or a USB Host (like the one in
Note: in this article you really need to have an your Personal Computer).

179
46 | December 2012 | www.elektor.com/magazine

Personal Download for Petar Crnojevic | copyright Elektor


Arduino On Course

The AOAP establishes that accessories act as


hosts while the Android devices act as clients.
This allows the host feed the client with electric-
ity (you Arduino board will be re-charging your
phone once plugged), among other features.
To establish the communication between the two,
you saw in the previous article that you need to
run the USB Host library as part of your Arduino
code. You could check one of the examples to
the library just to confirm you have it installed.
Note: use the menu to navigate through: “File Figure 1.
/ Examples / USB Host”, if you didn’t find those Arduino Mega ADK with
examples there, it would mean that you hadn’t Tinker Kit Shield and phone.
installed the USB Host library in Arduino. Check
the downloads for this article [3] and install it;
you are going to need it. Figure 1 shows the
hardware involved.

Experimental setup:
the processing side
Let’s first look into the software you need to pro-
gram you Android applications:

• Android SDK with all the updates up to the Figure 2.


latest version of the APIs Arduino Mega ADK
• Processing 2.0b3 or newer (if you read the connected to a PC and to a
first article, you will see we have updated to phone.
the latest version, you should do the same
at this point) dows computers or “Documents/Processing” in
• The Arduino ADK Tool for Processing Mac and Linux.
• The Arduino ADK USB Library for Processing This library comes with four examples. We rec-
ommend you start you accessories from one of
The last item in that list is what you will be miss- those examples, as it will make your life much
ing if you experimented with the previous article easier. Let’s start by trying out the example called
in the series. That one was omitted intentionally ‘digitalWrite’. In this case you will be connect-
back then. ing your Arduino board to the phone and when
touching the screen, an LED connected to your
You need the complementary library to USB Host board will go on. If you stop touching the screen,
on the Processing side to make sure you can get the LED will go off.
your board to talk to your phone. We call that
library “Arduino ADK USB”. The following section DigitalWrite
explains how to install it; Figure 2 shows the Each example has two parts. The first one runs
hardware side of things. on the Arduino board, it handles the communi-
cation to and from the phone, while perform-
Installing the Arduino ADK USB Library ing actions on the other pins on the board. The
for Android second part is code to be compiled in Process-
Inside the download archive for this article you ing and that will run inside the Android device.
will find a folder named “Processing” This app will be reading and writing data to the
which will have a subfolder called ‘libraries’. You phone’s cable connection as well as performing
should copy the contents of that folder inside your some actions on the screen or reading any of the
Processing libraries folder. The latter is located phone’s sensors like camera, accelerometer, etc.
inside your Processing sketchbook folder, usu- Let’s first analyse the Arduino code, open your
ally stored at ‘My Documents/Processing’ in Win- Arduino IDE and type in the code at Listing 1.

180
www.elektor.com/magazine | December 2012 | 47

Personal Download for Petar Crnojevic | copyright Elektor


Projects

Listing 1. DigitalWrite example from the Arduino’s USB Host library.

#include <AndroidAccessory.h>

// accessory descriptor. It’s how Arduino identifies itself to Android


char accessoryName[] = “DigitalWrite”; // your Arduino board
char companyName[] = “Arduino SA”;

// led variables
int ledPin = 10;

// counters
long timer = millis();

// initialize the accessory:


AndroidAccessory usb(companyName, accessoryName);

void setup() {
// start the connection to the device over the USB host:
usb.begin();
// configure the LED pin as output

Remember to upload it to the board once you return an affirmative answer. When the phone
are done! starts sending data, usb.available() will return
a value different from zero that Arduino will then
This code example will be listening to the USB read and store in the variable val. Something
port. Once the phone connects to the Arduino very similar to what’s pictured in Figure 3 should
board, the usb.isConnected() function will happen at your place too.

Listing 2. Processing sketch that will detect screen touches.

import cc.arduino.*;

// create the ADK object


ArduinoAdkUsb arduino;

void setup() {
// Lock PORTRAIT view
orientation( PORTRAIT );
// initialize the ADK object
arduino = new ArduinoAdkUsb( this );
if ( arduino.list() != null )
arduino.connect( arduino.list()[0] );
}

void draw() {
// Draws a filled rect based on arduino connection state
connected( arduino.isConnected() );
}

181
48 | December 2012 | www.elektor.com/magazine

Personal Download for Petar Crnojevic | copyright Elektor


Arduino On Course

pinMode(ledPin, OUTPUT);
}

void loop() {
// print to USB 10 times per second
if(millis()-timer>100) {
if (usb.isConnected()) { // is the USB connection open?
if (usb.available() > 0) { // is there data?
char val = usb.read();
// ‘a’ turns the LED on, ‘b’ off
if( val == ‘a’ )
digitalWrite( ledPin, HIGH );
else if( val == ‘b’ )
digitalWrite( ledPin, LOW );
}
timer = millis();
}
}
}

On the Processing side you will need to write a just lifted. We are detecting the events ‘start’
program that will check for the event of some- and ‘stop touching’ as we don’t want to flood
one touching the screen. If there is a connec- the communication port.
tion over the cable, the phone will then send ‘a’ Open your Processing IDE and search for the
to indicate someone just started touching the adk_digitalWrite example. You will find it at
screen. It will send ‘b’ to indicate the finger was the menu ‘Examples / Contributed Libraries /

public boolean surfaceTouchEvent(MotionEvent event) {


if ( arduino.isConnected() ) {
if ( event.getAction() == MotionEvent.ACTION_DOWN )
arduino.write(‘a’);
else if ( event.getAction() == MotionEvent.ACTION_UP )
arduino.write(‘b’);
}

// if you want the variables for motionX/motionY,


// mouseX/mouseY etc.
// to work properly, you’ll need to call
// super.surfaceTouchEvent().
return super.surfaceTouchEvent(event);
}

[…]

182
www.elektor.com/magazine | December 2012 | 49

Personal Download for Petar Crnojevic | copyright Elektor


Projects

ArduinoADKUsb’ if you installed the library prop- GIFdecoder library we used last month to play
erly, see Listing 2. animated GIFs inside your Android app. As we
want to keep the programming simple to under-
The code in Listing 2 is mostly self-explana- stand, the way we recommend you animate your
tory. One part you might find a little upsetting Rabbit is very simple: you should make an array
is the method definition surfaceTouchEvent of images designed to contain the frames you
(Motion‑Event event). Java is a very powerful want to be part of the animation. This concept is
programming language and in this case it allows based in the Processing example Animated Sprite
overriding some of the existing callback methods. by James Paterson [2], see Listing 3 at [3].
Whenever you touch the Android’s screen, the
system is configured to call that specific func- Note: Listing 3 is not showing the Animation class
tion (surfaceTouchEvent(MotionEvent event)). that will open all the images named s00.gif, s01.
If you override it in your program (basically, if gif, etc. We recommend you check the full code
you rewrite it) you can make it do whatever you listing coming with the example Elektor_Sim-
want to. ple_Animation. You will also see a folder called
In this case, we detect two of the many system ‘data’ inside the Processing sketch folder contain-
events: MotionEvent.ACTION_DOWN (the equiva- ing all the images that are part of the animation
lent to start pressing the screen) to send ‘a’ to (54 in total).
Arduino and MotionEvent.ACTION_UP (the same
for stop pressing the screen) to send ‘b’. The ultimate setup
Next up, we’ll modify the example to include the
A bit more fun library handling the USB communication. We rec-
Once you have got the first example to run… ommend you merge the previous code with the
why not building something a little more fun? adk_analogRead example. The result will look
The Internet is packed with cats, that’s why we like the code in Listing 4 you can find at [3].
decided to create the Elektor_Miau application There are a couple of things in the example that
last month. We wanted to make a fun comment need to be highlighted. First there is an array
and, at the same time, show you that it is pos- called delays[i]. It’s responsible for control-
sible to start making things more appealing than ling the time each frame will be displayed in the
the classic “Hello World” example when learning animation. Every time you load a new frame,
programming. you also change the timer length in the condi-
tion millis()- timer > delays[index]. You
This month we want to build upon the story and are welcome to experiment with the numbers in
encourage you to learn how to make small ani- that array to see how it affects the animation.
mations using Processing. You can look for any Remember there have to be as many numbers
animated GIF on the internet and use it to rep- as frames in the animation.
licate what you will see in this example. The
only condition is that you need the animated Also there is a keyFrames[i] array that holds a
gif exported as frames. You should name them list of frames in the animation that will be expect-
in the following way: s00.gif, s01.gif, s02.gif … ing an action from the user for the movie to con-
You are of course welcome to use the same image tinue. In this case we are going to detect button
we are using for our article. We got an illustra- presses. The animation will stop at those frames
tor to draw for us a small rabbit appearing out until the user presses the button attached to the
of a hat. The goal of this example is making a TinkerKit Shield as seen in Figure 5.
small interactive game where you will use sen-
sors (a button and a potentiometer) to interact If you look at the line checking how many
with the small rabbit on the phone’s screen, like bytes arrived from the Arduino board, we check
in Figure 4. arduino.available() >= 3 to see whether
we got 3 bytes. The information is encoded as
This time it will best to start looking at the code follows:
to be running inside the phone. The first step is
building an animation inside Processing. If you • Byte 0: has to be 255, it’s a marker we use
are versed in Android, you can try porting the to distinguish when the block starts;

183
50 | December 2012 | www.elektor.com/magazine

Personal Download for Petar Crnojevic | copyright Elektor


Arduino On Course

• Byte 1: is the potentiometer’s value; range


0 to 254;
• Byte 2: comes from the button; it will be
either 0 or 1.

The potentiometer’s value will be used to change


the screen background colour, while the button
will trigger the next sequence of the animation.

Note: use the Arduino ADK Usb tool (menu ‘Tools


/ Arduino ADK’ in your Processing IDE) to upload Figure 3.
this program from to your phone. A dialog win- The LED is on when touching
dow will pop up. In the text field labelled “model”, the screen.
enter the name of the app you call inside Ardui-
no’s IDE. The last parameter is used to select
the version of the SDK for your accessory type.
If your phone or tablet runs Android 3.0 or later,
you should check SDK v12; SDK v10 is only for
those devices running Android 2.3.4. In the unfor-
tunate case your Android device was running OS
version 2.3.3 or earlier, you wouldn’t be able of Figure 4.
using the Accessory mode. A couple of frames of our
rabbit movie.
Finally, the Arduino code is practically a repeat of
the adk_analogRead example adding the extra
marker byte, limiting the analog reading to 254
and adding the button. The loop for that pro-
gram is found in Listing 5 at [3]. Please check
the full program inside the documentation you
can get from Elektor’s website [1], in the folder
“Arduino / code”.

Closing words
With this article we finish our introduction to Figure 5.
Android and how it connects to Arduino. You Button and potentiometer
should be ready to create new projects, build on top of the TinkerKit
robots where your phone can be the intelligence, Shield.
or integrate sensors that aren’t coming with your
Android device. If you make any cool projects
using any of our code don’t hesitate to drop us
a line at [email protected], we will be happy to
let the rest of the community know about them. Acknowledgements
(120573)
The Arduino design team expresses its
thanks to the team at Circuits@Home for
their first work on the USB Host Library for
Arduino and Philip Lindsay for his work on
Internet Links & References
debugging the initial collection of official
[1] Processing Project: http://processing.org Arduino Libraries for Android. Also to
[2] Animations using multiple images with Pro- Rodrigo Calvo who helped unveiling how to
cessing: http://processing.org/learning/top- improve the USB Host library to work with
ics/sequential.html Android 4.1 devices. And Laura Balboa for
[3] www.elektor.com/120573 her illustration job.

184
www.elektor.com/magazine | December 2012 | 51

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Arduino on Course (4)


A plant watering supervisor
for communal use
By David Cuartielles (Sweden/Spain)

At Elektor’s recent Expert Meeting a full day was spent dis-


cussing how we make projects, or which are the hot topics
we think Elektor should cover in the future. During one of the
round-table sessions, E-Editor Jan suddenly started dropping
small piles of components on our tables and asking the ques-
tion: “Picture this! A weekend off, you start rummaging your
e-junkbox and hit upon these components. What would you
do with them?”

When I returned home from that trip I started to • 9 V battery connector


think about those forgotten components I own. I • 9 V battery (for Arduino) + CR2032 battery
have plenty of things bought during the experi- (for the RTC)
mental phases of projects that never made it into • A box to put everything in
the final prototype. I opened one of the boxes
and I found a dot matrix display and a couple Note: I built this project in a cardboard box,
of buttons. I thought it would be interesting to but I reckon there should be many other crea-
make some sort of clock out of it. So I bought a tive housings out there ranging from a discarded
Real Time Clock (RTC) chip from a local supplier lunch box to a more professional plastic enclo-
and hooked everything together. The result is sure… everything goes!
pictured above, and described below.
My design brief:
Materials make something useful
The materials for this month’s hands-on experi- I gave some thought to what I could do with my
ment are: salvaged parts. I live in an apartment building
and have some shared plants in the staircase
• Arduino Uno board well. Meaning: one of the apartment dwellers
• Prototyping shield waters those plants rather unsystematically, so
• Pinheaders (male) nobody knows for sure when the plants are okay
• USB cable for water. The truth is that most of the plants
• Two pushbuttons that appear in the staircase space end up drying
• Dot Matrix display w. HT1632 controller; I up sooner or later.
used the 32x16 from Sure I’d like to believe people do not water those plants
• RTC DS1302 because they think others are doing it, and not
• 32 kHz quartz crystal because they don’t care. So I came up with the
• CR2032 battery holder idea of making a time counter that supplies a

185
54 | January & February 2013 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


arduino on course

visual indication of the last time the plants got


watered by “somebody”.
I didn’t want the project to be too complex, there-
fore I decided that it should be focusing only on
the human aspects of watering a plant and it
should not involve measuring the humidity of
the plant’s soil or any other ambient conditions
around the plant itself. Neither did I want to make
anything connecting to the Internet to remind me
about watering the plants (the project Botanicalls
[1] is doing precisely that, it tweets a message
when the plant is in dire need of water).
I just wanted a device to let my neighbours check
out when was the last time someone took care
of the plants. So I thought about the chess clock
paradigm. Players have to press a button on the
clock at the end of each move to pass the turn
to their opponent. My idea was to create a clock
that would offer the same interaction. Once some-
one waters the plant, he or she presses a button
and passes the responsibility to someone else.
When pressing yet another button, the machine
will indicate just how long the plant hasn’t been This display controls 16x32 R/G LEDs. In other Figure 1.
watered. words, it has 512 duo colour LEDs. They can be The parts that go into the
Arduino’d Plant Watering
At this point, I mustered the components I fig- red, green or both at once, which gives orange
Supervisor.
ured I’d need (Figure 1). light. It is also easy to daisy chain and I have read
about projects that control up to four of these
Controlling the dot matrix display displays in a row, that is 2048 LEDs!
There is something about blinking LEDs that fas- For this project I use only one of the LEDs as I
cinates people. It is very easy to make the con- don’t need to show that much information and I
nection between controlling a single 5 mm LED just want to display how much time passed. But
Figure 2.
like the one we all use in small projects and a you may want to do more, so let’s take a look Schematic showing the
huge display in a public space. I bet that, as soon at what you can do with the display. whole project.
as you got your first LED to shine, the possibil-
ity of putting a hundred together to do the same
starts milling around in your head.
There is a limit to the number of pins on a micro-
controller, and another limit on how much cur-
rent each pin can supply. A Dot Matrix display
is a plastic unit in which the LEDs have either
their anode or cathode commoned, which makes
them easier to handle mechanically. Sometimes
driver chips are included as part of the definition
of Dot Matrix display. For our project the various
parts are connected up like in the “schematic”
in Figure 2.
I own a couple of displays from a brand called
Sure. I got them from the Arduino Store for some
experiments I did for my classes last year. I am
sure you can get the same display from other ven-
dors as well. It was documented a-okay online,
so I thought it would be good to add it to my
repertoire.

186
www.elektor-magazine.com | January & February 2013 | 55

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Install the library for the display You will have to download the library from
I put together a library using code from several Elektor’s website [4] and install it. Remember
authors, just re-factored the code to respect that adding a new library to the IDE is effectively
the Arduino library style, and added a couple done by creating a folder called ‘libraries’ inside
of simple examples. The library is compatible your sketchbook and uncompressing the file you
with revisions of the IDE 1.0 and above. Every- got from the website right there. After that, you
thing is aimed at using an RTC (real time clock) should restart the Arduino IDE and the library
unit built on the Arduino prototyping shield, see will then show up in the above mentioned menu.
Figure 3. Note: Arduino’s IDE is going to include a system

Listing 1. Listing 2.

#include <fonts.h> #include <fonts.h>


#include <HT1632c.h> #include <HT1632c.h>
#include <images.h> #include <images.h>

HT1632c display(6, 5, 3, 4); HT1632c display(6, 5, 3, 4);

void setup() { void setup() {


display.setup(); display.setup();
} }

void loop() { void loop() {


display.text(“Hej”, 5, 5); display.image(Arduino_logo, 0, 0, 32, 16);
} }

Listing 3.

#include <fonts.h>
#include <HT1632c.h>
#include <images.h>

#define heart_icon_width 17
#define heart_icon_height 16

unsigned char PROGMEM heart_icon[] = {


0x00, 0x1e, 0x00, 0x3f, 0x80, 0x7f, 0xc0, 0x7f, 0xe0, 0x7f, 0xf0, 0x7f,
0xf8, 0x3f, 0xfc, 0x1f, 0xfe, 0x0f, 0xfc, 0x1f, 0xf8, 0x3f, 0xf0, 0x7f,
0xe0, 0x7f, 0xc0, 0x7f, 0x80, 0x7f, 0x00, 0x3f, 0x00, 0x1e };

HT1632c display(3, 4, 5, 6);

void setup() {
display.setup();
}

void loop() {
display.image(heart_icon, 0, 0, heart_icon_width, heart_icon_height);
}

187
56 | January & February 2013 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


arduino on course

to automatically install libraries from the com-


pressed files you download from the Internet.
However at the time of writing this feature isn’t
deployed yet.

With the library you will be installing a series of


examples that are educational to follow in detail,
even if you do not envisage to replicate the hard-
ware in detail. The examples will allow you to:
Figure 3.
• test whether the display is working properly; The Arduino prototyping
• show simple text messages; shield with the components
soldered.
• scroll text on the screen;
• load images.

It’s easy to access the examples, just use the


menu to navigate through: File / Examples /
HT1632c.
Whenever you want to use the library, you will
need to include three header files: fonts.h,
HT1632c.h and images.h. When calling the
constructor you will need to specify the pins
you have attached the display to. They have the Figure 4.
Wow! Our ‘screen’ is
following order: Data pin, Write clock pin, Chip
showing the Arduino logo
Select, and Clock pin.
from the ‘Simple_image’
example.
Configure the display
In this project, the display is connected to digi-
tal pins 3, 4, 5, and 6. The library allows any like in Listing 2, employing the ‘Simple_image’
digital pins to be configured to send data to the example, loading a default icon.
LEDs. You can also daisy chain multiple displays Figure 4 shows the result of loading the Simple_
in sequence. I only had two to test, but I am image example on the dot matrix display or is it
confident it will work for more, without problems. “the screen”? In this case it is the Arduino logo
The display is powered directly from the Arduino type I stored in the library as a default example.
regulator; during my tests I didn’t seem to need If you want to display your own image, you can
significantly more power than the battery was generate code friendly images using Gimp, which
able to source. If you are planning on connecting is a free image editing suite that runs on all the
many displays as part of one single project though main operating systems. You will need to:
you should keep in mind the amount of current
you will need for the system to keep working. • open the image and scale it to fit the screen
Now, Listing 1 configures the display with the (32 columns x 16 rows);
• rotate the image 90 deg. clockwise;
‘simple_text’ example that comes with the library. • export them as XbitMap;
By default the text method will be using orange • open the xbm file and copy the resulting
as a colour to show the text. A fourth parameter array;
will determine the colour, you can use the con- • paste the array in your program as unsigned
stants: BLACK, GREEN, RED, and ORANGE. char PROGMEM, in other words, push it into
program memory space, just to leave the
RAM untouched.
Show a simple image
It is possible to render low resolution images on An example of a result is shown in Figure 5, it’s
one of these displays. You will need to have the a clip art of a heart, and importing it into code
image stored in program memory as an array would look like Listing 3.

188
www.elektor-magazine.com | January & February 2013 | 57

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

not be switched off, and therefore we need to


power them with a battery. On the other hand,
they consume very little power and can run on
3.3 V batteries for a really long time, sometimes
even years.
The chip I picked for my project is the DS1302
from Maxim, a very common RTC that’s been
widely documented by the Arduino commu-
Figure 5. nity. There is a really good read available by
Clip art of a heart image Arduino user Krodal at the Arduino Playground
before being processed for [2] together with some code exploring the capa-
inclusion in the Arduino bilities the chip in depth. However, for the sake
Sketch]
of simplicity, I decided to use a library by Matt
Sparks [3].
Note: the way the xbm file is rendered is a little So far we have only used four pins on the Arduino
different from the way it gets rendered on the Uno to connect the display; the RTC needs three
screen. Therefore you need to change width for digital pins, so I chose 7, 8, and 9. Figure 6
height when you want to load your own icon. In shows the RTC, where to plug in the power and
my case, the icon was 16x17, but I enter the the 32 kHz clock, as well as the pins where to
data as 17x16 (width x height). connect the chip to Arduino.
Tip: you can add multiple icons/images to your
program, just give them different names so that Install the RTC library, set the time
you can call them from anywhere in your code. You can get a copy of the RTC library from the
There is a lot that can be done with the library Elektor website [4] or from the github project
controlling the display, but for the purpose of by its author [3]. Install it by uncompressing
making this project, we just need to show text the file inside your libraries folder, as explained
and possibly some simple images. Feel free to earlier for the HT1632c library, and check inside
explore the library as it is free software, and the the examples.
functions in it are self-explanatory. Let’s move You need to run the example set_clock.pde
on and explore how to use the Real Time Clock. once in order to configure the time on your RTC.
As long as the RTC itself is plugged to a battery,
Real Time Clock chips you won’t need to run this code again. Make sure
Thanks to an external 32 kHz crystal RTCs can you modify the line inside setup that configures
Figure 6. measure time in a very precise way. As RTCs the time in the clock, Listing 4 shows the part of
Schematic showing the RTC
need to be counting time constantly, they can- set_clock.pde you need to configure manually.
connected to Arduino.

Use the EEPROM to store current time


The ATMega 328 on the Arduino Uno has 512
bytes of EEPROM, or non-volatile memory, to
retain data when the system is off. This part
of the memory is frequently used by embed-
ded designer to store the basic configuration of
a device.
In our case, we will use the EEPROM to store the
date when someone last watered the plants (and
pressed the button). In total we need to store
three bytes: year, month, and day. Then we need
to add to our program the ability to estimate
the time difference between the time stored in
memory and the one we could read at any time,
as we want to show on the screen that the plant
hasn’t had any water for some days. Listing 5
shows how to store something in EEPROM.

189
58 | January & February 2013 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


arduino on course

Listing 4.

[…]

void setup() {
Serial.begin(9600);

/* Initialize a new chip by turning off write protection and clearing the
clock halt flag. These methods needn’t always be called. See the DS1302
datasheet for details. */
rtc.write_protect(false);
rtc.halt(false);

/* Make a new time object to set the date and time */


/* Tuesday, May 19, 2009 at 21:16:37. */
Time t(2009, 5, 19, 21, 16, 37, 3);

/* Set the time and date on the chip */


rtc.time(t);
}

[…]

A project made from things


I found in my e-junkbox
A button to store time ject is the way battery consumption is handled. I
A button supplies a trigger signal flagging that decided that the best way to save battery power
a time needs to be recorded. When the button is not to have the system on at all. As you might
is pressed, the current time has to be read from have noticed in the bill of materials for this pro-
the RTC, and pushed to the EEPROM. I associ- ject, there are two pushbuttons listed in it. And
ated the button with pin 12, in my code (List- so far in the code we are only using one.
ing 6) I will make sure that pin is configured
as INPUT_PULLUP just to save some time when
Listing 5.
soldering the components together.
After storing the time, the readout on the box #include <EEPROM.h>
will show the message “nice!”, and stop there.
Other operations are blocked until the program int val;
is restarted. I think this is a good workaround
to stop people from reading and writing to the void setup() {
EEPROM too often.
}
Check the full code listing in the Elektor archive
file for this article. I have added an extra ani-
void loop() {
mation to thank my neighbors for watering the
val = analogRead(A0);
plants!
EEPROM.write(0, val);
A button to control it all }
Probably the most important part of this pro-

190
www.elektor-magazine.com | January & February 2013 | 59

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

of days since the plant was watered.


Adding this button also means that, for the sys-
tem to store the new time, you need to press
both buttons at once. One will turn the system
on, while the other will tell the system to store
the time from the RTC in the EEPROM. Like in
Figure 7.

Closing words
Figure 7. With the excuse of building ‘something’ from
“Hey, it’s been three days ‘any’ parts, we got the chance to experiment
since I last got some water”.
with drivers capable of driving hundreds of LEDs,
as well as with timers. The next step is going to
The second button is all about cutting the bat- be checking out whether my prototype fits the
tery power; unless you press it, the system is not purpose. I will place it in my staircase and see if
going to get any power. Microcontrollers wake ‘our’ plants get a better life.
up rapidly; in this case, the first thing you will I am sure you can figure out multiple uses for
see on the screen is the Arduino logotype and, a box with a display and two buttons beyond
after a few seconds, it will tell you the number the one described in this article: from clocks
to games. Just add a buzzer and some more
pushbuttons to the mix and turn it into a small
Listing 6.
game console.
[…] (120714)

int saveTimePin = 12;


References
int saveTimeButton = LOW, saveTimeButtonOld = LOW;
[1] The Botanicalls project:
http://botanicalls.com
void setup() {
[…] [2] Krodal’s explanation on the DS1302 RTC:
http://arduino.cc/playground/Main/DS1302
pinMode(saveTimePin, INPUT_PULLUP);
} [3] Mark Sparks’ RTC library:
https://github.com/msparks/arduino-ds1302

void loop() { [4] Program and library downloads:


[…] www.elektor-magazine.com/120174

saveTimeButton = digitalRead(saveTimePin);
if(saveTimeButton == LOW && saveTimeButtonOld == HIGH) {
// we will use the Time stored in t to save the time Acknowledgements
EEPROM.write(0, t.yr); // position 0 – year to the guys at the Arduino Store, who kindly
EEPROM.write(1, t.mon); // position 1 – month gave me the display I used for this project some
EEPROM.write(2, t.date); // position 2 – day time ago.
// clear the display
display.cls();
// show a thank you text
display.text(“nice!”, 2, 5);
// stay here
while(true) {};
}
saveTimeButtonOld = saveTimeButton;
}

191
60 | January & February 2013 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Arduino on Course (5)


Cookie thief framed!
By David Cuartielles We found out someone is eating the cookies from the jar in the kitchen! We dis-
(Spain) and
Bobbie Cuartielles cussed the issue and decided to set up a trap to reveal the thief. Rest assured, we
(Sweden) don’t want to hurt anyone, we just want to know and have evidence of the ‘crime’.

• Breadboard
• One 1-megohm (1 MΩ) resistor
• Jumper wires
• TinkerKit Module: Ultra Bright White LED +
TinkerKit wire

The idea
We are going to create a trap where a home-made
toy (pictured above) is constantly guarding our
cookie jar. If anyone touches the jar, a camera
hidden inside the toy shoots a picture and hope-
fully photographs the robber’s face.
Capturing the image is done with a program writ-
ten in Processing, which will be taking pictures
through the camera inside the toy. We will then
activate the camera from an Arduino board that’s
effectively detecting when someone touches our
precious cookie storage. This will be achieved
using the capacitive sensing capabilities imple-
mented on all ATMega chips.
The concept sounds simple enough and integrat-
ing the parts is also kind of easy. First we will
make a Processing sketch though that’s effec-
tively capable of triggering the photo shot using
Arduino over the computer’s serial port.

So here we are, with a clear mission and a whole Installing Processing


lot of tools at our disposal. We decided to put on Download ‘Processing’ from its website [1]. If you
our inventor coats on and make a machine that haven’t been following any of my recent Arduino
takes a picture of whoever opens the cookie jar. On Course installments, you should know that
Processing is a cross-platform software devel-
Materials opment environment dedicated to the creation
This month the list of materials to replicate this of Java, Android, and Javascript programs. It is
project is pretty straightforward: aimed at people learning how to code and make
complicated things in uncomplicated ways.
• Arduino Uno board We are going to use a webcam; therefore you
• Computer with Processing IDE and Arduino should double check whether your camera works
IDE installed inside Processing. If you are running Windows or
• Webcam Mac, please read [2] in case it didn’t work out
• USB cable of the box, and if you happen to be a Linux user

192
38 | April 2013 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Arduino on course

(like me) read this other link [3] where it explains Table 1.
which packages you need to install for Process-
index name size fps
ing to take control of your webcam.
[0] /dev/video0 1280x720 10
From Processing we are going to use the Video
and Serial libraries, and both come with the IDE [1] /dev/video0 960x540 10
by default. Therefore you don’t need to worry [2] /dev/video0 800x448 15
about finding and installing extra libraries this [3] /dev/video0 640x480 30
time. ...
[86] /dev/video0 320x240 15
Capturing a (webcam) image
The latest version of Processing implements its
video library using Gstreamer [4], a suite of soft- Listing 1
ware tools capable of accessing various video /**
devices connected to your computer, pipe the * Check cameras in Processing
streams, implement codecs, etc. You can access */
the video stream coming from a camera con-
nected to the computer through a file handler. import processing.video.*;
For example, on *nix based machines (like Linux
or Mac OSX), all your video devices are listed Capture cam;
under the file /dev/videoXX, where XX represents
void setup() {
a different number identifying different cameras.
For this project, as I am programming from my
String[] cameras = Capture.list();
laptop, /dev/video0 represents the camera that
comes embedded with the computer, while / if (cameras.length == 0) {
dev/video1 is the camera I have placed inside println(“There are no cameras available for capture.”);
the toy guard. exit();
The first thing you need to take into account is } else {
that the same camera can have different configu- println(“Available cameras:”);
rations in terms of resolution and image shooting for (int i = 0; i < cameras.length; i++) {
speed. Therefore, you should run the program println(“[“+i+”] “+cameras[i]);
shown in code Listing 1, and check out the }
}
different cameras and possible configurations
}
in your computer as they will come out printed
in the console inside your Processing IDE. The
void draw() {
program processes code to do a survey of cam- }
eras available in your computer.

You will be surprised by the long response coming Listing 2


from that program; in my case, listing only the
if (cameras.length == 0) {
possible configurations for my computer’s inter-
println(“There are no cameras available for capture.”);
nal camera, I get a list like the one in Table 1 exit();
(list trimmed). } else {
println(“Available cameras:”);
Next, decide on the camera configuration based for (int i = 0; i < cameras.length; i++) {
on the size you want your sketch to be. In my println(“[“+i+”] “+cameras[i]);
case, I wanted to have one configured at 640 }
x 480 pixels, i.e. index number 3 in Table 1.
Note that there may be configurations with the // The camera can be initialized directly using an
element
same values in the result; you should check
// from the array returned by list():
which one best suits you.
cam = new Capture(this, cameras[3]);
The camera selection has to be done inside the
cam.start();
program’s setup — simply modify the condi- }
tional statement inside setup to contain the code

193
www.elektor-magazine.com | April 2013 | 39

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

shown in Listing 2, this will effectively activate picture whenever you either press “p” or “P”.
the selected camera.
Look at the highlighted line:
Using the keyboard in Processing saveFrame(“pic-######.png”) — this is the
We want to capture an image when someone method that saves an image in the sketch folder
touches the jar, and it is good to test that func- using the name “pic-######” in PNG format,
tionality beforehand. I would suggest you imple- and with that extension. The string of hash signs
ment and test something like using the keyboard ###### represents the picture number. Differ-
to take a picture. Just modify Listing 2 with the ent pictures will have different numbers.
code in Listing 3, and the camera will store a
Note that saveFrame() saves the information
contained inside the application’s frame only —
Listing 4
not the rest of the desktop.
void draw() {
if (cam.available() == true) { Timestamp that picture!
cam.read(); As saveFrame()writes a pixel-by-pixel copy of
}
your application into a file, it is possible to add a
image(cam, 0, 0);
layer of information on top of the image. In our
String timeStamp = String.format(“%02d”, hour());
case, we are interested in knowing when the jar
timeStamp += “:” + String.format(“%02d”, minute());
timeStamp += “:” + String.format(“%02d”, second()); was opened and its precious contents thieved! In
timeStamp += “ “ + year(); CSI Miami speak: the crime has to be evidenced
timeStamp += “/” + String.format(“%02d”, month()); in terms of time. So let’s put a timestamp on the
timeStamp += “/” + String.format(“%02d”, day()); camera picture as shown in Listing 4. This will
also print a note to STDOUT.
text(timeStamp, 10, height-10); // superimpose text on
image An experimental but successful snapshot is shown
in Figure 1. The low resolution is obviously due
// for the keyboard detection to work, you need to have
to the webcam, but the detectives will be equally
// clicked on the application window first (aka focus)
happy.
if(keyPressed) {
Next thing is writing some Arduino code to deter-
if (key == ‘p’ || key == ‘P’) {
saveFrame(“pic-######.png”); mine whether someone touched the jar, and
println(“capturing Frame at: “ + timeStamp); // report immediately return a command to the computer.
to the console
} Detecting touch with Arduino:
} CapacitiveSensor Lib
} Inside archive file 120745-11.zip created for
this article you will find a folder named “Ardu-
ino” which has a subfolder called “libraries”. The
Listing 3 archive file may be downloaded for free from
[6]. You should copy the contents of that folder
void draw() {
inside your Arduino libraries folder. The latter is
if (cam.available() == true) {
cam.read(); located inside your Arduino sketchbook folder,
} usually stored at “My Documents/Arduino” in
image(cam, 0, 0); Windows computers, or “Documents/Arduino”
in Mac and Linux.
// for the keyboard detection to work, you need to have
// clicked on the application window first (aka focus) The CapacitiveSensor library was originally made
if(keyPressed) { in 2008 by Paul Badger [5] and it comes with
if (key == ‘p’ || key == ‘P’) { one single but clear example. I recommend you
saveFrame(“pic-######.png”);
take a look at the Arduino playground page ref-
}
erenced at [5]; there you will find everything you
}
need to know about how capacitive sensors work.
}
Essentially, the library uses two digital pins: one

194
40 | April 2013 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Arduino on course

to send a pulse, and one to read that pulse. Both


pins are connected through a resistor of a certain
value (1 MOhm for us) and leaves the receiving
pin ‘open’ though a wire or piece of conductive
metal that will act as an open-ended capacitor.
The mere presence of the human body will modify
the capacitance value of such a pin and therefore
modify the amount of time it takes for the signal Figure 1.
at the receiving pin to reach a value that can be Detail of captured image
understood as logic High. The CapacitiveSensor with superimposed
library measures that time — if it is long enough, timestamp.
most likely a human being is interacting with the
jar opening pin and we are in a position to pho-
tograph the culprit red handed.

Capacitive sensors are literally everywhere in


our digital lives. These devices are so sensitive
they can be hidden behind plastics, wood, and
any other non-conductive materials. At the same
time, extending the coverage of the touch sen-
sors is as easy as adding more metal to them
and configuring a couple of passive components
(resistors and capacitors).

The circuit we are going to add to Arduino boils


down to a single 1-MOhm resistor and a couple of
wires. On top of that, considering that our guard
might have to shoot a picture at night, we added
an ultrabright LED board from TinkerKit to easily
illuminate the scene. We made the guard’s mouth Figure 2.
from translucent acrylic sheet (plexiglass) for the Arduino connection diagram
light to shine through. Check the ‘schematic’ in for the project (made with
Figure 2 for more details on the construction. Fritzing).
Back to software, the Arduino code needed for
performing all of these operations is fairly simple • touch the sensitive area and observe the
as you can see in Listing 5. measurement in the Serial Monitor;
• make THRESHOLD = (MAX_VALUE +
For those of you with some experience with Ardu- DEFAULT_VALUE) / 2 and change it in the
ino, notice that I highlighted the lines that belong code.
to the new library in use. You will need to config- When your program detects a value coming from
ure the THRESHOLD constant to fit your specific this homebrew sensor to be over the THRESHOLD,
circumstances. If you check Figure 3 you will see it will return the character ‘p’ to the Processing
we cut an ‘antenna’ out of aluminum foil to place application through the serial port. The only two
underneath our cookie jar. The shape and size of things missing now are: fixing the Processing
that antenna determine the times measured by program to trigger the camera shot through the
the library. You will have to configure the value serial communication with Arduino, and mount-
of the THRESHOLD constant for the program to ing the trap.
operate properly. Follow these steps:
Triggering the camera from Arduino
• connect your circuit to the aluminum foil; Basically you need to modify your Processing
• measure the default value, depending on application to include the serial library, and read-
how much foil you have this value should be ing data whenever it arrives through the port as
in the range of 200; shown in Listing 6.

195
www.elektor-magazine.com | April 2013 | 41

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Mounting the trap used. Tien’s construction is pictured in Figure 4.


Our friend Tien Pham designed a Cyclops-like, As explained earlier, we made the touch sensor
monstrous Cookie Guard that got cut on a laser from a piece of aluminum foil. It’s shaped like
cutter at the local FabLab. Tien cleverly used the the letter ‘i’ but with a colossal dot. The dot is
mechanical properties of our webcam to become the antenna where we put our jar on. The alu-
the neck of Cookie Guard. The camera sensor minum foil is glued with tape to the wire going
is hidden behind the guard’s only eye, and the to the breadboard and to pin number 5.
ultrabright LED is behind the mouth. There is
enough room behind the guard’s body to hide the Note that a metal jar was used; the project should
Arduino board and the small breadboard we have also work with other materials, but you may have
to make your sensor more sensitive by increas-
ing the value of the resistor from 1 MOhm to,
say, 10 MOhm.
Listing 5
#include <CapacitiveSensor.h> Closing words
This is a project that came to us as a fun thing
#define THRESHOLD 500 // Note you have to configure this
to do during a weekend, when we noticed some-
value
one had eaten our cookies. We were able to build
// declare the pins to be used everything out of small parts left over from other
// 1M resistor between pins 4 & 5 projects. There is a lot of room for improving
// ultrabright LED on pin 7 this design: you could start by soldering all the
CapacitiveSensor cs_4_5 = CapacitiveSensor(4,5); components on a prototyping shield, looking for
int ledPin = 7; a better material to build the sensor, make a bed
for the sensor, etc. For now, the result is shown
void setup() { in Figure 5.
// uncomment to turn off autocalibrate on channel 1
//cs_4_5.set_CS_AutocaL_Millis(0xFFFFFFFF);
However, I wanted to show that for building a
convincing proof of concept you need very lit-
// configure the serial port
tle, even when dealing with digital electronics.
Serial.begin(9600);
If I find more time, I will modify the Process-
// configure the pin for the LED ing code to post the pictures taken straight to
pinMode(ledPin, OUTPUT); a webserver, making the information available
} remotely in an instant.
(120745)
void loop() {
long sensorReading = cs_4_5.capacitiveSensor(30);

if (sensorReading > THRESHOLD) {


// turn on the light
Acknowledgements
digitalWrite(ledPin, HIGH);
Thanks to Paul Badger for his original Capacitive
// tell the computer to take a picture Sensor library for Arduino, created back in 2008.
Serial.write(‘p’); To Paul Stoffregen, who revised the original code
to work with Arduino IDE v1 and later. And to
// wait and then turn the light off Tien Pham from Malmö FabLab for modeling our
delay(2000); Cookie Guard with integrated webcam.
digitalWrite(ledPin, LOW);
}
else {
// uncomment these lines for configuring your system
// Serial.println(sensorReading);
// delay(200);
}
}

196
42 | April 2013 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Arduino on course

References
[1] Processing project: http://processing.org
[2] Issues when using webcams in Processing:
http://wiki.processing.org/w/Video_Issues
[3] List of packages to get GStreamer for Linux
to take webcams inside Processing:
http://forum.processing.org/topic/how-is-vid-
eo-on-linux-handled#25080000001764427
[4] Gstreamer official website:
http://gstreamer.freedesktop.org/
[5] Paul Badger’s CapacitiveSensor Library for
Arduino:
http://playground.arduino.cc/Main/
CapacitiveSensor
[6] Cooke Guard project software:
www.elektor-magazine.com/120745

Figure 5.
Framed!! Who’s stealing our
cookies?

Listing 6
import processing.video.*;
import processing.serial.*;

Capture cam;
Serial myPort; // The serial port

void setup() {
[…]

// we don’t need the camera at full blast


frameRate(1);

Figure 3. The all-DIY capacitive sensor.


// List all the available serial ports
println(Serial.list());
// Open the port you are using at the rate you want:
myPort = new Serial(this, Serial.list()[0], 9600);
}

void draw() {
[…]

if (myPort.available() > 0) {
int inByte = myPort.read();
if(inByte == ‘p’) {
saveFrame(“pic-######.png”);
println(“capturing Frame at: “ + timeStamp);
}
}
}
Figure 4. Detail of Cookie Guard’s neck construction.

197
www.elektor-magazine.com | April 2013 | 43

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Arduino on Course (6)


Report on the
Mobile Weather
Station
experiment

Arduino Verkstad (“Workshop”) was


tasked to create a set of education-
al experiments aimed at introducing
Highschool students to electronics. The
primary goal was to make it affordable,
yet engaging and challenging enough
to trigger their curiosity. Included in
the set of experiments is The Mobile
Weather Station, a cross-curricular
experiment combining natural sciences,
physics and technology.

By David Cuartielles, For the mobile weather station, we wanted stu- balloon, we had to figure out a different method.
Clara Leivas, and dents to be able to actively gather data from That, along with a few other unexpected issues,
Tien Pham different environments—in the city, through the complicated what we thought would be a rela-
(Arduino Verkstad) parks, and along the riverbanks. Each environ- tively simple project.
ment might provide a different set of data for In order to keep costs low, we decided to use
the students to use for comparison. a cluster of balloons rather than a single large
We decided to use tethered balloons so that stu- weather balloon. We purchased a consumer-size
dents could control the placement and gather data helium tank along with regular party balloons.
at higher altitudes. This also gave us the oppor- Searching online, we were able to estimate that
tunity to include a time-lapse camera enabling it would take about 25 or so balloons to lift the
the kids to correlate and visualize their data to Arduino, a shield, the sensors and a lightweight
the different environments. frame or container.
Next up was the anemometer. To measure wind
Decisions, decisions speed accurately wasn’t our goal so much as to
We set about gathering the required electron- be able to compare the speeds. Deciding to only
ics—a temperature/humidity sensor, a micro- measure rotations per second, we thought to use
phone, a lightweight spy camera, and a CO2 sen- a light dependent resistor (LDR) and an LED to
sor. To our knowledge, there were no ready-built create a sensor. The idea was to place the LDR
wind speed sensors that would fit our require- opposite the LED with a paper disk in between
ments. Most anemometers require a stable sur- the two. The disk would have a slot cut out and
face or object to attach to in order to get their as the blades would turn and intermittently allow
readings, but because ours would hang from a light to pass through to trigger the LDR.

198
70 | January & February 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Arduino on Course (7)

Problem solving
As part of our first attempt we tried placing the
LED very close to the LDR hoping the magnitude of
the readings would obviate the need for shielding.
As suspected, this wasn’t the case, so we decided
to find a dark box to house the electronics.
This presented another set of problems regard-
ing mechanic assembly, and so we set out minds
on using an infrared (IR) sensor and a black and
white paper disk instead. This looked more hope-
ful as it required just one electronic component,
meaning less room for mechanical error.
We tested the assembly and got it to work. The
next part was a bit trickier—how to actually catch
the wind in order to spin the disk. Because our
aim was to build a lightweight weather station,
we couldn’t exactly use its weight to stabilize it
Figure 1. A paper-and-tape crafted model of a turbine for
so that an anemometer could spin while having
use as an anemometer. Hopefully!
a stationary point as reference.
Again, to make the assembly reproducible any-
where by students, we decided to try papercraft.
We made a simple turbine blade out of paper and Figure 2. About a dozen balloons appeared enough to
tape (Figure 1). We mounted it horizontally so lift the Arduino Mobile Weather Station assembly, rather
than 25 as initially calculated.
that regardless of wind direction, it would spin.
In order to keep the balloons stable, we clustered
the balloons at the four corners hoping that the
weather station wouldn’t spin.

Blowing in the wind


Our paper mockup proved that it might work. In
any case, we got the IR sensor and paper disk
to work so we were quite happy. Time was now
upon us to test the proof of concept—we only
had the temperature/humidity sensor, IR sensor,
and spy camera.
We first tested the temperature/humidity sensor
and camera indoors. We walked over to the Uni-
versity building nearby, inflated the balloons and
were quite happy to realize we didn’t have to use
that many balloons (Figure 2). Up it went—we
did our high-fives as we loaded the results from
the SD card. Now it was time to test the make-
shift anemometer.
The West Harbor in Malmö, Sweden, is very windy
and we were hoping that it would yield good
results. So, out we went with the balloons. As
soon as the sliding doors opened the balloons
got sucked out and the tether pulled taut. The
balloons started to spin wildly and tangled their
strings. Not only that, but the winds were so
strong that the balloons and weather station blew
almost horizontally, seemingly close to the point
of breaking the tether string.

199
www.elektor-magazine.com | January & February 2014 | 71

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

was to mount the turbine vertically. The problem


was getting it to align to the wind so we tried
adding a tail similar to that of weather vanes.
That shifted the weight of the unit and simply
was too unpredictable as it oscillated in the wind.

Bidirectional turbine
Finally, we decided to design and 3D-print a tur-
bine that would blow in both directions. This was
achieved by twisting the shape of the blades
along its spinning axis. Since the test school we
were working with already had a 3D printer, they
could at least print the turbine out at a reason-
able cost. It was a compromise, but we couldn’t
think of anything better at the time (and time
was pressing).
The person in charge of the mechanics (that
would be me, David) didn’t have much experi-
ence with 3D printing—in fact, it would be his
Figure 3. Initially impressed It was only then that we realized what should first time. After a few tries, a rough, workable
with the Rokkaku kite. have been obvious. The design of the anemom- prototype was printed.
eter wouldn’t work because the balloons would We tested it again and were glad to find that,
never be upright if tethered. At best, it would be yes, the anemometer worked at almost every
at a slight angle. Perhaps it was because of the angle. At this point, we decided to also laser-cut
Figure 4. Connection
traditional design of free-floating weather bal- a frame out of MDF (plywood) so that it could
diagram intended for
loons that we didn’t consider this, but having a be mounted properly, and construction would be
Highschool kids working
at the “connect-wire-x-to- tether changed the dynamics completely. consistent. This would help to enable the sensors,
wire-y” level. Defeated, we tried several designs, one of which especially the IR sensor, to work well. (In terms
of cost, it would be relatively inexpensive for
us to use the communal laser cutter to produce
lightweight kits that we could send off. Again, a
compromise, but still affordable.)
Our joy was short lived as we again went to test
it outside (no balloons, just outdoors). Somehow,
the IR sensors were receiving a lot of interfer-
ence being outside. The only solution we could
find was to spray-paint the plastic casing black.
Eventually, we would have to print the casing
using only black plastic since other colors allowed
interference. The IR sensor proved to be just as
temperamental as the LDR. Moving the sensor
a few millimeters closer or farther from the disk
would prevent the sensor from reading values
correctly. In fact, it seemed that the IR sensor
we were using had a small working range toler-
ance, but we finally managed to get it working.

Goodbye balloons
We found that 3D printers, while being great for
prototyping, weren’t necessarily the most accu-
rate (perhaps it was simply a matter of inexpe-
rience) or smooth. Small points of friction where
the print was bumpy meant it now required more

200
72 | January & February 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


Arduino on Course (7)

wind, thus raising the speed threshold. Another


compromise, but one we again decided to take.
We thought we were nearing the finish line but
then remembered the issue regarding the bal-
loons. The idea of a kite came up and we figured
it would be best to try it that way. So, it was off
to research kites.
Our first foray into kite making was a box kite.
Someone mentioned an anecdote about a box
kite capable of producing enough pull to lift a
human, so we decided that would be our first
model. After building a rather sad looking kite
using dowels and trash bags, we managed to get
it flying... for about ten seconds before it crashed
back down. Adding wings as stabilizers helped,
but the area we were in had unpredictable winds
and the kite came crashing down—hours of work
gone with a few broken dowels.
Eventually, we happened upon a kite design called
rokkaku—a six-sided kite originating from Japan bly is pictured in Figure 5 as an exploded view. Figure 5. Final assembly of
that was said to be the most stable single-string More of these drawings showing the electronic the Mobile Weather Station
kite available. We built a mockup with bamboo side of things are available for free download- hardware. Temperature,
and plastic sheeting, and got it up and flying (Fig- ing from [1]. humidity, altitude and
CO2 level are measured,
ure 3). We were quite happy with the result, it
processed by Arduino and
being the first kite that any of us had ever built. Running the show
written to an SD card. The
We were set to bring the whole thing together We tried the weather station hanging from bal- system also takes pictures
for a test run . . . when it was then decided that loons, as well as from a kite. Both attempts at from above. Note the 3-D
all of these elements would be a bit too unpre- getting meaningful pictures out of the experiment printed turbine incorporated
dictable for our purposes. We needed something turned out bad. Therefore we decided to hang in the PCB.
a bit more foolproof and so we compromised yet the station from a long pole with a staff exten-
again by deciding to hang the mobile weather sion (Figure 6).
station from a long stick with a curved hook. This The first time this weather station was put into
actually turned out be a good and interesting practice was at the “Etopia Kids” Tech-Camp in
decision because it felt a bit more interactive. Zaragoza (Spain) that took place in June and July
Students could direct the weather station into the 2013. During this event, kids get exposed to dif-
trees to see if greenery would affect readings, or ferent interactive technologies during a period of
hover it over a bridge directly above the water. 5 days. They learn how to count in binary, how
Satisfied, we went back to working with the elec- to program Arduino boards, get robots to move,
tronics. We added the sound sensor and it worked and how to read environmental data and show
perfectly. The CO2 sensor was another matter. it on a display.
While it did work, there were complications. It The kids first assemble the station and then go
requires warming up and demands quite a lot of for a hike to capture data at different locations.
care on the source code, and therefore it gets Temperature, humidity, sound level and wind
hard to explain to the kids participating in the speed are captured at a constant pace together
workshop how the sensor works. Figure 4 gives with an image of the location from above. The
an idea of how everything gets connected up to participants then return to the computer lab,
the Arduino. and using the ‘Processing’ software application,
While we aren’t 100% completely satisfied with they map the information with the images and
the way the experiment turned out, we are sat- proceed to create a small presentation for the
isfied with the learning curve. We messed up and other groups explaining what they learned about
failed many times, but eventually, we got there. the different locations. The Processing “sketch”
Sometimes, there is success in failure. developed for the project is also available at [1].
The completed Mobile Weather Station assem-

201
www.elektor-magazine.com | January & February 2014 | 73

Personal Download for Petar Crnojevic | copyright Elektor


•Projects

Figure 6. After fruitless Lessons learned


attempts with balloons and As the time of writing we have been running the [1] Arduino software Processing sketch (.zip file);
kites, it was decided to hang experiment with kids for three days. It will be done electrical and assembly drawings (.zip file):
the Arduino Weather Station
a total of 15 times over the following three weeks www.elektor-magazine.com/130043 (free
from a long pole. Here’s
and 150 kids will get to try the weather stations. download).
what the teachers had in
One thing we have seen is that there are far too
mind… and an example of
how one kid built it. The many cables on the design. For a successful con-
turbine parts were produced tinuation of this or even the expansion to more
in different colors. sites, the current Arduino shield design needs to
have the components soldered to a board. Also,
the camera we hacked for taking the pictures
turned to be as weak as one could expect for the
price we paid. We had to resolder the wires that
“hack” the button on it several times.
We’ll definitely develop this experiment further
and if you have any feedback, ideas on how to
improve it, or know of similar successful exper-
iments that we can refer to, please feel free to
let us know at [email protected].

The illustrated story


The set of tech drawings presented to students About Arduino Verkstad
to assist in the assembly of the Arduino Mobile Arduino Verkstad (“workshop” in Swedish)
Weather Station is available for free downloading is a newly formed team—each of us
from the Elektor website [1]. One set of draw- specializes in different areas, some of which
ings illustrates the connection of the external overlap.
electronics to the Arduino main board (‘Balloon- Not everyone was directly involved in the
Experiment-xx.png), the other, the assembly of process, but nearly everyone was able to
the complete unit, including the pole it is hung contribute a bit of advice and guidance to
from (MDF_WeatherStation_Instructions-xx.png). the main developers, Tien and Clara.
(130043)

202
74 | January & February 2014 | www.elektor-magazine.com

Personal Download for Petar Crnojevic | copyright Elektor


MiCrocontrollerS

Android Switch Interface


Using an Android smartphone as a remote
control or user interface
for your microcontroller
projects

A low-cost Android phone forms an excellent basis for a


high-end user interface or remote control for a microcontroller
circuit. In this article we tell you how to implement various wireless
sensing and switching functions using an Arduino board with a Bluetooth
shield. We also describe how you can program your own Android app for this
purpose and what (free) PC software you need for this.

By Jos van Kempen (The Netherlands) capability, which can be used as a fancy remote control unit. Some
microcontroller boards have built-in Bluetooth capability, and with
others you can buy adapters or shields to add this capability. In this
Nearly all microcontroller circuits intended to control something article we use a small Arduino board with a Bluetooth shield (ITead,
have some form of user interface. This often involves several but- priced at around 15 pounds) augmented by a small I/O shield spe-
tons, knobs, LEDs and an LCD module. If you want something really cifically designed for this article.
nice, you might even use a touchscreen. A remote control can Articles about adding Bluetooth functionality to your own circuits
also be handy – preferably one that does not have to be aimed so have been published in previous issues of Elektor (September 2004
precisely. and February 2010). Elektor also published an article about program-
However, ‘luxury’ interfaces of this sort usually cost more and are ming Android apps in the June 2011 edition, and an Android control-
more difficult to implement. This doesn’t have to be the case. As ler using the audio output was described in December 2011.
you will see, an attractive user interface with remote control does
not heed to be expensive, and the programming is reasonably easy. Many of you are familiar with microcontroller programming,
There’s a good chance that your have a smartphone with Bluetooth although you may not have any experience with programming a

24 203 03-2012 elektor

Personal Download for Petar Crnojevic | copyright Elektor


MiCrocontrollerS

VCC
Arduino Board

R2
VCC RE2.A
1 G5V-2 D2

560R
R1 16 1N4148
RE1 K4 K8
1 G5V-2 D1

560R
VCC LED2
K5 K1 8 8
AREF
T1
mobile phone, so we devote only minimum attention to micro- RST
1 1
16 1N4148 R6
7 7
GND
2 2 6 6
controller programming in this article. However, we discuss 3.3V
3 3 LED1
4k7
5 5
D13
5V D12
smartphone programming in detail, from downloading and GND
4 4 T2 BC547B 4 4
D11
5 5 R5 3 3
installing the software to programming the various compo- GND
6 6 4k7 2 2
D10
Vin D9
nents of the desired user interface. We hope this information BC547B
R4 1 1
D8
100R
will be sufficient to enable you to program a user interface T3
R3

yourself for your own application with your own microcon-

560R
troller. The source code of the application described here (for LED3
BS170
both the microcontroller and the smartphone) can of course VCC

be downloaded from the Elektor website [1].


S1
K3 K7
R8
Hardware and microcontroller software K6 K2
1k
8 8
D7
7 7
A Bluetooth shield is fitted on the Arduino board. It commu- 1 1
R7
6 6
D6
A0 D5
nicates over the UART interface. In Bascom you can use the

10k
2 2 5 5
A1 D4
3 3 4 4
‘input’ and ‘print’ instructions to receive commands and send A2
4 4
R9
3 3
D3
A3 D2
data from and to the Arduino board. 5 5 2 2

1k
A4 D1
6 6 8 9 1 1
For this project we also developed a simple shield consisting A5 RE2.B
4
RE1.B
13
D0

of a pair of relays with LEDs (digital outputs), a PWM output

PWM
NTC

with a FET (‘analogue’ output), a switch (digital input) and an 6 11


VCC
NTC thermistor as an analogue sensor (analogue input). The
schematic diagram is shown in Figure 1, and the PCB layout
designed for this circuit is shown in Figure 2. This shield can 10 9 8 7 6 5 4 3 2 1
K9
be used to experiment with all of the options for communica-
tion between the Android smartphone and the Arduino board NTC

using Bluetooth. All relay, switch and sensor lines are available 120075 - 11
6k8
on connector K9.

The microcontroller software (written in Bascom) works as fol- Figure 1. Schematic diagram of the I/O shield consisting of a pair of LEDs
lows (see Listing 1). and relays, an NTC thermistor, a pushbutton, and a PWM output with a
FET and an indicator LED.
A loop checks whether a character has been received. If the
Arduino receives an ‘R’, output D11 is activated (LED1 lights
up and relay RE1 is energised). If it receives an ‘r’, LED1 and RE1 are a ‘P’ (short for ‘PWM’) is received, the routine ‘Input’ waits for a
de-energised. Output D13 and the second LED and relay behave in value (the smartphone must send the character string ‘\r\n’ after
a similar manner, but they respond to the characters ‘O’ and ‘o’. If the value), and this value is used to drive the PWM output. FET T3

COMPONENT LIST
Resistors K7,K8 = 8-way pinheader socket
R1,R2,R3 = 560Ω K9 = 10-way pinheader socket
R4 = 100Ω RE1,RE2 = 5V miniature relay (e.g. TE Con-
R5,R6 = 4.7kΩ nectivity type MT2-C93401 or OMRON type
R7 = 10kΩ G5V-2-H1)
R8,R9 = 1kΩ S1 = pushbutton with make contact (e.g.
B3F-1000)
Semiconductors PCB # 120075-1 (see [1])
D1,D2 = 1N4148
LED1,LED2,LED3 = LED, red, 5 mm
T1,T2= BC547
T3 = BS170
3

Figure 2.
1

Miscellaneous
K1,K2 = 6-pin pinheader
The PCB layout is designed such that
the connectors mate with a standard
4

K3,K4 = 8-pin pinheader


K5,K6 = 6-way pinheader socket Arduino board.

elektor 03-2012 204 25

Personal Download for Petar Crnojevic | copyright Elektor


MiCrocontrollerS

Listing 1. The microcontroller program (written in Bascom).


$baud = 9600 : Ucsr0a = &H00 'Thanks to J.F. Theinert
'Software under CC-BY-NC-SA licence by Jos van Kempen.
Config Adc = Single , Prescaler = Auto , Reference = Avcc 'ADC (analog) input initialize
Start Adc 'PWM (analog) output initialize
Config Timer1 = Pwm , Pwm = 8 , Compare A Pwm = Clear Down , Prescale = 8
Config Pinb.1 = Output 'PB1 =digpin9=pwm1a
Pwm1a = 0
Dim Pwm_str As String * 5 'text 0-255
Dim Pwm_b As Byte
Dim Value As Integer
D13 Alias Portb.5 : Config D13 = Output 'Dig13 no resistance needed for LED
D11 Alias Portb.3 : Config D11 = Output 'Dig11
D7 Alias Pind.7 : Config D7 = Input 'Initialize DigInput Dig7
Declare Sub Set_pwm
Dim B As Byte
Do
B = Ischarwaiting()
Print B
If B = 1 Then 'if incoming command
B = Waitkey()
Select Case B
Case "R" : D11 = 1
Case "r" : D11 = 0
Case "O" : D13 = 1
Case "o" : D13 = 0
Case "P" : Call Set_pwm
End Select
End If
Waitms 300
Pwm_b = Pwm_b + 3
Value = Getadc(0) 'A0
Print "T" ; Value ; "t"
Waitms 40
If D7 = 1 Then Print "G" Else Print "g"
Waitms 30
Loop
End
Sub Set_pwm
Input Pwm_str Noecho
Pwm_b = Val(pwm_str) : Waitms 30
Pwm1a = Pwm_b
Print "*" ; Pwm_b : Waitms 30
End Sub

has a maximum rating of 60 V / 0.5 A. LED3 provides an indication 2. The Android Software Development Kit (SDK) is available at [3].
of the PWM level. After installing the SDK, you should have a look at the rest of the
The measured value of the NTC thermistor sensor R9 is also printed site, where you can find a lot of information about program-
with the format ‘T;adc(0);t’, and the signal level at input D7 to which ming, help files and USB drivers for your smartphone (which you
pushbutton S1 is connected is printed as ‘G’ if it is high (‘1’) or ‘g’ if will need later for downloading your app). The USB driver may
its is low (‘0’). The interface is configured with standard data rate already be installed on your PC if you use USB to exchange pho-
of 9600 baud, which means that a small waiting time (around 30 to tos, music and so on between your PC and your smartphone.
40 ms) is necessary after a value has been sent. 3. Download the ADT plugin for Eclipse from the same site, and
make note of the folder it goes into.
Required software 4. We used Eclipse Classic 3.6.2 as the integrated development
The following software that you need in order to program apps for environment (IDE). It can be downloaded from [4]. (Note: the
Android smartphones can be downloaded for free: latest Android plugin at the time of writing was ADT12, which
is not compatible with Eclipse 3.7.)
1. The Java language is used for programming. The Java Develop- 5. After installing Eclipse, you have to install the Android plugin
ment Kit (JDK) can be downloaded from the Oracle website [2]. (under Help | Install new software | Archive). Select the ADT zip

26 205 03-2012 elektor

Personal Download for Petar Crnojevic | copyright Elektor


MiCrocontrollerS

file and enter the name ‘Android’. Then go to Windows | Prefer-


ences and look for the folder with the extracted Android SDK (in
lower-level folders, including ‘Tools’).
Go to Windows | Android SDK and AVD Manager, select New (Vir-
tual Device), and select Gingerbread for version 2.3.3 (or Sam-
sung_GIO or something similar) so that you can simulate the
program on the PC without a smartphone if necessary.
6. Download the folder containing the BluetoothInterface example
project from [1], but do not put it in the Eclipse workspace.

The BluetoothInterface project


The software that allows a Bluetooth device to find other Bluetooth
devices, establish contact and exchange messages is complicated,
but fortunately an example is included with the Android SDK. Unfor-
tunately, it apparently does not work properly with many Bluetooth
devices. A replacement for one of the files (BluetoothRfcom-
mClient.java) can be found on the Internet. After the declara-
tions are modified, it solves this problem (see [5] and [6]). Now you
can use the project to make your own interface.
After starting Eclipse, you can select File | New |Android project | to
create a new project (perhaps based on an example), but in this case
you already have a project that you want to import into the Eclipse
workspace. To do this, select File | Import.. | Existing Projects in Work- Figure 3. The file structure of the BluethoothInterface project.
space. Be sure to tick Copy projects into workspace, as otherwise the
original project will be overwritten. Browse to the folder where you
placed the downloaded BluetoothInterface project. change) by two radio buttons labelled ‘On’ and ‘Off’ (radioGroup
Various .java and .xml files are visible in the project file structure orientation horizontal).
(Figure 3). You may have to click the relevant folder to see them. The signal level on the analogue input is indicated by a horizontal
The ones we are interested in are BluetoothChat.java (main pro- progressBar (style: horizontal), a number in a textView and a chart in
gram), main.xml (smartphone screen interface) and strings.xml an imageView.
(declaration of the variables used in the interface). The PWM output with the FET is set by a slider on a seekBar.

Interface implementation
Double-click main.xml to display the smartphone screen interface
(see Figure 4). The tabs below the screen layout can be used to
switch between the graphical layout and the automatically gener-
ated code.
A horizontal layout is already defined on the interface, including a
ListView for the detected Bluetooth devices, an EditText for the enter-
ing the text you want to send during a chat session, and a button
for sending the text.
In many cases the easiest way to place a component is to drag it to
the Outline pane. An error may occur when you drag the size on the
screen if your PC is configured for a comma decimal marker. In this
case you must replace the ‘,’ in the file main.xml with a ‘.’.
When you place a button or a radio button, you can define the pro-
cedure that will be executed if it is clicked by entering the name of
the procedure for the OnClick property.

The LEDs and relays (digital outputs) on the shield are operated by a
set of buttons or checkboxes. For this purpose, place a linear layout
of checkboxes or (toggle) buttons on the screen or in the outline
(which is often easier). Figure 4. The interface screen layout. It’s often easiest to place the
The switch state (digital input) is indicated on the interface (for a controls in the Outline pane.

elektor 03-2012 206 27

Personal Download for Petar Crnojevic | copyright Elektor


MiCrocontrollerS

you must first select the right COM port in the terminal emulator
(e.g. Hyperterminal or Advanced Serial Port Terminal) and establish
a connection.

After the app has been downloaded and tested, establish a connec-
tion by clicking the menu button at the lower left and choosing the
desired Bluetooth device (select connect to device –secure). If every-
thing goes right, you should see the message ‘connecting’ followed
a short while later by ‘connected: <device name>’ (Figure 5).
The code in the BluetoothChat file may look like this:
Figure 5. Select ‘Connect a device – Secure’ and then select one of
the already paired devices or scan for devices that are configured private CheckBox chkD13, chkD11,chkDIM;
as ‘discoverable’. You have to enter a code for (initial) pairing; (The variable must be declared if the checkbox
‘0000’ and ‘1234’ are common codes. properties are read (or written) in the program)

chkD13 = (CheckBox) findViewById(R.id.chkD13);


You haven’t programmed anything yet, but you can already see what (The link between the name in main.xml (the screen
the interface will look like when it’s done. You can also run a simula- layout) and the name in the program is created in
tion on the PC with a virtual smartphone displayed on the monitor, the procedure ‘onCreate’)
but it isn’t possible to simulate a Bluetooth device with this.
Connect your smartphone to the PC with a USB cable and then public void chkD13Click(View view){
select the associated project folder. Right-click the folder and select if (chkD13.isChecked()==true)
Run As.. | Android Application. The app will be compiled and down- sendMessage(“O”); else sendMessage(“o”);
loaded to your phone. }
If Bluetooth reception is enabled, you can now receive data and dis-
play it on your phone. The procedure itself is very simple. Either an ‘O’ or an ‘o’ is sent,
depending on whether the checkbox is ticked or cleared. These are
If you wish, you can also test the app by communicating with a Blue- the commands that cause the microcontroller to activate or deac-
tooth USB stick plugged into the PC, in combination with a termi- tivate LED 2 and relay 2.
nal emulator program for sending and receiving data. Of course, The code for sending a value determined by the position of the
slider on the seek bar when it is released is a bit more complicated.
However, if you start typing the ‘quick fix’ assistant will point out
your mistakes and generate most of the code automatically. It also
automatically adds implements OnSeekBarChangeListener in the class
declaration.

public void onProgressChanged(SeekBar seekBar, int


progress, boolean fromUser) {
// TODO Auto-generated method stub
textView2.setText(Integer.toString(progress));
}
public void onStartTrackingTouch(SeekBar seekBar) {
// TODO Auto-generated method stub
textView2.setTextColor(Color.rgb(255, 48, 48));
}
public void onStopTrackingTouch(SeekBar seekBar) {
// TODO Auto-generated method stub
textView2.setTextColor(originalTextColor);
sendMessage(“P”);
Figure 6. The interface in use. The messages sent by Itead (the try{
Bluetooth shield) or Me (the phone) are visible at the top. Thread.sleep(1000);
Commands to be sent can be entered manually at the bottom. } catch (InterruptedException e) {
These features are handy for troubleshooting, but you may want to // TODO Auto-generated catch block
remove them for other applications. e.printStackTrace();

28 207 03-2012 elektor

Personal Download for Petar Crnojevic | copyright Elektor


MiCrocontrollerS

} RTemp=Temp;RTemp=RTemp/6;// 0-255 naar grdC


sendMessage (seekBar1.getProgress()+ // nooit hoger dan maximum progressbar
“\r\n”); A0.setProgress(Temp*4); //schaal progressbar
} Temp=Temp/2; //schaal grafiek
DecimalFormat formatter = new DecimalFormat(“#.#”);
The only things you have to add here are code to change the dis- textView1.setText(formatter.format(RTemp));}
played text value when the slider in the seek bar moves, code to
change the colour of the text when you are moving the slider, and The measured value is also plotted on the chart. The chart is erased
code to cause the phone to send a ‘P’ (which is the signal for the when the number of measured values reaches 150, after which the
microcontroller to call a procedure in which the desired PWM value outline with scale lines is drawn again:
is read using Input Pwm_str) followed by the character string ‘\r\n’
to mark the end of the message. xcoordoud=xcoord;xcoord+=1;
if (xcoord==1){ //tekenen kader en hulplijnen
There is also already a procedure that receives messages from the paint.setColor(Color.BLUE)
microcontroller and places them in the text box. The following code canvas.drawLine(0,105,150,105,paint);//10 grd
is important for this: canvas.drawLine(0,85,150,85,paint);//15 grd
canvas.drawLine(0,65,150,65,paint);//20 grd
case MESSAGE_READ: canvas.drawLine(0,45,150,45,paint);//25 grd
byte[] readBuf = (byte[]) msg.obj; canvas.drawLine(0,25,150,25,paint);//30 grd
// construct a string from the valid bytes paint.setColor(Color.YELLOW);
in the buffer canvas.drawRect(1, 1, 149, 124, paint);
String readMessage = new String(readBuf, 0, }
msg.arg1); if (xcoord==150) {xcoord=0;
mConversationArrayAdapter. canvas.drawColor(Color.BLACK);}
add(mConnectedDeviceName+ else
“: “ + readMessage); {canvas.drawLine(xcoordoud,
break; 125-Tempoud,xcoord,125-Temp,paint);
}
Now all you have to do is to ‘capture’ the message and assign the OldMessage=readMessage;
right values to the radio buttons or the progress bar according to
the message content. To prevent the application from starting up with a keyboard,
The radio buttons are controlled by the characters ‘G’ (on) and ‘g’ Androidmanifest | Application | Window soft input mode is set to
(off): stateHidden.

if (readMessage.contains(“G”)==true) This completes the discussion of the main points.


G1.setChecked(true); Of course, you will want to tailor the application to your specific
if (readMessage.contains(“g”)==true) needs. We hope that you now have enough information to be able
G0.setChecked(true); to do this yourself. The download on the Elektor website includes a
complete application file (.apk) that you can copy directly to your
For the progress bar, the code first checks whether the string smartphone and try out all of the features described here after
‘Txxxxt’ has been received. Here ‘xxxx’ is a number in the range of installing it.
0 to 1023, which is the digitised value of the signal level on the ana- (120075-I)
logue input. The entire string is evaluated because it sometimes
arrives in two pieces, which should not lead to an incorrect value:
Internet Links
if (readMessage.charAt(0)==’T’) [1] www.elektor.com/120075
if (readMessage.contains(“t”)==true){
[2] http://www.oracle.com/technetwork/java/javase/downloads/
Tempoud=Temp;Temp=readMessage.indexOf(“t”);
OldMessage=readMessage.substring(1,Temp); [3] http://developer.android.com/sdk/index.html
Temp=Integer.parseInt(OldMessage); [4] http://www.eclipse.org/downloads/
[5] http://projectproto.blogspot.com/2010/09/android-bluetooth-
The following code handles the value shown as text (the current
temperature); for the progress bar and the chart it is sometimes oscilloscope.html
necessary to recalculate and format the values due to the scale: [6] http://code.google.com/p/android-bluetooth-oscilloscope/

elektor 03-2012 208 29

Personal Download for Petar Crnojevic | copyright Elektor


Arduino Shields

BOTTOM VIEW 110092 - 11

By Michael Gaus (Germany)


junction with any of these three boards. ets on the Arduino boards is not an integer
The Arduino microcontroller platform is For hardware all we need is a standard piece multiple of 0.1 inch, and so it is necessary to
rather popular. One significant reason for this of perforated prototyping board and headers bend the headers slightly to make them fit.
is the wide availability of a range of daughter with a 0.1 inch (2.54 mm) pitch. The correct Turn the Arduino printed circuit board over
boards (which are called ‘shields’ in Arduino position for the headers can be obtained from and then attach the headers to the prototyp-
terminology) containing additional items of the drawing (which is viewed from the under- ing board with solder joints on its underside.
hardware, which can quickly and easily be side of the board).
plugged into and unplugged from the mother The photograph shows an example Arduino
board. The easiest way to start is first to plug the shield constructed in this way. The compo-
headers directly into the sockets on the nents of the expansion circuit can be mounted
It is easy enough to make a shield board your- Arduino motherboard. Then fit the proto- on the top side of the prototyping board and
self. The relevant header sockets are always typing board over the headers. Leave a small soldered on its underside. Ordinary wire can
found in the same place across the Arduino gap between the underside of the prototyp- be used to connect between the components
‘Uno’, ‘Duemilanove’ and ‘Diecimila’ board ing board and the plastic carrier of the header and the header pins.
versions and all have the same pinouts, which in each case to allow for soldering there later. (110092)
means that a DIY shield can be used in con- Unfortunately the distance between the sock-

209

2 7/8-2011 elektor

Personal Download for Petar Crnojevic | copyright Elektor


Arduino Nano Robot Controller
By François Auger (France)
This circuit is intended to be fitted onto the
front of the BOE-Bot mobile robot described
+5V
in [1]. Although there’s nothing to stop you RIGHT
using this circuit with any microcontroller, R5

it has been designed for connecting to the +5V

4k7
P1
Arduino Nano support board [2]. This support
RIGHT
board is a suitable size for fitting to this robot 250R 1
and can be connected to two servomotors D1 K1 R8
driving the robot by way of connectors that S1
1

2k2
have been provided for this purpose. VCC
IR C1
4
GL
IC1 330n
IS471F R7
The circuit shown here allows a mobile robot 2
VO 2k2
to detect information about its immediate GND
+5V
surroundings by means of two microswitches 3
RIGHT
(end-of-travel detectors), two photoresistors, C4
and three infra-red proximity detectors. All
330n R1
this will enable the microcontroller to steer +5V 220R
P2 R2
the robot correctly by sending appropriate
CENTRE 1M
commands to the servomotors. 250R VT935G
D2 K3 G1
The interface circuit for the three infra-red 1 Right IR sensor signal 1
detectors is standard, and has already been VCC 4
IR C2
Right switch signal 2
14
GL 15
used in [3]. Potentiometers P1, P2, and P3 let IC2 Right LDR signal 3
330n R9 16
you adjust the current drive to the transmit- IS471F 2 Centre IR sensor signal 4
VO 2k2 17
ting diodes, and hence the maximum distance GND 5
18
3 6
at which the detector will be able to detect 19
+5V Left LDR signal 7
the presence of an obstacle. The 2.2 kΩ resis- 20
LEFT Left switch signal 8
tors protect the microcontroller against the C5 Left IR sensor signal 9
21
22
accidental short-circuits that might occur if +5V 10
P3
330n R4
23
the microcontroller pin is configured as an LEFT 220R
11
24
output and generates a logic level different R3 12
250R 25
1M 13
from that generated by the detector. D3
VT935G
G2
1
IR C3
The microswitches make it possible to detect VCC 4 SUB-D25
GL
the presence of an obstacle on the route and IC3 330n
IS471F R11
thus avoid collisions. They force the micro- VO
2
2k2
controller’s input pin low. GND
+5V
3
LEFT R10

The two photoresistors make it possible to R6


2k2

follow a reflective track, so the robot can fol-


4k7

low a path marked out on the ground. They


are connected in such a way as to allow us to 1
measure their resistances using just a single K2
logic input/output: at the outset, the micro- S2
controller pin is configured as an output and
100395 - 11
set high to discharge the capacitor. Then the
pin is configured as an input, which puts it
into high impedance. The capacitor charges
via the photoresistor, so the pin goes from
logic 1 to logic 0 after a time that is propor- nect the Arduino Nano support board with Internet links
tional to the time constant RC. Hence by additional circuits (electronic compass, real- [1] Basic Stamp Programming Course, Elek-
measuring the time it takes the pin to go time clock, maths co-processor, accelerome- tor, September–December 1999.
from 1 to 0, we can measure the value of the ter used as an inclinometer, and so on).
[2] www.elektor.com/100396
photoresistor, and thus the intensity of the
light falling on it. On the web page for the article [4] you’ll find a [3] Basic Buggy, Elektor, April 1999.
few test ‘sketches’ along with the PCB design [4] www.elektor.com/100395
An additional expansion board that includes a for the additional expansion board.
quick prototyping area make it easier to con- (100395)

elektor 7/8-2011 210 25

Personal Download for Petar Crnojevic | copyright Elektor


MICROCONTROLLERS

Support Board
for Arduino Nano
By Philippe Frétaud & François Auger (Saint-Nazaire Institute of Technology, France)

Arduino boards exist in several formats. The standard board


(which itself also exists in several versions like the Diecimila, the
Duemilanove, the Uno, etc.) is the one that measures around 5 × 7 cm
and to which can be added a ‘shield’ — an Arduino extension board.

The LilyPad board is a circular Arduino for As these two outputs can’t supply much
clothing applications, and the Nano is a current, an additional 5 V linear regulator
small Arduino module (18 × 43 mm) spe- has been incorporated into the support
cially designed for use with prototyping board. The 9 V input rail is also wired to K6
boards and breadboards. and K7.
(100396)
In place of the standard Arduino’s female
connectors, the Nano has two rows of 15 K4
solder pins on a 2.54 mm (0.1”) pitch. So
LEFT SERVO
it looks quite a bit like the boards for older
R1
microcontrollers like the Basic Stamp 2 or 10k

the CUBLOC CB320, with an additional USB GND


K5
link that is ideal for current computers. K1
RIGHT SERVO
R2
Unlike a standard Arduino module, the 6 VDC S1
10k
3
GND
Nano needs a support board if we want to GND 2
1 D2
use it in an application. In this article, we’re 6
proposing a motherboard that was origi- 5 1N4148
4
+9V IC1 +5V
nally designed for a robotics application, D1
7805 3
1
but which can very well be used for other K2 1N5819
jobs too. The robotic aspect of this board C1 C2 2 C3 C4
can be seen in the 6 V supply and connec- 9-15 VDC 47u 100n 100n 1u
tors K4 and K5, to which a servomotor can GND 25V 25V
I/O09
I/O08

be connected. If you’re not using servos, GND

you can dispense with the 6 V supply.

For the rest, the board is very simple: All Y1 K6 K7


G1 G1
the Nano’s inputs/outputs are quite simply I/O11 16 15 I/O10 A0 14
1 I/O00 I/O00 1
14 A0
D13 D12 2 I/O01 I/O01 2
brought out to two 25-pin sub-D connec- 17
3V3 D11
14 I/O09 A1 15
3 I/O02 I/O02 3
15 A1
AREF 18 13 I/O08 A2 16 16 A2
tors (K6 and K7). AREF D10 4 I/O03 I/O03 4
JP1 A0 19 12 I/O07 A3 17 17 A3
A7 D9 5 I/O04 I/O04 5
3 A1 20 11 I/O06 A4 18 18 A4
A6 D8 6 I/O05 I/O05 6
A2 21 10 I/O05 A5 19 19 A5
2 A5 D7 7 I/O06 I/O06 7
The boards are powered by 9 V. The Nano A3 22
A4 D6
9 I/O04 A6 20
8 I/O07 I/O07 8
20 A6
A4 23 8 I/O03 A7 21 21 A7
has an on-board 5 V linear regulator, and 1 A5 24
A3 D5
7 I/O02 22
9 I/O08 I/O08 9
22
A2 D4 10 I/O09 I/O09 10
also makes available the 3.3 V rail produced A6 25
A1 D3
6 I/O01
+5V
23
11 I/O10 I/O10 11
23
+5V
A7 26 5 I/O00 24 24
by the USB interface chip. By means of JP1, A0 D2 +9V 12 I/O11 I/O11 12 +9V
27 4 25 25
+5V GND 13 AREF AREF 13
one of these two voltages can be connected GND
28
RESET RESET
3
GND G2 G2 GND
C5 29 2 GND
GND D0/RX
to K6 and K7, by fitting a jumper to contacts 30 1
100n VIN D1/TX
1 and 2 (5 V) or 2 and 3 (3.3 V). These rails +9V
are also available when the Nano is powered Arduino Nano Board 100396 - 11

via its USB port.

66 211 01-2011 elektor

Personal Download for Petar Crnojevic | copyright Elektor


READER’S CIRCUITs

Wireless Instrumentation Network


Measuring with Arduino and XBee
By Johan van den Brande (Belgium) ([email protected])

In this article we describe how to put


together a wireless instrumentation
network with the Arduino platform and
MaxStream XBee modules. The network
uses an EtherShield module to automatically
make measurement data accessible via the
Internet.

It’s not difficult to construct a wireless instrumentation network Serial commu-


with the Arduino platform. Here we use two stations to form the nication is an
network (see Figure 1). The first station is the node, which takes important
readings from the sensors and sends the results to the second sta- part of Arduino
tion, which is the gateway. The node consists of an Arduino nodule sketches. Most
with an XBee shield module. The gateway also consists of these two peripheral devices use
modules, plus an EtherShield module for communication with the this to communicate with
Internet. The resulting measurement data can be retrieved from the PC. The loop routine contains
the Pachube website [1]. the actual program, which controls read-
ing data or a signal from individual inputs,
Arduino responding to the input signals, and driving the outputs.
Arduino is an open-source microcontroller platform with a user-
friendly development environment, based on an 8-bit Atmel AVR XBee
microcontroller. It is used primarily by hobbyists and artists to XBee modules are a convenient way to add wireless communication
create interactive projects. The Arduino platform has a low entry to a design. The modules from MaxStream are an implementation of
threshold. You don’t need to know how to program in assembly lan- the ZigBee technology developed by the ZigBee Alliance, a nonprofit
guage or write your own boot loader. The programming language consortium of chip makers, technology providers, OEMs and end
you use is a lot like C, but all of the difficult tasks such as initialising users. ZigBee technology is intended to facilitate the creation of inex-
the microcontroller and communication with a PC are already taken pensive, low-power wireless sensor networks. The modules transmit
care of. The Arduino development environment is based on a pro- data at rates up to 250 kbps over a range of 30 to 100 m, depending
gram called Processing, which is used by graphic artists to create on the version (1 mW or 10 mW) and the ambient conditions.
visual masterpieces. It includes a handy library with lots of routines The modules can be used to replace a serial communication cable,
to help you achieve useful results quickly. but they can also be controlled through the Application Program-
The Arduino module has several digital ports and analogue inputs. ming Interface (API) mode to form a more complex wireless net-
The analogue inputs utilise the A/D converter of the AVR microcon- work. The modules are configured using AT commands. For serial
troller. Some of the outputs can be driven in pulse width modulation line emulation, it is important that both modules are configured with
(PWM) mode. If you add a small RC filter, the result is a nice ana- the same network ID and the same channel (CH). By default, the MY
logue signal. The basic functionality can be extended with modules parameter (the 16-bit module address), the DL parameter and the
called shields, which can be plugged onto headers on the Arduino DH parameter are set to ‘0’. This means that both modules can iden-
module. Shields are available for all sorts of applications, such as tify each other. The DL and DH parameters specify the destination
video and audio, joysticks, MP3 and so on. address (DL = lower 16 bits, DH = upper 16 bits). They determine the
A program for the Arduino module is called a sketch, and it includes reception options. These parameters may be configured in various
a setup routine and a loop routine. In the setup routine, the ports ways. If DH is ‘0’ and DL is less than ‘0xFFFF’, every module whose
are defined as inputs or outputs and the serial port is initialised. MY parameter matches the value of DL receives data from the trans-

Readers Circuits contain contributions from Elektor readers for experimental purposes and further development by others.
The circuit(s) presented on these pages have not been tested for reproducibility or actual use in the Elektor Lab.

36 212 11-2010 elektor

Personal Download for Petar Crnojevic | copyright Elektor


READER’S CIRCUITs

XBee XBee
Arduino EtherShield
GND AN0 +5V Arduino
Sensor

mitting module. If DH is ‘0’ and DL is ‘0xFFFF’, every module receives 10k


Router
the data transmitted by this module. If DH is not ‘0’ and DL is greater
pachube Internet
than ‘0xFFFF’, data is received only by modules whose serial number
matches the destination address of the transmitting module (SH of
the receiving module = DH of the transmitting module and SL of the
091092 - 13
receiving module = DL of the transmitting module).

Extension shields
In this project we use a ready-made shield called EtherShield, which
provides Internet access capability for the Arduino module. It has an
RJ45 connector and can be linked to a router or a switch by a UTP cable. Figure 1. The instrumentation network consists of a node, a
A separate software library is available for the EtherShield module. gateway and a data platform at www.pachube.com.
It’s usually possible to stack several Arduino shields on top of each
other, as long as there aren’t any conflicts between the inputs and
outputs that are used. Although a standard XBee shield is available
for the Arduino module, it poses a problem here because it can-
not be stacked with the EtherShield module. For this reason, we S2 Arduinoshield
JP3
developed a shield that can accept an XBee module and can also be RX
RX
+5V A5
IC1
plugged on top of the EtherShield module. TX
D2
XBEE/USB
78L03 +3V3
A4
A3
The design of our shield module is reasonably straightforward (see D3 S1
JP1
JP2 A2
D4 A1
Figure 2). We included the voltage regulator because the Pro ver- D5
TX
XBEE/USB
C1 C2 C3
A0
D6
sion of the XBee module can draw up to 100 mA, which is too much D7
10u 10u 100n

for the integrated regulator of the Arduino module. The XBee mod- D8 VIN
+3V3 +5V
ule also requires a 3.3-V supply voltage. D9
D10
GND1
GND2
XB1
The XBee module communicates with the Arduino module via D11
D12 XBee
+5V
+3V3

pins 1 (RX) and 2 (TX). The Arduino module also uses these pins for D13
1
2
VCC AD0/DIO0
20
19
RESET
AGND DOUT AD1/DIO1 S3
serial communication with the PC. As we want to be able to pro- AREF R1
3
4
DIN/CONFIG AD2/DIO2
17
18

10k CD/DOUT_EN/DO8 COORD_SEL/


gram the Arduino module with the XBee shield fitted, we inserted 5
RESET
AD3/DIO3
RTS/AD6/DIO6
16 RESET

6 15
a pair of switches in the communication path. The Arduino module R2 R4 7
PWM0/RSSI ASSOC/AD5/DIO5
VREF
14 R3
8 13
normally communicates with TTL-level signals on pins 1 and 2, so a
1k

1k
15k

ON/SLEEP
9 12
DTR/SLEEP_RQ/DI8 CTS/DIO7

voltage divider reduces the level of the input signal on the XBee RX
10 11
LED2 GND RF_TX/AD4/DIO5 LED1

pin to 3 V. Level adjustment is not necessary in the other direction, RSSI ASSOC

since the Arduino sees 3.3 V as a high level.


The PCB layout has been kept simple, and all of the components 091092 - 11

(except the pushbutton) are leaded types. The Eagle and PDF files
of the PCB layout are included in the download file for this article [2].
Figure 2. The schematic diagram of our Arduino shield is
reasonably straightforward.
Sensor options
We use the analogue inputs of the Arduino module in this project,
which means we can use simple sensors, such as an LDR to measure
light intensity. Another interesting application is measuring rela-
tive humidity. You can make a simple sensor for this by embedding
two nails about half a centimetre apart in plaster of Paris inside a VCC
length of plastic pipe. Connect one of the nails to +5 V and the other
to an analogue input pin and to ground via a 10-kΩ resistor (see
ANALOG IN
Figure 3).
A lot of other quantities can be measured using the digital inputs.
The number of ports can be expanded with an I2C bus device, such R1
10k

as the Texas Instruments PCA9535.


091092 - 12
All together now
As already mentioned, our system consists of two stations: the
node formed by the Arduino and XBee shield modules (Fig- Figure 3. A simple humidity sensor can be made by embedding
ure 4) and the gateway formed by the Arduino, XBee shield and two nails in plaster of Paris inside a length of plastic pipe.

elektor 11-2010 213 37

Personal Download for Petar Crnojevic | copyright Elektor


READER’S CIRCUITs

The Internet of Things


In the last while there’s been a lot of activity related to the ‘Internet type (GET, POST, PUT or DELETE) and the resource, which is where
of Things’, which means connecting everyday objects to the Internet. the command is supposed to do its work. It may be followed by other
Sensor data platforms such as the Pachube website are a good exam- header lines that supply various parameters to the web server, such as
ple of this. On this site you can store and retrieve sensor data for pur- the type of content your client is able to process. A header line consists
poses such as displaying a chart or maintaining a log. Another poten- of a name and value. For the application described in this article, the
tial application is monitoring sensor values and performing a suitable API key belonging to the feed is placed in a header line.
action if they exceed a defined level, such as sending an e-mail or text The header is followed by the data. The following is an example of a
message. Pachube is a publicly accessible site with a simple protocol PUT request to the Pachube website:
for sending data to the site. You can assign geographic coordinates to
your sensors, which are then shown on a map of the world. The data
can be viewed in the form of charts, and you can also grant other peo- PUT /v2/feeds/ENTER_FEED_ID_HERE.csv HTTP/1.1
ple access to your data. Instead of sending data directly to other par- Host: api.pachube.com
ties, you can publish it once on the Pachube site, where other parties X-PachubeApiKey: ENTER_YOUR_PACHUBE_API_KEY_HERE
can subscribe to receive your data stream.
Content-Length: 10
After registering on the Pachube site, you have to create a feed. You
Connection: close
should click ‘Manual update’ when you configure your feed, since this
allows the microcontroller to determine when to publish new data.
With the other option, ‘Automatic’, the Pachube site actively sends 0,100
Web request commands to fetch the data. To make this possible, you 1,244
would have to embed a web server in the microcontroller and config-
ure your network to allow access to the microcontroller from the Inter-
The HTTP protocol is easy to implement in a sketch (an HTTP-based
net. After you create your feed, you are assigned an API key.
protocol of this sort is called a REST API). It is even possible to test the
The microcontroller uses the HTTP protocol for manual updating. This adaptation of the feed from the console, for example with the curl
is a very simple text-based protocol that supports the usual task of command:
retrieving data (GET command), as well as sending data (PUT com-
curl --request PUT --header “X-PachubeApiKey: YOUR_API_KEY” --data
mand), modifying data (POST command), and deleting data (DELETE
“0,100” “http://www.pachube.com/api/feeds/YOUR_FEED_ID.csv”
command).
The curl function is available in the standard OS X installation and can
An HTTP request consists of a header and a body, separated by a blank
easily be installed under Linux. Windows users can download it from
line. The first header line contains the protocol version, the command
http://curl.haxx.se/download.html.

EtherShield modules (Figure 5). Plug the EtherShield module onto Firmware
the Arduino gateway module first, and then plug the XBee shield This brings us to the firmware, or as it is called, the sketches. The
module on top so its pins and switches are readily accessible. Set sketch that runs in the node (see the program code in the download
both switches in the USB position when you want to program the package [2]) is the simplest. Briefly, it waits for a certain time, takes
Arduino module, and set them to the XBee position when you a snapshot of the analogue inputs, and sends it via a serial link to the
want to transmit or receive data with the XBee module. If you only XBee module. The following description is based on the program
want to receive data from the XBee module, set the RX switch listing with line numbers provided in a separate document.
to the XBee position and the TX switch to the USB position. This
allows you to display IDE debug information on the serial port con- The time interval for reading and forwarding the measurement data
sole of the Arduino module. It may be convenient to fit the board is specified in line 10. Here it is set to 5 seconds, which is the short-
with headers with jumpers instead of switches so you can open the est allowable interval for sending data to Pachube with a non-pro-
TX signal path between the Arduino and XBee modules, which is fessional account. Line 11 assigns a unique name to the node. This
handy for debugging. name is not used at present, but you could use it in the gateway to
XBee modules must be properly configured in order to communi- distinguish between different nodes. In the setup routine, the trans-
cate with each other. They are supplied with a factory default con- mission rate is set to 9600 baud in line 42 (the standard value for the
figuration for operation in serial line emulation mode. You can con- XBee modules). Furthermore, serial communication is configured to
figure them by using the terminal emulator utility in a Windows, 8 bits, no parity and 1 stop bit without any additional parameters.
Minicom or Linux environment to send them Hayes AT commands, The loop routine is fairly simple. It calls the intervalPassed routine,
or by using the X-CTU software supplied by MaxStream [3]. This does which determines whether the configured interval (5 seconds) has
not require any special hardware. Set both switches to the USB posi- expired. If it has, the measure routine is called. First we send the
tion and unplug the AVR microcontroller from the Arduino module. name of the node to the XBee module (lines 29 and 30), followed
Now you can use the USB link to communicate with the XBee mod- by a colon (:). The for loop in lines 32–35 polls all of the analogue
ule via the PC. ports and sends their values to the XBee module (line 32). Line 34

38 214 11-2010 elektor

Personal Download for Petar Crnojevic | copyright Elektor


Advertisement
AFFORDABLE
inserts a comma after each analogue value (except the last one)
EXPERTISE
to separate the values. Line 37 finishes off with a new line.
THE PC OSCILLOSCOPE RANGE FROM
The sketch for the gateway is more complex because it also PICO TECHNOLOGY
looks after the Internet link to the Pachube website (see inset
‘The Internet of Things’). The gateway waits until a full line has
been received from the serial link and then sends the name
of the measurement method and the sensor values to the
Pachube site.

Before using this sketch, you must edit it to have the right
parameter values for your Pachube account and network. In
line 13, enter the ID of the feed you have created, and in line 14,
enter your API key (from My Profile > Settings at [1]).
Connect the gateway to a router or switch so it can access the

BANDWIDTH
20 MHz to 12 GHz
SAMPLING RATES
50 MS/s to 5 GS/s
MEMORY
Figure 4. The node for reading the sensors consists of an 8 kS to 1 GS
Arduino module and an XBee shield.
RESOLUTION
Internet directly. Configure the network parameters in lines 16
8 to 16 bits
to 18 by putting the MAC of the EtherShield module in line 16
and its IP address in line 17. A MAC address identifies a specific PRICES
device in an Ethernet network. You can use nearly any value you
want for the MAC as long as it does not cause a conflict with
£125 to £6995
other devices connected to the router or switch. Choose an
unused IP address in the address space of your local area net- Latest Software Updates: I²C & CAN bus decoding,
work and enter it in line 17. Here you must replace the dots
in the IP address with commas, since the code in lines 16–18 mask limit testing, advanced triggers,
defines a set of arrays. The IP address of the Pachube site is spec- digital low pass filtering, rapid triggering
ified in line 18. In more elaborate software you could use the
Domain Name Service (DNS), which translates domain names
into IP addresses, but the approach used here is adequate for
our purposes.
www.picotech.com/scope2023
Line 20 allows you to set a debug flag that activates the _LOG
macro in line 23. This macro first reserves 256 bytes on the stack

elektor 11-2010 215 39

Personal Download for Petar Crnojevic | copyright Elektor


READER’S CIRCUITs

function returns the next token or character each time it is called.


As a result, when the for loop in lines 78–82 has completed execu-
tion, the full line has been analysed and the corresponding sensor
values are located in the sensor structure. The atoi function converts
an ASCII number to an integer value.

The connection to the Pachube site is established by the pachubePost


function (line 36). It receives the sensor structure as an input parame-
ter. The name is not used, but you could use it to select a different feed.
Lines 42–46 convert the sensor values into comma-separated values.
The format consists of the sequential number of the sensor and the
value, separated by a comma. Each sensor is on a separate line.
Lines 49–61 handle the actual data transfer between the gate-
way and the Pachube site. Line 49 establishes a connection to the
Figure 5. The gateway, with an adapter board that allows the XBee Pachube site at the TCP level. Once this connection is available,
shield to be used together with an EtherShield module.
the print and println functions can send data to the Pachube site.
Line 52 outputs a PUT command to Pachube, along with the feed
name (FEED_ID). The data is sent as a CSV file, which is why the key
as a C string in the m variable. This is followed by a formatted print has the .csv extension. The HTTP 1.1 protocol is used for this. Sev-
command (snprintf) for this string. Like the printf (and snprintf) func- eral header lines are sent as well. Line 53 sends the host header line,
tion, this macro can receive a variable number of parameters. This which indicates that the data is intended for the pachube.com host.
is indicated to the compiler by the ellipsis (…) in the macro defini- This construction allows more than one domain to be hosted from
tion. The construction ##__VA_ARGS__ expands this variable num- a single IP address. Line 54 sends the API key. Pachube uses this
ber of parameters in code that calls snprintf. If you disable the debug unique key instead of a user name and password. Line 59 terminates
function by commenting out line 20, the _LOG macro is expanded the header with a blank line, after which the sensor data is sent by
to nothing (line 25). line 60. The data length must be the same as the value stated in
Lines 27 and 28 link in the Ethernet library. This library is necessary the Content-Length header. After this operation, the feed has been
for using the EtherShield module. The string library (line 29) is nec- supplied with new data and the current values and history can be
essary for snprintf and strncat, among other things. retrieved from the Pachube website.
Line 30 specifies that six sensors will be read, and lines 31–34 define
the sensor structure. The data received from the remote sensor is Final remarks
transformed to this structure. Line 35 creates an EtherShield client It’s easy to put together a wireless instrumentation network with
object: the TCP client, which establishes a connection to server on MaxStream XBee modules linked to Arduino modules. Serial line
port 80 at the Pachube IP address. emulation allows data to be sent and received relatively easily.
An EtherShield module handles the connection to the Internet.
The core of the sketch is the loop function in lines 103–112, which Although it is possible to use more then one sensor node, you have
runs reiteratively. Lines 105 and 106 define a character buffer (buf) to watch out for interference when two nodes send data at the same
for the data read from the remote node. The data is read in by call- time. It’s therefore better to switch to API operation and configure
ing the function readRemoteSensors (line 109). After a full line has a mesh network or star network. This requires considerably more
been received, it is analysed in line 110. The parse function con- complex software, although the hardware remains the same.
verts the data to the sensor structure. The pachbubePost function in (091092-I)
line 111 sends the converted data to the Pachube site.
The readRemoteSensor function defined in lines 85–97 reads data Internet links
from the serial port and places it in the buffer (buf) until the ‘new
line’ character \n is received or the buffer is full (while loop at [1] www.pachube.com
line 90). Line 91 checks for new data on the serial input. If new data [2] www.elektor.com/091092
is present, it is read in line 92 and placed in the buffer, and the buffer [3] www.digi.com/support/kbase/kbaseresultdetl.jsp?kb=125
pointer i is shifted one position to the right. When all the data for
the buffer has been read, the routine sets the current buffer loca- [4] www.arduino.cc/en/Main/ArduinoXbeeShield
tion to ‘0’ and exits. [5] www.ladyada.net/make/xbee/arduino.html
The parse function in lines 67–84 uses the strtok function to analyse [6] www.faludi.com/projects/common-xbee-mistakes
the data in the buf variable. It split the string each time it encounters
any of the characters defined in the sep (separator) variable, which [7] www.adafruit.com/index.
in this case are the colon (:) and comma (,) characters. The strtok php?main_page=product_info&cPath=29&products_id=126

40 216 11-2010 elektor

Personal Download for Petar Crnojevic | copyright Elektor


DESIGN TIPS

A voltage booster using Arduino


By Clemens Valens (Elektor France Editorial) +5V

If your project needs a higher voltage rail than is already available L1


in the circuit, you can use an off-the-shelf step-up device. But when
68uH
you want a variable output voltage, it’s less easy to find a ready-
made IC. However, it’s not complicated to build such a circuit your- C2
*4n7
self, especially if you have a microcontroller board that’s as easy to D1 +4V3...+24V
program as the Arduino. And this also lets you experiment with the V+
T1
circuit so you can get a better understanding of how it works. 1N4936
Arduino
No surprises in the circuit — a largely conventional boost convertor. The R1
DIGITAL_PIN 11
MOSFET is driven by a pulse width modulated (PWM) signal from the 62,5kHz

82k
µC, and the output voltage is measured by one of the µC’s analogue IRF644
inputs. The driver adjusts the PWM signal according to the difference ANALOG_PIN 0
Vm R2 R3
between the output voltage measured and the voltage wanted. Arduino C1
*

22k

1k
We don’t have enough space here to go into details about how this 100u 35V
circuit works, but it’s worth mentioning a few points of special inter-
est. The small capacitor across the diode improves the efficiency of 090849 - 11
the circuit. The load is represented by R3. The components used
make it possible to supply over 1 A (current limited by the MSS1260T
683MLB inductor from Coilcraft), but maximum efficiency (89%) is grammed in assembler, allowing a maximum frequency of 62.5 kHz
at around 95 mA (at an output voltage of 10 V). To avoid damaging (the µC runs at 16 MHz). To sample the output voltage, a frequency
the controller’s analogue input (≤5 V), the output voltage may not of 100 Hz is acceptable, which means we can use Arduino’s standard
exceed 24 V. For higher voltages, the values of resistors R1 and R2 timers and analogue functions. The Arduino serial port is very handy
would need to be changed. — we can use it for sending the output voltage set point (5–24 V)
The MOSFET is driven by the µC, which is nothing but a little Arduino and for collecting certain information about the operation.
board. The Arduino’s default PWM signal frequency is around Thanks to the Arduino environment, it only took about half an hour
500 Hz — too low for this application, which needs a frequency at to program. You can download the software from [1].
least 100 times higher. So we can’t use the PWM functions offered (090894-I)
by Arduino. But that’s no problem, as the Arduino can also be pro- [1] www.elektor.com/090894

UV light box
By Gert Baars (The Netherlands) is not nearly as difficult as most people assume.
The required items are a housing with a sheet of glass, UV fluo-
Fabricating printed circuit boards is not something that every elec- rescent tubes and perhaps a timer. The latter is not really neces-
tronics hobbyist does for themselves. It is, however, not really that sary when a clock or watch is available. It therefore comes down to
difficult. The most important necessities are a PCB layout, a printer obtaining the UV fluorescent tubes with starters and ballast and a
(or perhaps a copier), a light box, photo-sensitive PCB material, housing with a sheet of glass.
chemicals and an etching tray. It is often the light box that presents There is a cheap solution for this. For the housing you can use a dis-
the most difficulties. carded sheet scanner with all the innards removed. The fluorescent
The PCB layout can be copied (using a copier) from an existing tubes could come from a face tanning machine, for example. In the
design or you can design it yourself using a computer and suitable 'prototype' made by the author the frame complete with the fluo-
software. The layout needs to be printed onto a transparency (make rescent tubes was cut out. This could then be placed in its entirety
sure that the transparency is suitable for use in laser or inkjet print- into the housing for the scanner. The accompanying starters and
ers). The necessary chemicals (sodium hydroxide for the develop- ballast fitted elsewhere in the old scanner housing and after con-
ing and iron(III)-chloride or copper-chloride for the etching) are not necting all the wires everything immediately worked as it should.
difficult to obtain. It is not necessary either to etch using a foam- Because the layout has to be in good contact with the PCB to pre-
etching box, but this does etch much quicker. Etching can simply vent shadowing, a sturdy piece of cardboard the same size as the
be done in a plastic tray, and etching with iron(III)-chloride will be a glass was attached to the inside of the lid of the scanner. It is neces-
little faster if the etchant is at about 40 °C. sary to apply some pressure on the lid during the exposure, but a
As already mentioned, exposing the PCB is often the most diffi- few books or fat catalogues on top of the lid is already sufficient. The
cult part. In the past, the PCB with the layout in an exposing frame exposure time for the best results with this construction appears to
would sometimes be placed in the bright sun and it is also possible be about 2-3 minutes.
to expose the PCB using UV lamps. To make a 'real' light box yourself (090088)

elektor 04-2010 217 75

Personal Download for Petar Crnojevic | copyright Elektor


MICROCONTROLLERS

Arduino + Theremin = Theremino


Using a Theremin oscillator as a proximity sensor
By Martin Nawrath (Academy of Media Arts, Cologne, Germany)

The Theremin is one of the very first electronic


musical instruments, dating back to the 1920s. It is
played by the musician bringing his hands close to its
two antennas. The oscillator at the heart of the Theremin
remains an interesting circuit in itself, and in this project we
connect such an oscillator to an Arduino microcontroller board.
The processor can detect the shifts in the HF signal from the
oscillator and convert them into an audible sound. However, this
is by no means the only possibility: we can also use the circuit to
convert hand and body movements into control signals for other
musical instruments, servos and computers.

This tiny oscillator circuit, when coupled a superhet circuit: the oscillator output is frequency changes when a human hand
with the software running on the Arduino mixed with a fixed frequency generated by (or other electrically conductive object)
microcontroller board, has a huge range a further oscillator, arranged so that the dif- is brought near to the antenna. The addi-
of potential applications, allowing prox- ference frequency is in the audible range. tional capacitance of the hand affects the
imity-based control of any other circuit Our circuit has just one oscillator, never- frequency of the resonant circuit in the
or system. theless designed around the same princi- oscillator (Figure 1). It seems reasonable
The circuit has already found use in many ple as the Theremin. The oscillator is con- to call this circuit a ‘Theremin oscillator’.
installations and objects at the author’s nected to an antenna, and the oscillator’s As in the original Theremin, we convert
college. One example is where the device is the modulated high-frequency signal into
interfaced to the Max/MSP music and mul- the audible range; but rather than using a
timedia development environment, which is superhet converter, we do the job in soft-
capable of producing sounds that provide a ware on the Arduino board. Our ‘There-
pleasant contrast to the square waves that mino’ therefore replicates just the pitch
the Arduino can generate directly. 4.1MHz ± ∆f control part of the original instrument. It
Oscillator
would be possible to build a second Ther-
What makes a theremin a emin, suitably modified to provide a vol-
theremin? ume control, to emulate the analogue
The Elektor editorial team felt it was possible Theremin fully.
that calling this project a ‘Theremin’ might
be a little misleading. The musical instru- LC oscillator using a 74HC00
ment named after Russian inventor and The circuit shown in Figure 2 consists of
engineer Léon Theremin (born Lev Termen) an amplifier, made to oscillate by coupling
consists of two antennas, each connected its output signal back to its input. At the
to an oscillator. One oscillator controls the input to the amplifier is a parallel resonant
081163 - 11
pitch of the instrument and the other the circuit, made from a coil and a capacitor,
volume. The original Theremin is a purely which determines the frequency of the
analogue device, with the conversion from Figure 1. The parallel capacitance of a oscillator. Any extra parallel capacitance
the modulated high-frequency signal to human hand near to the oscillator affects due to the connected antenna will affect
an audible frequency being performed by its frequency. this frequency.

32 218 11-2009 elektor

Personal Download for Petar Crnojevic | copyright Elektor


The amplifier is made from two NAND gates
from a 74HC00 connected in series. Each is +5V
equipped with a resistor (R1 and R2) to pro-
vide negative feedback, which causes the C2 14
gates to behave as amplifiers. C3 provides C3 IC1
feedback from the output to the resonant 100n 7
circuit at the input consisting of L1 and C1. ANT
10p
C4 couples the signal on the resonant circuit
into the input of the amplifier. The resonant
IC1.A IC1.B IC1.D IC1.C
circuit is also connected to the antenna. The C4 1 4 12 9
3 6 11 8 F_OUT
theoretical resonant frequency of the LC 2 & 5 & 13 & 10 &
combination is 4.11 MHz. 10p

L1 R1 R2
The oscillator is followed by the two remain- C1 100k 100k
ing gates of the 74HC00, used to square up GND1
IC1 = 74HC00N
its output waveform into a TTL-compatible 150p
NP0 10MH
signal. This signal is suitable for connection GND2
to a digital input on the Arduino board.
081163 - 12

Components and construction


Capacitor C1 in the LC network should be Figure 2. Circuit of the LC oscillator using the 74HC00. To increase the sensitivity of the
a ceramic NP0 type (such as Farnell order circuit to the proximity of a human hand, an antenna, made from a length of wire, is
code 9411720) for best temperature stabil- connected to the LC network.
ity. L1 should have a high Q factor. A suita-
ble type is the Fastron SMCC-100K-02, which
has a Q factor of 65; it is difficult to do better used, including the ‘Elektorino’ design that ital pin 5 (PD5, pin 11 on the ATmega168 [3]).
than that, even with a hand-wound coil. we published in February 2009 [2]. The oscil- This pin has the extra function of acting as
lator circuit of Figure 2 is provided with +5 V an input to hardware counter/timer Timer1
The circuit can be built, like the author’s and ground from the Arduino board and the in the ATmega168. To detect the frequency
prototype, on a small piece of prototyping oscillator output (fout) is connected to dig- shifts of the oscillator, an accurate fre-
board. To reduce drift with temperature, it
is a good idea to mount the board in a small
plastic enclosure. The software running on
the Arduino board also has features to help
compensate for temperature drift and com-
ponent tolerances.

The antenna that is connected to the LC cir-


cuit should be no longer than about one
metre (3 feet). A loop of 1.5 mm copper
wire (or, for greater mechanical strength,
steel wire) works well.

With the antenna operating at 4 MHz metal


objects and cables near to it (including USB
cables) will also act as parasitic antennas. It is
therefore important to keep the unit fixed in
place to avoid unwanted frequency drift.

Arduino software
For our tests in the Elektor lab we used an
Arduino Diecimila board [1] with software
downloaded from the author’s project web-
site. In principle any Arduino board could be Figure 3. The oscillator can be built on a small piece of prototyping board.

elektor 11-2009 219 33

Personal Download for Petar Crnojevic | copyright Elektor


Listing 1. Frequency is measured using Timer1 as a counter and Timer2 to measure the gate time.
//******************************************************************
void f_meter_start() {
f_ready=0; // reset period measure flag
i_tics=0; // reset interrupt counter
sbi (GTCCR,PSRASY); // reset prescaler counting
TCNT2=0; // timer2=0
TCNT1=0; // Counter1 = 0
cbi (TIMSK0,TOIE0); // disable Timer0 again // millis and delay
sbi (TIMSK2,OCIE2A); // enable Timer2 Interrupt
TCCR1B = TCCR1B | 7; // Counter Clock source = pin T1 , start counting now
}

//******************************************************************
// Timer2 Interrupt Service is invoked by hardware Timer2 every 2ms = 500 Hz
// 16Mhz / 256 / 125 / 500 Hz
// gate time generation for freq. measurement takes place here:

ISR(TIMER2_COMPA_vect) {

if (i_tics==50) { // multiple 2ms = gate time = 100 ms


// end of gate time, measurement ready
TCCR1B = TCCR1B & ~7; // Gate Off / Counter T1 stopped
cbi (TIMSK2,OCIE2A); // disable Timer2 Interrupt
sbi (TIMSK0,TOIE0); // enable Timer0 again // milli-s and delay
f_ready=1; // set global flag for end count period

// calculate now frequency value


freq_in=0x10000 * mlt; // multiply number of overflows by 65536
freq_in += TCNT1; // add counter1 value
mlt=0;

}
i_tics++; // count number of interrupt events
if (TIFR1 & 1) { // if Timer/Counter 1 overflow flag
mlt++; // count number of Counter1 overflows
sbi(TIFR1,TOV1); // clear Timer/Counter 1 overflow flag
}

quency counter is realised in the Arduino tion, called every two milliseconds under The frequency shifts and calibration values
firmware using Timer1 as a counter and control of Timer2 (see Listing 1). are output on the serial port for further
Timer2 as a timebase. When suitably con- processing or for viewing using a terminal
figured by the software, the counter incre- At the end of the gate period a global flag program on a PC.
ments by one for each pulse on the input variable is set. This signals to the main code
pin, typically over four million times per sec- (see Listing 2) that a new result is ready. A rudimentary DDS tone generator function
ond. Timer2 provides a gate time of exactly Since we are only interested in relative is implemented in software to produce an
1/10 s (100 ms). With an input frequency of changes in the input frequency and not its audible frequency on port B. The signal can
4.1 MHz Timer1 will increment 410 000 times absolute value, we subtract the first meas- be heard by connecting a piezo transducer
during the gate period, and the frequency ured frequency after power-up from each or small loudspeaker to digital pin 8 (PB0,
can be measured to a resolution of 10 Hz. reading. If after a preset number of read- or pin 14 of the ATmega168) via a 1 kΩ series
This precision is required in order to detect ings the frequency shift is less than a certain resistor. You can see and hear the circuit in
the relatively small frequency shifts caused threshold value, an automatic calibration is action in a video on the author’s project
by the Theremin effect. performed: this compensates for the effect website [4].
of long-term oscillator drift. The two par- (081163-I)
Timer1 is only a 16-bit counter and so it will ameters (number of readings and threshold
overflow several times in each gate period. value) can be adjusted to suit a particular
The overflows are counted and combined application. The calculated frequency shift
with the counter value to produce a final value (variable ‘tune’ in the listing) can be
result at the end of the gate period. All the used as a starting point for your own appli-
timing work is handled by an interrupt func- cation ideas.

34 220 11-2009 elektor

Personal Download for Petar Crnojevic | copyright Elektor


Listing 2. Excerpt from the main loop. The variable ‘tune’ contains the frequency shift as produced by the
proximity sensor. Automatic calibration compensates for the effect of long-term oscillator drift.
void loop()
{
cnt++;

f_meter_start();

tune=tune+1;
while (f_ready==0) { // wait for period end (100ms) using interrupt
PORTB=((dds+=tune) >> 15); // kind of DDS tone generator: connect speaker to portb.0 = Arduino pin8
}
tune = freq_in-freq_zero;
// use the tune value here for your own purposes like control of servos, midi etc.

// startup
if (cnt==10) {
freq_zero=freq_in;
freq_cal=freq_in;
cal_max=0;
Serial.print(“** START **”);
}

// automatic calibration
if (cnt % 20 == 0) { // try automatic calibration after n cycles
Serial.print(“*”);
if (cal_max <= 2) {
freq_zero=freq_in;
Serial.print(“ calibration”);
}
freq_cal=freq_in;
cal_max=0;
Serial.println(“”);
}
cal = freq_in-freq_cal;
if ( cal < 0) cal*=-1; // absolute value
if (cal > cal_max) cal_max=cal;
}

Internet Links
[1] www.arduino.cc/en/Main/
ArduinoBoardDiecimila
[2] www.atmel.com/dyn/resources/
prod_documents/doc2545.pdf
[3] www.elektor.com/080931
[4] http://interface.khm.de/index.php/lab/
experiments/theremin-as-a-capacitive-
sensing-device/

Figure 4. Arduino board with oscillator


circuit and piezo transducer.

elektor 11-2009 221 35

Personal Download for Petar Crnojevic | copyright Elektor


PROJECTS ARDUINO & MONOME

Touch LEDs for


Arduino
A cheap 4x4 Monome shield

By Clemens Valens (Elektor France Editorial)

Most of the projects published in Elektor simply provide a solution to a problem or fulfil a need. Even
though their designers have often tried to propose an elegant circuit or design an attractive PCB, the
aesthetic effect of the project itself, if there is one, usually takes second place. One exception is the
Monome open source project, a USB luminous matrix keyboard that was designed to be good-looking.
Here, it’s the application that seems to have been relegated to second place.

Let’s make it clear right from the start: only produced in small runs and their
Main Specifications the project shown here is not espe- prices are high (expect to pay €/£ 375
cially good-looking. It was inspired or $500 for a basic Monome) — espe-
• 4x4 Monome shield for Arduino by the Monome project [2], which is cially when you think that they are
attractive. Even if the design of a genu- nothing more than simple USB keypads
• Open source hardware ine Monome may not to your taste, it that don’t even work with MS Word!
• 16 push buttons has to be admitted that the aesthetic
aspect of the project is very important The aim of the project described here
• 16 LEDs
— you only have to visit the website to is to offer everyone the opportunity to
• TLC5940NT LED controller see for yourself. produce their own Monome for a cost
• 12-bit LED brightness control Exclusiveness seems to be one of the that is derisory compared with the
project’s other goals. Monomes are price of a ‘real’ one. What’s more, our

222
26 Personal Download for Petar Crnojevic | copyright Elektor elektor - 10/2009
Monome can be used for any other pur-
pose, since the software, like the hard-
ware, is open and you can modify eve-
rything. The brightness of each LED
is 12-bit adjustable, thanks to the LED 16x
driver, and we can dream up all man-
ner of fine, luminous objects. USB
ARDUINO PC
But just what is a Monome exactly?
A Monome is a rather special USB key-
pad. First of all, the keys, positioned 4x4 SHIELD
on a grid (usually square, though not
090527 - 11
necessarily so), do not have predefined
functions, and are all identical. In addi-
tion, each key is fitted with an indica-
Figure 1. Block diagram of our Monome. Here, ‘Shield’ doesn’t mean screening, but indicates an extension card for Arduino.
tor that makes it light up.

The Monome communicates with a


computer via USB. When we press or allows analogue values to be sent to OK, I want one!
release a key, the Monome sends the the computer.
co-ordinates of the key and its status. In fact, Monome is the name of the Once you’ve understood the concept
The application running on the com- company that developed the keypad, of the Monome, it’s easy to build your
puter that receives the co-ordinates which itself has names like 40h (8×8), own version. All you have to do is
of the keys decides how to interpret two fifty six (16×16), one twenty eight assemble a lot of keyswitches around
them. And the application also drives (16×8) or sixty four (8×8). So the name a small microcontroller, and the job is
the Monome’s lights. So the Monome indicates the number of keys. 40h is done. This is when you realize that key-
does not control its own lights — it’s the hexadecimal value for 64, and so switches with built-in indicators are
a bit like a keypad and a display built the Monome described in this article not very cheap, and that you’ll need 16
into the same housing. is called 10h, as it is based on the 40h, just for a little 10h Monome. The offi-
but only has 16 keys. cial Monomes use thermo-formed key-
Even though a Monome is a USB key- pads in transparent silicone. This type
pad, it doesn’t operate like a standard For those people who like to know eve- of cheap keypad is unfortunately not
keyboard and can’t be used to replace rything, Monome is a company that available to amateurs, who will have
one. This is because of the commu- sees itself as minimalist. Its name to make do with standard illuminated
nication protocol used by the Mon- refers to the monomial matrix, a square push-buttons at €/£ 3 each. That’s
ome, which is incompatible with nor- matrix that only contains 1’s and 0’s, why the following project is interest-
mal keyboards. And there are several with only a single 1 in any given row ing, because we’re going to explain
different Monome protocols, which or column. The company is fairly envi- how to make your own illuminated
makes thinks even more complicated. ronmentally-friendly, and its products push-buttons for less than €/£ 1! If you
Some Monomes include an accelerom- are manufactured with minimum envi- are good at DIY and a shrewd buyer,
eter and the communication protocol ronmental impact. it’s possible to build a 10h Monome

Programming the FTDI chip


MProg gives you access to the param-
eters of the FTDI chip on the Arduino (or - Check the Use Fixed Serial Number
other) board, and as you can see, there box
are quite a few of them! If you’re not -Enter an 8-digit serial number starting
careful, you risk disabling your USB in- with ‘a40h-’ — for example, a40h-001
terface, so don’t change any parameters
if you don’t know what they’re for. -Save the configuration: File -> Save
As…
MProg can be a bit temperamental.
Sometimes, it’s impossible to change - Click Device -> Program
between editor and programmer modes. Everything hangs up for a couple of sec-
It seems that opening or saving a file onds, then the message Programmed
should clear this blockage. The following Serial Number: a40h-001 ap-
procedure seems to work quite well: pears. Your Arduino is now Monome
-Run MProg compatible!

-Connect the Arduino board


- Click Tools -> Read and Parse

223
10/2009 - elektor Personal Download for Petar Crnojevic | copyright Elektor 27
PROJECTS ARDUINO & MONOME

26
S1 S2 S3 S4
5V
21
17
AN5 VCC LD1 LD2 LD3 LD4
18 27 28
AN4 3V3 OUT0
19 19 1
AN3 DCPROG OUT1
S5 S6 S7 S8 20 2
AN2 OUT2
21 27 3
AN1 VPROG OUT3
23 22 24
VIN AN0 XLAT LD5 LD6 LD7 LD8
28
IC2
16 4
RESET XERR OUT4
5
S9 S10 S11 S12 OUT5
ARDUINO 6
9 18 OUT6
D7 GSCLK 7
1 10 23 OUT7
AREF D6/PWM BLANK
2 11 LD9 LD10 LD11 LD12
AGND D5/PWM 8
3 12 26 OUT8
S13 S14 S15 S16 D13 D4 SIN 9
4 13 17 OUT9
D12 D3/PWM SOUT 10
14 25 OUT10
D2 SCLK 11
15 OUT11
D1/TX
16 TLC5940NT LD13 LD14 LD15 LD16
D0/RX 12
8 OUT12
D8 20 13
7 IREF OUT13
D9/PWM 14
6 OUT14
D10/PWM R1 15
5 C1 OUT15
D11/PWM GND
GND1 GND2 3k3 22
24 25 100n

090527 - 12

Figure 2. Monome circuit diagram. The Arduino board is based on an ATmega8 or ATmega168, as the PWM function is not used.

for less than €/£ 35. What’s more, the controller pins. Broadly speaking, the
project can be used for other things, as interface is divided into two parts, one
it is just a simple display keypad. for the data transfer and the other for
refreshing the LEDs. This interface can
be optimised by combining certain sig-
Let’s get down to business! nals, but this has not been done here.
We are basing our design on an LED If you are thinking of experimenting
Arduino board [3][4], which is inex- with this device, you may like to know
pensive and easy to program, but you that it lets you adjust the maximum
can use a different controller board if S current individually for each output,
you prefer. The only thing that really a nice option that could cause you to
matters is the USB interface, which waste a lot of time. If you can no longer
090527 - 13
absolutely has to be a variant of the get one or more LEDs to light up, or if
FT232R chip from FTDI, otherwise the the brightness levels are no longer the
communication software wouldn’t be Figure 3. How to construct a touch LED using an LED, a same, it could be that you have inad-
able to detect your Monome. Because keyswitch, and a little bit of patience. vertently modified the parameters of
our Monome uses Arduino, it one or more outputs. In this
belongs to the family of Ardui- case, disconnect the power to
nomes, which is no pointless reinitialize the device — just
distinction, since it requires resetting isn’t enough.
special software. R1 sets the maximum cur-
You’ll find the block diagram of rent for all the outputs, you
the project in Figure 1 and the can select this to increase or
circuit in Figure 2. As you can reduce the brightness of the
see, it’s quite simple, thanks Monome overall.
to Arduino and the LED driver
IC1. This IC contains 16 current
sources for driving 16 LEDs.
So, these keys?
Each output is controlled by We’re going to construct the
12-bit PWM (pulse width mod- Monome keys using 10 mm
ulation), offering 4,096 bright- LEDs and miniature push-but-
ness levels per LED. This tons (Figures 3 and 4). The
device has a slightly special idea is to use the LEDs to
serial interface, not very well press the push-buttons. The
explained in the data sheet, LEDs are large enough to hide
but which only requires six Figure 4. Building the prototype. the push-buttons, and seen

224
28 Personal Download for Petar Crnojevic | copyright Elektor elektor - 10/2009
from above, only the LEDs are visible.
To obtain vertical-action keys, the LED COMPONENT LIST
leadouts have to be bent in such a way
as to obtain a sort of ‘shock-absorber’. Resistors
R1 = 3.3kΩ
Then the push-button is slipped into
the shock-absorber and the LED + but- Capacitors
ton assembly is fitted to the board. C1 = 100nF
Concerning the LEDs, before you start
making the keys, check that all the Semiconductors
D1–D16 = LED, 10mm diam.
LEDS have the same brightness for IC1 = TLC5940NT
a given current. It can vary from one
LED to another, especially with cheap Miscellaneous
ones. Don’t skip this step, since once S1–S16 = miniature pushbutton,
6x6 mm, e.g. Omron type B3W-1000
the keys have been fitted, it’s not easy
2 pcs 6-way SIL pinheader, 0.1”
to remove them again. (2.54mm) lead pitch
2 pcs 8-way SIL pinheader, 0.1”
(2.54mm) lead pitch
Construction PCB # 090527-1 [1]
Arduino board
A PCB has been designed for this
project [1], see Figure 5. In keeping
with the ‘Open Source’ philosophy,
you’ll find on the web page for this Figure 5. Component side of the PCB.
project the complete Eagle file (circuit
and PCB) which you can modify as you
wish. Take care not to route any tracks
beneath the push-buttons on the com- imum) and then starts all over again. have opted for automatic detection of
ponent side, as the LED leadouts This loop lasts for around 40 seconds the Monome by interrogating the USB
already pass through this space. or so. If you press on an LED, the peripherals; it’s not possible to do this
Start by fitting R1, C1, and IC1. Then brightness of this LED is reset and it manually, which is a bit of a pity.
fit the keys, starting with the ones in restarts its loop. In this way, you can In order to be recognized as a Mon-
the centre of the grid. Fit the push- create some hypnotic sequences. The ome, the peripheral must have a serial
buttons carefully horizontal, and try to first reception of a Monome command number in the format a40h-xxx (xxx is
keep a small space between the LED exits the demonstration mode. For the for you to choose). We adopted a40h-
leadouts and the board to improve the moment, your circuit still isn’t a real 001. Refer to the box for details about
vertical movement of the keys. This job Monome, so it is unable to receive programming the FTDI chip.
requires a bit of patience and accuracy Monome commands — so let’s carry
to end up with a satisfactory result. on getting it ready.
Finish the wiring with the pin head-
On the computer side...
ers that have to be fitted on the solder As explained above, the FTDI chip also To finish off our Monome, or rather
side of the board. has to be programmed. You may not the operational testing, there are two
know it, but this device is programma- more pieces of software to be installed
ble thanks to a small EEPROM mem- on the computer (Figure 6). The first
Initial testing ory. FTDI provides the MProg tool for piece of software, Arduinome Serial [6],
Two components have to be pro- doing this [5]. This is necessary in is used to translate the Monome com-
grammed before the Monome will order to make our Monome work with munication protocol into MIDI (Musi-
work: the microcontroller and, surprise, the driver on the computer. In their cal Instrument Digital Interface [7], a
the USB interface! The microcontroller efforts to make it as simple as possible language dating from the 80’s, mainly
is programmed like an Arduino, since to use a Monome, the driver’s writers used for synthesizers) or into OSC
it is an Arduino, and this can be done
from the Arduino environment [4], but
if you prefer, you can flash the micro-
controller directly with the HEX file. PC
You’ll find all the source codes and the
HEX file at [1]. Arduinome Serial
If you’ve programmed your circuit with 16x
the software available in the article’s monome App.
monome USB 40h prot.
web page, your Monome now has a 10h
demonstration mode that lets us see if (4 x 4) MIDI / ex. MAX/MSP
the board is working properly. Restart OSC
the circuit and watch the LEDs. You’ll
see first of all that all the LEDs light
up briefly: flash! Then the program 090527 - 14
goes into a loop which progressively
increases the LED brightness from zero Figure 6. Arduinome Serial translates the data sent by the Monome into MIDI or Open Sound Control (OSC). The translated messages
up to a certain maximum (not the max- are sent to the Max/MSP application via the computer’s internal network.

225
10/2009 - elektor Personal Download for Petar Crnojevic | copyright Elektor 29
PROJECTS ARDUINO & MONOME

(Open Sound Control [8], a language package from [1] and unzip it onto your
that is more recent, more powerful, computer’s hard disk somewhere.
and more flexible than MIDI). Ardui-
nome Serial has to be used for Mono-
mes based on Arduino or, to be more
Final testing
precise, Monomes that use the FT232R Connect the Monome to the computer
chip for their USB interface. (For the via a USB cable and run Arduinome
others, there is Monome Serial.) Serial. If all is well, the software will
The second piece of software to install find the Monome and display the serial
is Max/MSP [9] (also see inset). This number you’ve just programmed for it
software is a powerful graphical pro- (Figure 7). There’s no need to mod-
gramming environment for music, ify the parameters for our tests, the
audio, and multimedia which is used default values will do.
for developing multimedia patches. Now run Max/MSP and load the Mon-
The part of the environment that runs ome_test.mxb patch, in the ‘Monome
the patches (the runtime) is free, which base’ package (don’t take any notice
lets you run them on any Mac- or Win- of the messages about matrixctrl). A

Max, Pure Data, jMax


Max/MSP is one of the pieces of music software most used by professional and amateur mu-
sicians alike; it lets you synthesize sounds, analyse, and record, as well as controlling MIDI
instruments. Originally called Patcher, Max was invented and developed by Miller Puckette
at IRCAM in the mid 80’s. The first commercial version was distributed by Opcode System
in 1990, and Cycling ‘74 [9] has been looking after its development since 1999. In 1996,
Miller Puckette, working at San Diego University, created a free version called Pure Data,
while IRCAM has developed a free version jMax in Java with a graphical interface. There’s a
substantial community of users and developers around Max/MSP, a collaboration that mainly
consists of exchanging ‘patches’ and ‘external’ objects, and suggesting improvements to the
Figure 7. Arduinome Serial detects the Monome automatically,
software. [source Wikipedia]
and the default parameters are good enough for testing.

Here’s what a PureData patch looks like for breaking down, modifying, and re-synthesising an audio signal using wavelets.
The rectangles in the ‘program’ part are objects that contain sub-programs,
the lines between the rectangles are the data flows.

Other music programming languages, albeit without nice graphical interfaces, are, for ex-
ample, Csound (www.csounds.com) and ChucK (http://chuck.cs.princeton.edu/).

Pure Data: http://puredata.info/


jMax: http://freesoftware.ircam.fr/rubrique.php3?id_rubrique=2

dows-compatible computer. So down- second window opens with two grids


load and install just the Max/MSP in particular (Figure 8), one for the
runtime. keys (‘keypads’) and the other for the
LEDs (‘lights’). Click on the ‘/sys/pre-
On the Monome website there are some fix/test’ button and check that Ardui-
patches for Max/MSP that will enable nome Serial now displays ‘/test’ in the
Figure 8. The Monome_test script for Max/MSP lets you check you to check your Monome is working Address Pattern Prefix box. If so, the
that a Monome is working properly. properly. Download the ‘Monome base’ two pieces of software are managing

226
30 Personal Download for Petar Crnojevic | copyright Elektor elektor - 10/2009
to communicate with each other. let you do a test that’s a bit more fun. you to modify the quite simple Mon-
Then, in the Monome_test window, Open the file and click the focus prefix ome software to sort everything out,
click the button next to the word ‘pair- button in the Monome_midi_64 win- as the options provided by Arduinome
ing’, just below the ‘keypads’ grid, and dow to change the Arduinome Serial Serial aren’t enough. Now it’s over to
select ‘press’. If you click somewhere in Address Pattern Prefix to </midi>. If you...
the ‘keypads’ grid, the corresponding you press an LED, you’ll hear a sound (090527-I)
box in the ‘lights’ grid changes colour. and you’ll be able to play a tune. You
Reboot the Monome. This is neces- can change the sound (the default is
sary because for some reason the piano) and the note values by clicking
Internet Links
automatic detection of the Monome and moving the mouse around in the [1] www.elektor.com/090527
by Arduinome Serial makes the serial matrix. [2] www.monome.org
link crash. Press the LEDs and you’ll
[3] www.arduino.cc
see the corresponding boxes in the You’ll probably have noticed that the
‘keypads’ grid light up. If you have boxes in the ‘keypads’ grid that light [4] www.elektor.com/080931
selected ‘press’, the LEDs will also up when you press the LEDs are some- [5] www.ftdichip.com/Resources/Utilities.htm
light up. If you release an LED, it will where in the middle of the grid, and [6] www.sourceforge.net/project/show-
go out. If you have selected ‘toggle’, the orientation is not the same as on files.php?group_id=235473&package_
the first press lights the LED, pressing the Monome. This is due to the Mon- id=285957
a second time will extinguish it. You ome software, which doesn’t com-
[7] www.midi.org/
can also use the mouse to click in the pletely follow the convention. Ardui-
‘lights’ grid to light up or extinguish nome Serial has a ‘Cable Orientation’ [8] www.opensoundcontrol.org/
the LEDs without pressing any keys. box that lets you choose between [9] www.cycling74.com
If all this is working, you Monome is ‘up’, ‘down’, ‘left’, and ‘right’ — see [10] www.Monome.org/data/app/base
operational (at last!) Figure 6. This box is used to orient
the Monome with respect to its USB
cable. So if you’re holding the Mon-
Just to finish off... ome in your hand with the USB cable
If your computer has a sound card, coming out downwards, you’ll need
the Monome_midi_64.mxb patch will to choose the ‘down’ option. It’s up to
Advertisement

227
10/2009 - elektor Personal Download for Petar Crnojevic | copyright Elektor 31
PROJECTS MICROCONTROLLERS

Microcontrollers fo
for
… Arduino for the enlightened
Clemens Valens (Elektor France Editorial)

Apparently Arduino is an Italian name – but when you search on the Internet, you mainly
find dozens of references relating to electronics and programming. What’s more, these
references are often in relation to art. Electronics and art – now there’s an interesting
subject that’s worth delving into! So just what exactly is Arduino?

At first sight, Arduino [1] is a small microcontroller board to certain functions, since this allows the Arduino develop-
with a USB port (Figure 1) that comes in several models. ment environment to be used for writing and compiling
There are even ‘daisy’-shaped boards (Lilypads) intended application before loading them onto the controller.
for wearable applications, i.e. to be incorporated into gar- The applications, called ‘sketches’, are written in a lan-
ments. The Arduino board is programmed in a language guage that closely resembles C. Hardly surprising – it is
very similar to C using Open Source tools available for C, but with some additional functions. All of the functions
Windows, Mac, and Linux. The hardware is also Open and presented as the language for Arduino form a Hardware
anyone can make their own Arduino – the circuit diagrams Abstraction Layer that lets you program the controller with-
and PCB photo masks are available free over the Internet. out needing to delve into the innards of the processor. The
Arduinos are used a great deal by artists who need elec- language has everything you need for most applications.
tronics in their creations. Broadly speaking, there are functions for digital and ana-
logue inputs/outputs, a few basic mathematical functions,
time management functions (delays) and a few function for
serial port communication – asynchronous (UART) and syn-
chronous (SPI).

The digital I/O functions let you manipulate the logic levels
of the pins, to read and write them. There is also a special
function that makes it possible to measure the duration of
a pulse. Using the analogue I/O functions, it is possible to
read voltages and generate PWM signals. Lots of appli-
cations don’t require anything more than this, and this is
exactly where Arduino’s strength lies. There’s no need to
go ferreting around in the registers and the controller data
sheet to make a PWM output or a counter work — the ‘dirty
Figure 1. work’ has already been done.
A Diecimila Arduino board.
The new Duemilanove If these functions aren’t enough, it’s perfectly possible to pro-
board is almost identical. gram on a lower level and, just as in standard C, you can
These boards are cheap also add libraries with their own functions. But do watch
and easy to find. out – if you go off into the darker depths of the Arduino
programming language, you risk losing compatibility with
the rest of Arduino community.
When you look at it a bit more closely, an Arduino is not
exactly a microcontroller board. In fact, an Arduino is quite The Arduino community? Already, Arduino is a microcon-
simply an 8-bit microcontroller from Atmel – an ATmega8 troller, as well as a development environment and a pro-
for the earliest Arduinos and now more likely to be an gramming language – now it’s a community too? Yes! In
ATmega168. This microcontroller is loaded with a ‘boot- fact, Arduino is more of a philosophy, the aim of which is
loader’ program that lets you load an application into the to popularize technology to make it accessible to artists.
controller via a serial port, without overwriting the boot- Arduino is a logical sequel to Processing [2] and Wiring [3]
loader. Since modern computers no longer have serial projects. Processing is a multimedia programming language
ports, a USB port is often used. All this becomes an Arduino and Wiring is a development environment for artistic elec-
when you decide to dedicate certain pins of the controller tronics But now we’re starting to get away from our original

228
32 Personal Download for Petar Crnojevic | copyright Elektor elektor - 2/2009
r Dummies …

point; refer to the box about the origins of Arduino if the name Freeduino for home-made
you want to find out more. Arduino boards. But after all, it’s only
a name, so let’s call ours Elektorino.
Elektorino
Simple, free programming is something we’re interested in. Implementation
What’s more, the electronics involved seem to be simple Before you can load a sketch into the Elektorino, you need
– so what could be more logical than to produce our own to load the bootloader. This is where things get more com-
Arduino-compatible system? Well, that’s just what we’re plicated, as there are two official Arduino bootloaders, the
going to do! only apparent difference between them being the way the
Our starting point is the basic Arduino Serial board. The sketch is run after loading. This is achieved by way of a
office computer I use all the time still has a serial port, but controller reset, which the Arduino environment can handle
for the unlucky owners of a computer that doesn’t, we’re if the board has been equipped for it, and if it has the right
going to use the USB-TTL cable [4]. In any event, we’re
going to be needing a TTL interface of some kind, as our
own Arduino will only have a TTL serial port.
J2 +5V +5V
1
Our processor is going to be an ATmega168, which we’ll 2 R9

be running at 16 MHz, to avoid getting caught out. For


10k

3
R7 C3
even though the controller is perfectly capable of operat- 4
1k
5
ing at up to 20 MHz, the standard bootloader assumes a 6
1k
R8
100n
S1

speed of 16 MHz. This can of course be modified if you


are prepared to go delving into the bootloader – but for the COM 21 7 20 RESET

moment we just want an Arduino board that works. J3 AREF VCC AVCC
J5
1 PIN0 2 1 RESET
To finish off our Arduino, all we need do is add an LED, a 2 PIN1 3
PD0 PC6
28 IN5 6
PD1 PC5
reset push-button, a few resistors and capacitors, and two 3 PIN2 4
PD2
IC1
PC4
27 IN4 5

connectors: one for the serial port and the other for pro- 4 PIN3 5
PD3 PC3
26 IN3 4
5 PIN4 6 25 IN2 3
gramming the bootloader. We need the latter to be able to 6 PIN5 11
PD4 PC2
24 IN1 2
PD5 PC1
program our Arduino for the first time, when the controller 7 PIN6 12
PD6 PC0
23 IN0 1

is still blank. Later, when the application is finished and the 8 PIN7 13
PD7 +5V
bootloader is no longer needed, this connector can be used 14
ATmega168
19 J1
PB0 PB5
for programming the controller directly from the application, J4
15
PB1 PB4
18 MISO 1 2

which saves memory. 1 PIN8


16
PB2 PB3
17 SCK 3 4
5 6
The LED has several functions. Given that the LED is present 2 PIN9
GND PB6 PB7 GND
on several types of Arduino, lots of sketches use it. So does 3
4
PIN10
PIN11
8 9 X1 10 22
MOSI
ISP

the bootloader, which flashes it at start-up. 5 PIN12


R10
Here’s the circuit diagram of our finished Arduino (Fig- 6 PIN13
Figure 2.
1k5

C1 16MHz C2
ure 2). Thanks to the simplicity of the circuit, we can build The circuit of the
22p 22p
it on prototyping board. D7 Elektorino. Not at
Unfortunately, we are not allowed to call our fine project all complicated. The
Arduino – only boards approved by the Arduino community connectors for the pins are
have the right to that name. This is why a second move- 080931 - 11
not necessary, they are
ment Freeduino [5] was created, which allows free use of mainly used as a reference.

229
2/2009 - elektor Personal Download for Petar Crnojevic | copyright Elektor 33
PROJECTS MICROCONTROLLERS

Hello world!
Once you have succeeded in loading the bootloader, it’s
time to see if Elektorino manages to communicate with the
Arduino environment and if it is possible to load a sketch.
So let’s install Arduino. I’ve only done it under Windows
XP, and that was extremely easy. All I had to do was down-
load a large zipped file and unzip it somewhere onto the
hard drive.

After running the Arduino environment (arduino.exe), you


find yourself with a window like the one shown in Fig-
ure 3. Go into the Tools menu, then Board, and select the
Arduino board being used. Of course, our one isn’t listed,
but an NG board using an ATmega168 will do.
You also have to select the serial port to be used for pro-
gramming the microcontroller. Go into the Tools menu, then
Serial port and select the correct port. If you want to use a
USB serial port, check first that the drivers are present.
The Arduino environment comes with a small sketch, Blink,
for checking that the board is working, and we can use this,
Figure 3. since we have fitted the LED. The procedure is simple:
The Arduino development
environment. - Load the sketch; it’s in File > Sketchbook > Examples >
Digital > Blink.
- Compile the sketch by clicking the Verify/Compile button;
bootloader. We haven’t made any provision for this, and so this only takes a few seconds and (usually) ends with a suc-
we need the basic bootloader for the so-called NG (New cess message.
Generation) boards.
- Load the sketch into Elektorino; first press the Reset button
But there is also another option: a third bootloader called briefly, then click Upload to set the program loading. If all
ADABOOT [6]. This bootloader, an improved version of the is well and if you are using ADABOOT, after a short delay
official bootloaders, handles the reset and run delays differ- you’ll see the LED start to flash randomly — this is normal,
ently. Initially, I worked for a bit with the NG bootloader, it shows the transfer is taking place. After around five sec-
before replacing it with ADABOOT. Both worked perfectly onds (depending on the size of the sketch), the program
well, but in the end I adopted ADABOOT, because it flashes is loaded and the controller is rebooted (the exact way in
the LED while the sketch is loading and because it is more which the program is run depends on the bootloader). If
convenient. the LED now flashes at a frequency of 1 Hz, everything has
See the box to find out how to load the bootloader into the gone alright. Elektorino is working! If nothing happens, try
controller. resetting Elektorino.

Loading the bootloader…


…is not as hard as all that, as long as you have all the information you need. To save you hours on the Net, we’ve summed it up
for you here in a few lines.
First of all, you need a programmer. There are several possibilities, for example, the one published in the 2008 double issue [7],
or another ‘SK200 compatible’ programmer, easy to build using the circuit available on the PonyProg website [8]. On the Arduino
website [1] yet another parallel port programmer is mentioned which is very simple and can be used directly from the Arduino en-
vironment. I tried it out, and managed to scramble one controller with it… so I went back to an SK200 one I already had.
Next, choose your bootloader. I recommend ADABOOT [6], but the NG version available on the Arduino website works perfectly
well too.
Loading the bootloader into the controller can be done, for example, using AVRDUDE [9], supplied with the Arduino environ-
ment. AVRDUDE is a typical UNIX tool – it’s basically a FreeBSD tool – with lots of incomprehensible options. Because it’s very
easy to make a mistake, here are the commands that work well (copy the bootloader into the directory that contains the AVRDUDE
executable):
avrdude -p m168 -c pony-stk200 -V -e -U lock:w:0x3F:m -U hfuse:w:0xDF:m -U lfuse:w:0xFF:m -U efuse:w:0x0:m
avrdude -p m168 -c pony-stk200 -V -D -U flash:w:ATmegaBOOT_168_ng.hex
avrdude -p m168 -c pony-stk200 -V -U lock:w:0x0F:m
If you use another programmer, replace pony-stk200 with the appropriate value. Also check the name of your bootloader.

There are three commands that, broadly speaking, unlock the memory, load the program, set the fuses, and finally lock the me-
mory. Refer to the AVRDUDE instructions if you want to know exactly what is going on (sensitive souls are advised to refrain!). Loc-
king the memory is used to avoid overwriting the bootloader accidentally when loading a sketch.
A good website about the AVR is called Lady Ada [10].

230
34 Personal Download for Petar Crnojevic | copyright Elektor elektor - 2/2009
A real application
It’s all very well to have an Arduino development environ-
ment that works wonderfully well, but without a real appli-
cation, it’s not very interesting. I already had ten motorized
slider pots, and it was high time to put them to good use.
Why not with Elektorino? Elektorino has analogue inputs
and PWM outputs — everything we need to drive a motor.
So I’m going to suggest a driver for motorized faders. Note
that this circuit can be used with any ATmega168-based
Arduino board.
The fader in question (Figure 4) consists of a slider pot,
a small motor, and an assembly of a few rollers, springs,
and a piece of cord that enables the motor to move the
slider in both directions. This assembly allows the motor to
freewheel when the slider is unable to move – at each end Figure 4.
of its travel, for example. Apart from the 10K B marked on A motorized fader of
the fader, I didn’t have any technical data on it, but a few unknown make.
experiments showed that the motor turned at a suitable
speed when powered from 12 V. In this case, its consump-
tion was around 200 mA.
The B marked on the fader might lead us to think it’s a log +12V
IC2
7805 +5V +5V
model (as is often the case), but after checking, my faders
turned out to be linear ones. C4 C5
IN0

As a motor driver, I chose a cleverly-modified double H 1μ 100n


R11
10k
25V
bridge with just two control lines and three states: anti- +12V

clockwise, clockwise, and braking – just what we need


(Figure 5). Usually, two controls allow four states, but in R2 R3 R6 R5
2k2

2k2

2k2

2k2
this circuit, states 00 and 11 are the same. A 5 V regulator T3 T4

has been slipped into the circuit so as to be able to power D2


2x
1N4001
D5

the whole controller assembly and motor from 12 V. The BD139 M1 BD139
transistor are all NPN types, and those forming the bridge D1
M
D4

must be capable of carrying 200 mA happily. In my proto- 1N4001 1N4001


T2 T5
type, I used BD139s. D3
2x
D6
Figure 5.
1N4001
The potentiometer is wired as a simple potential divider. By T1 BD139 BD139 T6 The modified double H
R1 R4
measuring the voltage on the wiper, we know where it is PIN9
5k6 5k6
PIN10
bridge and its three states.
(just so long as it’s a linear pot). BC547 BC547 The labels refer to the
The motor driver controls must be connected to digital out- 080931 - 12 pin designations, not the
puts capable of supplying a PWM signal. An Arduino terminals on the controller.
based around an ATmega168 has six, an ATmega8 only
three. The pot wiper itself can be connected to any of the
analogue inputs – in our case, in0.

The sketch
Now that we have connected a motor driver to Elektorino
(Figure 6), it’s time to deal with the software. You’ll see,
the final sketch will be amazingly simple, thanks to the
power of the Arduino.
A basic sketch consists of two functions: setup() and loop(),
which are called by the layer of a lower level. In setup,
called once at runtime, we put everything that relates to ini-
tializing the system – for example, the inputs/outputs and
the serial port speed.
99.9% of embedded programs probably spend their whole
lives in a loop. This is why in Arduino this loop is already
implemented in the form of the loop function. This loop Figure 6.
function is called periodically and may be regarded as The Elektorino prototype:
Arduino’s main. It’s important to realize that, even though the ATmega168 is on the
it looks like a special function, loop is just like any other left and the double H
function in C. So its local variables are reset each time it is bridge to drive the motor
called and variables that are required to keep their values on the right.
between different occasions loop is called must be declared
globally (or as static, for those familiar with C.)
serial port to drive our circuit, and for this it needs to be
The setup in our sketch doesn’t contain anything very much. initialized. Thanks to the simplification offered by Arduino,
The Arduino pins are inputs by default, so only the two all we have to do is enter the communication speed – in
outputs need to be initialized. We’re going to be using the our case, 9,600 baud.

231
2/2009 - elektor Personal Download for Petar Crnojevic | copyright Elektor 35
PROJECTS MICROCONTROLLERS

Processing, Wiring, and Arduino


Processing [2] is a language and an Open Source programming environment for programming images, animations, and inter-
actions. The project, an initiative from Ben Fry and Casey Reas, is based on ideas developed by the Aesthetics and Computation
Group of the MIT Media Lab. Processing was created in order to teach the fundamentals of programming in a visual context and
to serve as a sketchbook or professional software production tool. Processing runs under GNU/Linux, Mac OS X, and Windows.
Several books have already been written on Processing.
Just like Arduino, Wiring [3] is a programming environment with microcontroller board for exploring electronic arts, teaching pro-
gramming, and quick prototyping. Wiring, programmed in Processing, is an initiative by Hernando Barragán and was designed at
the Interaction Design Institute Ivrea (IDII) in Italy.
Arduino [1] is a fast, Open Source electronic prototyping platform. Arduino is aimed at artists, stylists, enthusiasts, and anyo-
ne interested in creating objects or interactive environments. Created by Massimo Banzi, Gianluca Martino, David Cuartielles,
and David Mellis, Arduino uses a programming language based on ‘Processing’. Arduino may be regarded as a simplification of
‘Wiring’.

Moving the pot wiper is done in loop. The principle is very may even begin to oscillate.
simple: if the voltage measured on the input pin is different To avoid these problems, we have used a Proportional Dif-
from the voltage required, the slider must be moved in the ferential (P-D) regulator. In this type of regulator, the system
direction which will reduce this difference. In real life, it’s reaches its final value without overshoot by continuously
a bit more complicated than that. To start with, there’s the adjusting the correction signal according to the difference
remaining to be corrected. So at the start of an adjustment,
when the error is greatest, a strong correction signal is
applied. Then, once the difference starts to reduce, the cor-
The STK200 compatible programmer used by the author. There are also simpler
rection signal reduces too and the system slows down.
programmers – it’s a matter of personal preference.
The correction signal consists of two parts: a signal propor-
D8
tional to the error (P) and a signal proportional to the error
20 C6
1N4148 reduction (D). With a properly adjusted system of this sort,
IC3 R12
the slider can be moved quickly without overshooting the
100k

100n
target value.
10

In the sketch (Listing 1) we can see the P-D regulator in the


MISO
loop function. First, we measure the voltage at the wiper.
LPT
IC3
The target value is subtracted from the measured value to
1

14
1 19
EN1
EN2
obtain the error to be corrected. From this value, we calcu-
15
2
3
late the two components P and D of the correction signal.
16
17
4 2 1D1 18 MOSI J7 The P component is the error multiplied by the constant Kp;
18
5
6
4
6
16
14
LED
SCK
1
3
2
4
the D component is obtained by multiplying the difference
19
20
7 8 12 5 6 between the current value and the previous error by the con-
8 11 9
21
9 13
1D2
7 RESET ISP stant Kd. The values for these constants were determined by
22
23
10
11
15
17
5
3
experimentation, and you can modify them to see how the
24
25
12 affect the adjustment. It’s highly instructive.
74HCT244
13
080931 - 13
The two components P and D are combined and the result
is adapted to the range of usable values. The pot slider
doesn’t move for values below 50, and the maximum value
for the PWM signal is 255.
Then we look to see if the error is small enough for us to be
problem of direction, but more significant still is the problem able to stop the motor. This comparison has to be performed
of inertia. Once the slider is moving, it takes a little time for for both slider directions. We leave a small margin for error,
it to come to a complete halt. So it’s easy to overshoot the since perfection is perhaps a little over-ambitious.
required position if braking occurs too late. In the event of When the error is small enough, we prevent further correc-
an overshoot, the slider has to be brought back, with the tions so as to free up the slider; we make the assumption
same risk of overshooting again, and so on. The system that the system is never going to overshoot the target value.

AVR ISP via USB


If you use the FT232R chip as a USB interface and if you have access to all its pins, it is possible to use this chip to load the boot-
loader into the microcontroller without even needing a special ISP programmer! The FT232R chip has a bus called a CBUS with
a bit function that lets you manipulate the associated pins individually. A certain Mr Suz from Japan has written a small piece of
software that exploits this possibility and which can be downloaded free. Its avrdude-serjtag tool only works under Windows and
its website is unfortunately in Japanese (suz-avr.sblo.jp/article/4438871.html). However, on his site one of his compatriots kindly
explains in detail in English how to program an Arduino using this tool. See reference [11] for details.

232
36 Personal Download for Petar Crnojevic | copyright Elektor elektor - 2/2009
In this way, it’s possible to move the slider manually, with-
out the system’s trying to move it back into place. (Who’s Listing 1 – Easy-peasy!
the strongest?)
Once the slider has been released, the system starts to out- void loop()
put the slider position periodically (10 Hz) via the serial {
port. The serial port input is also scanned and as soon as int error;
four characters have been received, they are transferred as int val;
a target value for the slider and the PD regulator is re-acti- int spd;
float spd_p, spd_d;
vated to move it to its new position. No format checking
is performed for the value received, the system requires an
// read wiper voltage.
ASCII four-digit value between 0000 and 1023. To mini- val = analogRead(slider);
mize errors, the target value obtained is limited between 3
and 1020, which minimizes problems of continuous activa- // Calculate error.
tion at the ends of the travel. error = val - target;
The serial port is not used while the motor is operating, as
this might produce interference, resulting in inaccurate posi- // Calculate proportional component P.
tions or even oscillation. I’ve not taken the trouble to find // Two directions – so use absolute value.
out why: I’ll leave that for you to do! spd_p = abs(error)*Kp;
(080931-I)
// Calculate differential component D.
spd_d = (last_error-error)*Kd;
last_error = error;

// Now mix P and D.


spd = int(spd_p+spd_d);

// Do not exceed limits.


spd = constrain(spd,0,255);
// Compensate friction.
if (spd<50) spd += 50;

if (error<-1 && stop==0)


{
// To maximum value (“left”).
digitalWrite(motor2,LOW);
analogWrite(motor1,spd);
}
else if (error>1 && stop==0)
{
// To minimum value (“right”).
digitalWrite(motor1,LOW);
analogWrite(motor2,spd);
}
else
{
// Shut down motor
digitalWrite(motor1,LOW);
digitalWrite(motor2,LOW);
stop = 1;
References and Resources
// Transmit cursor position.
[1] http://arduino.cc
Serial.println(val);
[2] www.processing.org delay(100);
[3] http://wiring.org.co
[4] www.elektor.fr/usb-ttl // 4 characters form a new target value.
[5] www.freeduino.org if (Serial.available()>=4)
[6] http://nearspacevermont.org/TheShoppe/freeduino/ADA- {
BOOT.shtml target = Serial.read()
- ‘0’; // Thousand.
[7] SimpleProg – ISP for AVR, Elektor, July/August 2008
target = Serial.read() - ‘0’
[8] www.lancos.com/prog.html + target*10; // Hundred.
[9] www.bsdhome.com/avrdude target = Serial.read() -
[10] www.ladyada.net/learn/avr/index.html ‘0’ + target*10; // Ten.
[11] www.geocities. target = Serial.read() -
jp/arduino_diecimila/bootloader/index_en.html ‘0’ + target*10; // One.
Getting Started with Arduino, Banzi, Massimo, O’Reilly, 2008 constrain(target,1,1022);
// Start motor
Making Things Talk, Igoe, Tom, O’Reilly, 2007
stop = 0;
The Duemilanove Arduino board is available from several sour-
}
ces including FunGizmos (US), LittleBird (Australia), SKPang (UK),
}
Tinker (Italy), Make Magazine (Makershed.com).
}

233
2/2009 - elektor Personal Download for Petar Crnojevic | copyright Elektor 37

You might also like