For this project I used one of my ATtiny84a development boards (see my other projects). Instead of having a standard distance measuring demo I decided to make it more fun. By placing the components in a creative manner I was able to create a little sculpture the shape of a person. I displayed it at my booth during one of the STEAM festivals, and kids love to hold and play with it.
The OLED display shows the distance in centimeters and the voltage supplied by the battery. The voltage is measured internally by the ATtiny84a.
Components
1×
ATtiny84 development board
See my other projects for more information
Upload the sketch using the Arduino UNO as SPI programmer. Use 1mm diameter pogo pins to connect to the board:
Make sure to burn the bootloader with the clock set to 8MHz (internal). Compile the following sketch with LTO enabled (sketch will be too large when LTO is not used):
#include<Arduino.h>#include<U8x8lib.h>#include<NewPing.h>#ifdef U8X8_HAVE_HW_SPI#include<SPI.h>#endif//U8X8_SSD1306_128X64_NONAME_4W_SW_SPI u8x8(/* clock=*/ 5, /* data=*/ 4, /* cs=*/ 1, /* dc=*/ 2, /* reset=*/ 3);U8X8_SH1106_128X64_NONAME_4W_SW_SPI u8x8(/* clock=*/5, /* data=*/4, /* cs=*/1, /* dc=*/2, /* reset=*/3);
#define TRIGGER_PIN 7 // Arduino pin tied to trigger pin on the ultrasonic sensor.#define ECHO_PIN 8 // Arduino pin tied to echo pin on the ultrasonic sensor.#define MAX_DISTANCE 200 // Maximum distance we want to ping for (in centimeters). Maximum sensor distance is rated at 400-500cm.NewPing sonar(TRIGGER_PIN, ECHO_PIN, MAX_DISTANCE); // NewPing setup of pins and maximum distance.char tmp_string[5];
long voltage;
voidsetup(void){
pinMode(6, OUTPUT);
pinMode(9, OUTPUT);
digitalWrite(6, HIGH);
digitalWrite(9, LOW);
u8x8.begin();
u8x8.setPowerSave(0);
}
voidloop(void){
//read and convert the voltage to a decimal
voltage = readVcc();
double decimalVoltage = doubleMap(double(voltage),0,6000,0,6);
//u8x8.setFont(u8x8_font_chroma48medium8_r);unsignedint uS = sonar.ping(); // Send ping, get ping time in microseconds (uS).
u8x8.setFont(u8x8_font_amstrad_cpc_extended_r);
//u8x8.setFont(u8x8_font_profont29_2x3_r);
u8x8.setCursor(10, 7);
u8x8.print(decimalVoltage);
u8x8.drawString(14, 7, "V");
if((uS / US_ROUNDTRIP_CM) == 0){
// do nothing, do not upate display
}
elseif((uS / US_ROUNDTRIP_CM) < 10) {
u8x8.draw2x2String(1, 3, " ");
u8x8.draw2x2String(5, 3, itoa(uS / US_ROUNDTRIP_CM, tmp_string, 10));
}
elseif((uS / US_ROUNDTRIP_CM) < 100) {
u8x8.draw2x2String(1, 3, " ");
//u8x8.print(uS / US_ROUNDTRIP_CM);
u8x8.draw2x2String(3, 3, itoa(uS / US_ROUNDTRIP_CM, tmp_string, 10));
}
else {
u8x8.draw2x2String(1, 3, itoa(uS / US_ROUNDTRIP_CM, tmp_string, 10));
}
u8x8.drawString(8, 3, "centi-");
u8x8.drawString(8, 4, "meters");
u8x8.drawString(2, 1, "Distance:");
delay(100);
}
doubledoubleMap(double x, double in_min, double in_max, double out_min, double out_max){
return (x - in_min) * (out_max - out_min) / (in_max - in_min) + out_min;
}
longreadVcc(){
// Read 1.1V reference against AVcc// set the reference to Vcc and the measurement to the internal 1.1V reference#if defined(__AVR_ATmega32U4__) || defined(__AVR_ATmega1280__) || defined(__AVR_ATmega2560__)
ADMUX = _BV(REFS0) | _BV(MUX4) | _BV(MUX3) | _BV(MUX2) | _BV(MUX1);
#elif defined (__AVR_ATtiny24__) || defined(__AVR_ATtiny44__) || defined(__AVR_ATtiny84__)
ADMUX = _BV(MUX5) | _BV(MUX0);
#elif defined (__AVR_ATtiny25__) || defined(__AVR_ATtiny45__) || defined(__AVR_ATtiny85__)
ADMUX = _BV(MUX3) | _BV(MUX2);
#elif defined (__AVR_ATtiny87__) || defined(__AVR_ATtiny167__)
ADMUX = _BV(MUX3) | _BV(MUX2);
#else
ADMUX = _BV(REFS0) | _BV(MUX3) | _BV(MUX2) | _BV(MUX1);
#endif
delay(20); // Wait for Vref to settle
ADCSRA |= _BV(ADSC); // Start conversionwhile (bit_is_set(ADCSRA,ADSC)); // measuringuint8_t low = ADCL; // must read ADCL first - it then locks ADCH uint8_t high = ADCH; // unlocks bothlong result = (high<<8) | low;
result = 1125300L / result; // Calculate Vcc (in mV); 1125300 = 1.1*1023*1000return result; // Vcc in millivolts
}
Turning this into a little person is a great touch! What is a proof-of-concept on the beadboard comes alive with some creative arms and legs ;-)