/*****************************************************************************************
This project was developed and created by Steve Barth (2021).
This is the main controller for the dosimetric access gate.
The system has an esp32 core that displays instructions on the 320x240
pixel color tft display, with a 5-second timeout, and a corresponding light and
sound signal, while the geiger counters connected here perform the measurements.
version 1.35
******************************************************************************************/
/********* DECLARATIONS & CONSTANS & PIN CONNECTING *************/
/*
A program (Flash): (18,8%) 246498 bájt-ot használ maximum 1310720 bájt-ból.
A globális változók (RAM): (4,2%) 13744 bájt-ot használnak a dinamikus memóriából, 327680 bájt.
*/
#include <Adafruit_GFX.h> // only for VS Code
#include <Adafruit_ILI9341.h>
#include <Arduino.h>
#include <SPI.h>
#include <Tone32.h>
#include <Wire.h>
#include <pitches.h>
// fonts from GFX
#include <Fonts/FreeSans12pt7b.h>
#include <Fonts/FreeSerifBold24pt7b.h> // add a custom fonts
#include <Fonts/FreeSerifBoldItalic24pt7b.h>
// connections
#define BUZZER_CHANNEL 0 // use PWM channel
#define ONBOARD_LED 2 // onboard (BLUE)led pin
#define IR_start 12 // connect IR sensor output
#define BUZZER_PIN 13 // buzzer connect GPIO
#define TFT_LED 22 // tft display backlite pin
#define Light_Red 25 // connect red led
#define Light_Green 26 // connect green led
// Connections for the TFT display
#define _cs 17 // goes to TFT CS
#define _dc 16 // goes to TFT DC
#define _mosi 23 // goes to TFT MOSI
#define _sclk 18 // goes to TFT SCK/CLK
#define _rst 5 // goes to TFT RESET
// #define _miso // Not connected
// 3.3V // Goes to TFT LED
// 5v // Goes to TFT Vcc
// Gnd // Goes to TFT Gnd
Adafruit_ILI9341 tft = Adafruit_ILI9341(_cs, _dc, _rst); // Use hardware SPI
/* LCD color def. RGB 5:6:5 bit Converter http://greekgeeks.net/#maker-tools_convertColor */
#define WHITE 0xFFFF // or tft.color565( 255, 255, 255)
#define BLACK 0x0000 // or tft.color565( 0, 0, 0)
#define GREEN 0x07E0
#define RED 0xF800
#define CYAN 0x07F2
#define YELLOW 0xFFE0
int timerMode = 0; // data type for timer mode
long startTime; // data type for starting time
bool Error; // data type for error state
/**************** SETUP ***************/
void setup()
{
// blue led program start indicating
pinMode(ONBOARD_LED, OUTPUT); // Program start indication
digitalWrite(ONBOARD_LED, LOW); // turn the Blue LED off (LOW is the voltage level)
digitalWrite(ONBOARD_LED, HIGH); // turn the Blue LED on (HIGH is the voltage level)
delay(100); // wait for a milisecond
digitalWrite(ONBOARD_LED, LOW); // turn the Blue LED off (LOW is the voltage level)
delay(250); // wait for a milisecond
digitalWrite(ONBOARD_LED, HIGH); // turn the Blue LED on (HIGH is the voltage level)
delay(100); // wait for a milisecond
digitalWrite(ONBOARD_LED, LOW); // turn the Blue LED off (LOW is the voltage level)
// tft display start
pinMode(TFT_LED, OUTPUT); // LCD backlite
digitalWrite(TFT_LED, LOW); // turn the LED off (LOW is the voltage level)
Serial.begin(115200); // serial communication speed settings
tft.begin(); // tft display initialising
tft.fillScreen(BLACK); // background color black
tft.setRotation(3); // LCD view direction ( 0 & 2 Portrait. 1 & 3 landscape)
digitalWrite(TFT_LED, HIGH); // turn the backlite on (HIGH is the voltage level)
// software version display
tft.setFont(&FreeSans12pt7b); // font type
tft.setCursor(15, 112); // set cursor
tft.setTextSize(1); // font size
tft.setTextColor(WHITE); // font color (white)
tft.print("created by Steve Barth 2021"); // subtitle
delay(800); // pause
tft.setCursor(92, 178); // set cursor
tft.print("version 1.35"); // subtitle
delay(1600); // pause
tft.fillScreen(BLACK); // background color black
// state light & measure proced start
pinMode(IR_start, INPUT_PULLUP); // setting pinmode with pullup resistor
pinMode(Light_Green, OUTPUT); // setting pinmode output for green led
digitalWrite(Light_Green, LOW); // green led off
pinMode(Light_Red, OUTPUT); // setting pinmode output for red led
digitalWrite(Light_Red, LOW); // red led off
// display white frames
tft.drawRoundRect(0, 0, 320, 240, 1, WHITE); // white frame 1
tft.drawRoundRect(0, 0, 320, 240, 2, WHITE); // white frame 1
tft.drawRoundRect(1, 1, 318, 238, 2, WHITE); // white frame 2
tft.drawRoundRect(1, 1, 318, 238, 3, WHITE); // white frame 2
tft.drawRoundRect(2, 2, 316, 236, 3, WHITE); // white frame 3
tft.drawRoundRect(2, 2, 316, 236, 4, WHITE); // white frame 3
tft.drawRoundRect(3, 3, 314, 234, 4, WHITE); // white frame 4
tft.drawRoundRect(3, 3, 314, 234, 5, WHITE); // white frame 4
}
/**************** LOOP ***************/
void loop()
{
Error = 0; // errormode status 0
// standby status
if (timerMode == 0) // if timermode "0" status
{
tft.setFont(&FreeSerifBoldItalic24pt7b);
tft.setCursor(66, 100); // cursor moving
tft.setTextSize(1); // set font size
tft.setTextColor(CYAN); // font color
tft.print("PLEASE"); // subtitle
tft.setCursor(96, 160); // cursor moving
delay(150);
tft.setTextSize(1); // set font size
tft.setTextColor(CYAN); // font color
tft.print("NEXT"); // subtitle
}
// when a start signal is received
if (digitalRead(IR_start) == LOW) // if IR sensor add start impuls (high-low-high)
{
delay(40); // delay for no bounce
startTime = millis(); // starttime settings
tft.fillRect(4, 4, 312, 210, BLACK); // 160 clear the time value field on the digit with background color: (x,y,width,height,color)
tft.drawRoundRect(10, 6, 300, 66, 15, WHITE); // white long frame 1
tft.drawRoundRect(11, 7, 298, 64, 13, WHITE); // white long frame 2
tft.fillRoundRect(13, 9, 294, 60, 12, RED); // fill white frame
tft.setFont(&FreeSerifBold24pt7b); // font type
tft.setCursor(82, 56); // cursor moving
tft.setTextSize(1); // font size
tft.setTextColor(WHITE); // font color (white)
tft.print("S T O P"); // subtitle
timerMode++; // I increase the timermode status
}
// the start of the measurment
if (timerMode == 1) // if timermode status 1
{
tft.setFont(&FreeSans12pt7b);
tft.setTextSize(1); // setting text size
tft.setTextColor(WHITE); // text color
tft.setCursor(50, 110); // cursor position
tft.print("(Measurment: 5 sec.)"); // text on the display
tft.setFont(&FreeSerifBold24pt7b); // set font
tft.setTextSize(1); // set font size
tft.fillRect(70, 136, 90, 40, BLACK); // clear the time value field on the digit with background color: (x,y,width,height,color)
tft.setTextColor(WHITE); // text color (only deault text-> (black background, white foreground))
tft.setCursor(75, 170); // cursor position
tft.print((millis() - startTime) / 1000.0); // print start time
delay(40);
tft.setCursor(180, 170); // cursor position
tft.print("sec."); // text on the display
if ((millis() - startTime) >= 5020.0) // time max.: 5 sec
{
delay(1);
timerMode++; // I increase the timermode status
}
}
// not enough time for measurement
else if ((20 <= (millis() - startTime)) && ((millis() - startTime) <= 4980) && timerMode >= 1) // if time between 0,02s-4,98s
{
digitalWrite(Light_Red, HIGH); // red led on
Error = 1; // errormode status 1
}
// when the measurement time has elapsed
if (timerMode > 1) // if timermode status bigger 1
{
if (Error == 0) // if errormode status 0
{
tft.fillRect(4, 75, 312, 160, BLACK); // clear the time value field on the digit with background color: (x,y,width,height,color)
tft.drawRoundRect(10, 6, 300, 66, 15, WHITE); // white long frame 1
tft.drawRoundRect(11, 7, 298, 64, 13, WHITE); // white long frame 2
tft.setFont(&FreeSerifBold24pt7b);
tft.fillRoundRect(13, 9, 294, 60, 12, GREEN); // fill white frame 2 background
tft.setCursor(35, 56); // cursor moving
tft.setTextSize(1); // font size
tft.setTextColor(BLACK); // font color
tft.print("You can GO"); // subtitle "YOU CAN GO"
tft.setCursor(65, 130); // cursor moving
tft.setFont(&FreeSerifBold24pt7b); // font type
tft.setTextSize(1); // font size
tft.setTextColor(GREEN); // font color
tft.print("All right!"); // subtitle
digitalWrite(Light_Green, HIGH);
tone(13, NOTE_A5, 100, 0); // sound on (BUZZER_PIN, 800Hz, 80ms, BUZZER_CHANNEL)A5
tone(13, NOTE_CS6, 100, 0); // sound on (BUZZER_PIN, 1kHz, 80ms, BUZZER_CHANNEL)C6
tone(13, NOTE_FS6, 180, 0); // sound on (BUZZER_PIN, 1.2kHz, 100ms, BUZZER_CHANNEL)E6
noTone(13, 0); // sound off (BUZZER_PIN, BUZZER_CHANNEL)
delay(200);
}
// if you do not wait for the measurement time
if (Error == 1) // if errormode status 1
{
tft.setFont(&FreeSerifBold24pt7b);
tft.setTextSize(1); // setting text size
tft.setTextColor(YELLOW); // text color
tft.setCursor(75, 115); // cursor position
tft.print("FAULT!"); // text on the display red
tft.setCursor(66, 155); // cursor position
tft.print("PLEASE"); // text on the display
tft.setCursor(75, 195); // cursor position
tft.print("AGAIN!"); // text on the display
tone(13, NOTE_C3, 700, 0); // Plays 131Hz tone for 0.7 seconds
noTone(13, 0); // sound off
}
delay(750); // 0,75 seconds delay before clear screen
digitalWrite(Light_Red, LOW); // red led off
digitalWrite(Light_Green, LOW); // green led off
delay(100); // pause
tft.fillRect(4, 4, 313, 210, BLACK); // clear the time value field on the digit with background color: (x,y,width,height,color)
delay(150);
timerMode = 0; // set timermode status 0
}
}
/***************** END of LOOP **********************/