The idea is a top/ chimney pipe/ tall hat which has the mind of it’s own (akin to the Sorting Hat in Harry Potter). This hat is very conscious about social distancing (rightfully) and if you go too close it will shout at you (not quite rightfully). When the hat is shouting it’s mind blows up in anticipation, this will be visualized with a star show housed within the hat.
This post will be about the electronics and the Arduino code of such a conscious hat.
The idea is to use ultrasonic sensors to measure the distance between our woke hat and people. This proto-system is using two sensors, so you can get the logic of the Arduino code and expand it should you wish to use more sensors. Explanation will be included later on.
When someone comes within the uncomfortable range of 1m (or any preset distance, but less than 7 meters), the hat will start to shout towards you. This is achieved with a MP3 player which will start to play the pre-recorded message/ music if someone within 1 meter of the hat and stops once the person is further away.

Bill of Materials:
– Arduino Uno
– 100K resistor
– DFMini MP3 Player module
– Two Ultrasonic Sensor modules (HC-SR04)
– A selection of jump wires
– Breadboard
This is the circuit diagram and a photo of my project breadboarded up. The wiring is fairly simple. You will use 6 pins on the Arduino. 2 will be used for the MP3 player and 2 for each sensor respectively. The 100K resistor will be inserted into the signal path of the virtual serial port, so the signal is clearer.
The system can be power from the Arduino’s 5V power supply. All three modules need power.

All the libraries used are available online, some code is from references and some is my own work.

The code is below with extensive commenting to explain each line. The code was written by me using references and software libraries.
*
* Creator
************************************************************************ * Andras Peter
* <https://apcreative.space/> *
* **********************************************************************
*
* references :
*
* DFplayer test example
Tutorial: https://electronoobs.com/eng_arduino_tut122.php
YouTube channel: http://www.youtube.com/c/ELECTRONOOBS
************************************************************************
* MP3 player using Arduino and DFPlayer mini
https://www.electronics-lab.com/project/mp3-player-using-arduino-dfplayer-mini/
Nick Koumaris
************************************************************************
*DFPlayer - A Mini MP3 Player For Arduino
<https://www.dfrobot.com/index.php?route=product/product&product_id=1121>
************************************************************************
*This example shows the basic function of library for DFPlayer.
Created 2016-12-07
By [Angelo qiao](Angelo.qiao@dfrobot.com)
GNU Lesser General Public License.
See <http://www.gnu.org/licenses/> for details.
https://wiki.dfrobot.com/DFPlayer_Mini_SKU_DFR0299
************************************************************************
* Programming Arduino - Simon Monks / McGrawHill Education
************************************************************************
*/
// calling pre written software libraries - use of simplified functions
// MP3 player by DFRobot – from wiki.dfrobot
#include <DFRobotDFPlayerMini.h>
// for using the Ultrasonic sensor
#include <NewPing.h>
// for communicating with the DFPlayer. creates two virtual serial ports for TX/RX. as standard serial port is used by serial monitor for debugging
#include <SoftwareSerial.h>
// defines pin numbers and locations (on Arduino) as constant variables for communicating with the two ultrasonic sensors (_0, _1)
const int trigPin_0 = 9;
const int echoPin_0 = 10;
const int trigPin_1 = 5;
const int echoPin_1 = 6;
// Use pin 2 and 3 to communicate with DFPlayer Mini, set up as serial ports with softwareSerial
static const uint8_t PIN_MP3_TX = 2; // settings pin, connects to module's RX(!)
static const uint8_t PIN_MP3_RX = 3; // setting pin, connects to module's TX(!)
SoftwareSerial softwareSerial(PIN_MP3_RX, PIN_MP3_TX); // sonnceting pins to softwareSerial
// Create the Player object - easier to refer to
DFRobotDFPlayerMini player;
// defines variables
long duration_0; // for sensor_0, used for measuring time for echo pin (0) to receive trigger pings
int distance_0; // used for measured distance
long duration_1; // for sensor_1
int distance_1; // for sensor_1
bool isPlaying; // Boolean variable for controlling/ indicating play/ stop
// this block runs once
void setup()
{
pinMode(trigPin_0, OUTPUT); // sets the trigPin_0 as an Output
pinMode(echoPin_0, INPUT); // sets the echoPin_0 as an Input
pinMode(trigPin_1, OUTPUT); // sets the trigPin_1 as an Output
pinMode(echoPin_1, INPUT); // sets the echoPin_1 as an Input
Serial.begin(9600); // starts the serial communication via physical
softwareSerial.begin(9600); // starts virtual serial port for DFPlayer Mini
if (player.begin(softwareSerial)) // Start communication with DFPlayer Mini
{
Serial.println("OK");
}
else if (!player.begin(softwareSerial)) // if serial communication failes
{
Serial.println(F("Unable to begin:")); // print msg
Serial.println(F("1.Please recheck the connection!")); // print msg
Serial.println(F("2.Please insert the SD card!")); // print msg
while(true); // do that until no change
}
Serial.println(F("DFPlayer Mini online.")); // print status msg
// Set volume (0 to 30).
player.volume(30);
player.stop(); // reset MP3 player
isPlaying = false; // switch isPlaying bool int to false
player.EQ(DFPLAYER_EQ_BASS); // set EQ to Davie504
}
// setting up a scanning procedure function for sensor_0, which can be called up on, named as "scan_0"
void scan_0 ()
{
// Clears the trigPin
digitalWrite(trigPin_0, LOW);
delayMicroseconds(2);
// Sets the trigPin on HIGH state for 10 micro seconds
digitalWrite(trigPin_0, HIGH);
delayMicroseconds(10);
digitalWrite(trigPin_0, LOW);
// Reads the echoPin, returns the sound wave travel time in microseconds
duration_0 = pulseIn(echoPin_0, HIGH);
// Calculating the distance
distance_0 = duration_0*0.034/2;
// Prints the distance on the Serial Monitor
Serial.print("Distance_0: ");
Serial.println(distance_0);
}
// setting up a scanning procedure function for sensor_0, which can be called up on, named as "scan_1"
void scan_1 ()
{
// Clears the trigPin
digitalWrite(trigPin_1, LOW);
delayMicroseconds(2);
// Sets the trigPin on HIGH state for 10 micro seconds
digitalWrite(trigPin_1, HIGH);
delayMicroseconds(10);
digitalWrite(trigPin_1, LOW);
// Reads the echoPin, returns the sound wave travel time in microseconds
duration_1 = pulseIn(echoPin_1, HIGH);
// Calculating the distance
distance_1 = duration_1*0.034/2;
// Prints the distance on the Serial Monitor
Serial.print("Distance_1: ");
Serial.println(distance_1);
}
// this block will repeat infinitely
void loop ()
{
scan_0(); // runs ultrasonic sensor_0 scanning procedure
delay(100); // delay of 100ms
if ((distance_0 < 50) && (isPlaying == false)) // checks for two conditions at the same time to execute 1. distance is less than 50cm 2. player is not playing
{
player.play(1); // start play
isPlaying = true; // switch isPlaying indicator to true
delay(100); // delay for 100 microseconds
}
scan_1(); // runs ultrasonic sensor_1 scanning procedure
delay(100); // delay of 100ms
if ((distance_1 < 50) && (isPlaying == false)) // checks for two conditions at the same time to execute 1. distance is less than 50cm 2. player is not playing
{
player.play(1); // start play
isPlaying = true; // switch isPlaying indicator to true
delay(100); // delay for 100 microseconds
}
if ((distance_1 > 50) && (distance_0 > 50) && (isPlaying == true)) // checks for three conditions at the same time to execute 1. distance is more than 50cm on sensor_0 2. distance is more than 50cm on sensor_0 3. player is playing
{
player.stop(); // stops play
isPlaying = false; // swithces isPlaying Boolean indicator to false
delay(100); // delay for 100 microseconds
}
}
And there you have it. The fully build project will be posted in due time (this year at some point)