#include "U8g2lib.h"
#include "Adafruit_SSD1306.h"
U8G2_SSD1306_128X64_NONAME_1_HW_I2C u8g2(U8G2_R1);
//bitmaps
//side lines (30x29px)
const unsigned char epd_bitmap_scroll [] PROGMEM = {
0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x10, 0x02, 0x00, 0x00, 0x10,
0x03, 0x00, 0x00, 0x30, 0x03, 0x00, 0x00, 0x30, 0x03, 0x00, 0x00, 0x30,
0x03, 0x00, 0x00, 0x30, 0x03, 0x00, 0x00, 0x30, 0x03, 0x00, 0x00, 0x30,
0x03, 0x00, 0x00, 0x30, 0x03, 0x00, 0x00, 0x30, 0x03, 0x00, 0x00, 0x30,
0x03, 0x00, 0x00, 0x30, 0x03, 0x00, 0x00, 0x30, 0x03, 0x00, 0x00, 0x30,
0x03, 0x00, 0x00, 0x30, 0x03, 0x00, 0x00, 0x30, 0x03, 0x00, 0x00, 0x30,
0x03, 0x00, 0x00, 0x30, 0x03, 0x00, 0x00, 0x30, 0x03, 0x00, 0x00, 0x30,
0x03, 0x00, 0x00, 0x30, 0x03, 0x00, 0x00, 0x30, 0x03, 0x00, 0x00, 0x30,
0x03, 0x00, 0x00, 0x30, 0x03, 0x00, 0x00, 0x30, 0x01, 0x00, 0x00, 0x20,
0x01, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, };
//main bar (24x7px)
const unsigned char epd_bitmap_mainBar [] PROGMEM = {
0x00, 0x00, 0x00, 0xFC, 0xFF, 0x3F, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
0xFE, 0xFF, 0x7F, 0xFC, 0xFF, 0x3F, 0x00, 0x00, 0x00, };
// bitmap array
const unsigned char* bitmap_elements[2] = {
epd_bitmap_scroll,
epd_bitmap_mainBar
};
//time marks
unsigned long previousTextMillis = 0;
const long textInterval = 550;
int scrollYpos = 128;
bool text_blink = false;
int textBlink = 0;
int boxBlink = 1;
//pins
#define trigger A0
#define gas_valve 2
#define flash_red 3
#define flash_green 5
#define flash_blue 6
#define selector 7
#define reload_button 8
#define UP 0
#define DOWN 1
//backlight / pins
const byte pwmR = 9;
const byte pwmG = 10;
const byte pwmB = 11;
const int minPWM = 60;
const int maxPWM = 255;
const int minBlinkPWM = 10;
const int maxBlinkPWM = 255;
byte fadeDirection = UP;
int fadeValue = 0;
int blinkValue = 0;
byte fadeIncrement = 10; //smoothness
unsigned long previousFadeMillis;
unsigned long previousBlinkMillis;
bool buttonPressed = false;
bool fadeBypass = false;
int fadeInterval = 60;
int blinkInterval = 10;
//trigger/reload
int trigger_pulled = LOW;
int reload_pressed = LOW;
bool reloadFinished = true;
unsigned long reloadStart = 0;
unsigned long previousMillis1 = 0;
bool semi_fired = false;
int shots_fired = 0;
// variables
int mag_size = 20;
int triggerThreshold = 50;
float firerate = 300;
float flash_delay = 40;
float yellow_flash_on = 20;
float flash_on = 80;
float valve_on = 15;
float reloadDelay = 1500;
unsigned long previousMillis2;
void setup() {
u8g2.begin();
Serial.begin(115200);
pinMode (trigger, INPUT);
pinMode (selector, INPUT);
pinMode (reload_button, INPUT);
pinMode (gas_valve, OUTPUT);
pinMode (flash_red, OUTPUT);
pinMode (flash_green, OUTPUT);
pinMode (flash_blue, OUTPUT);
analogWrite(pwmR, blinkValue);
analogWrite(pwmG, fadeValue);
analogWrite(pwmB, fadeValue);
}
void loop() {
unsigned long currentMillis = millis();
//trigger settings
int trigg_value = analogRead (trigger);
trigg_value = map (trigg_value, 0, 1023, 0, 255);
// reload settings
if (digitalRead (reload_button) == HIGH && (reload_pressed == LOW)) {
Serial.println ("reloading");
reloadFinished = false;
reloadStart = currentMillis;
shots_fired = 0;
reload_pressed = HIGH;
}
if (currentMillis - reloadStart >= reloadDelay) {
reloadFinished = true;
}
if (digitalRead (reload_button) == LOW && (reload_pressed == HIGH)) {
reload_pressed = LOW;
}
//auto settings
if (digitalRead (selector) == LOW && reloadFinished == true) {
if (trigg_value >= triggerThreshold) {
if ((shots_fired < mag_size) && (currentMillis - previousMillis1 >= firerate)) {
previousMillis1 = currentMillis;
digitalWrite (gas_valve, HIGH);
delay (flash_delay);
digitalWrite (flash_red, HIGH);
digitalWrite (flash_green, HIGH);
digitalWrite (flash_blue, HIGH);
delay (yellow_flash_on);
digitalWrite (flash_red, LOW);
delay (valve_on);
digitalWrite (gas_valve, LOW);
delay (flash_on);
digitalWrite (flash_green, LOW);
digitalWrite (flash_blue, LOW);
shots_fired++;
Serial.println (shots_fired);
}
}
}
// Semi-auto settings
else if (digitalRead (selector) == HIGH) {
if (shots_fired < mag_size) {
if (trigg_value >= triggerThreshold) {
if (semi_fired == false) {
digitalWrite (gas_valve, HIGH);
delay (flash_delay);
digitalWrite (flash_red, HIGH);
digitalWrite (flash_green, HIGH);
digitalWrite (flash_blue, HIGH);
delay (yellow_flash_on);
digitalWrite (flash_red, LOW);
delay (valve_on);
digitalWrite (gas_valve, LOW);
delay (flash_on);
digitalWrite (flash_green, LOW);
digitalWrite (flash_blue, LOW);
shots_fired++;
Serial.println (shots_fired);
semi_fired = true;
}
}
else if (trigg_value < 40) {
semi_fired = false;
}
}
}
//backlight settings
if (fadeBypass == true) {
fadeValue = 0;
analogWrite(pwmG, fadeValue);
analogWrite(pwmB, fadeValue);
}
//backlight fade
if ((currentMillis - previousFadeMillis >= fadeInterval) && (fadeBypass == false)) {
if (fadeDirection == UP) {
fadeValue = fadeValue + fadeIncrement;
if (fadeValue >= maxPWM) {
fadeValue = maxPWM;
fadeDirection = DOWN;
}
} else {
fadeValue = fadeValue - fadeIncrement;
if (fadeValue <= minPWM) {
fadeValue = minPWM;
fadeDirection = UP;
}
}
analogWrite(pwmG, fadeValue);
analogWrite(pwmB, fadeValue);
previousFadeMillis = currentMillis;
}
// reload blink
if (reloadFinished == false) {
fadeBypass = true;
if (currentMillis - previousBlinkMillis >= blinkInterval) {
if (fadeDirection == UP) {
blinkValue = blinkValue + fadeIncrement;
if (blinkValue >= maxBlinkPWM) {
blinkValue = maxBlinkPWM;
fadeDirection = DOWN;
}
} else {
blinkValue = blinkValue - fadeIncrement;
if (blinkValue <= minBlinkPWM) {
blinkValue = minBlinkPWM;
fadeDirection = UP;
}
}
analogWrite(pwmR, blinkValue);
previousBlinkMillis = currentMillis;
}
}
if (reloadFinished == true) {
fadeBypass = false;
blinkValue = 0;
analogWrite (pwmR, blinkValue);
}
// display settings
if (currentMillis - previousTextMillis >= textInterval) {
previousTextMillis = currentMillis;
if (textBlink == 0) {
boxBlink = 0;
textBlink = 1;
}
else {
boxBlink = 1;
textBlink = 0;
}
}
int bars = map (shots_fired, mag_size, 0, 0, 16);
u8g2.firstPage();
do {
u8g2.setDrawColor(1);
u8g2.setBitmapMode (1);
u8g2.drawLine(17, 0, 17, 127);
u8g2.drawLine(18, 0, 18, 127);
u8g2.drawLine(45, 0, 45, 127);
u8g2.drawLine(46, 0, 46, 127);
u8g2.setDrawColor(0);
u8g2.drawXBMP(17, scrollYpos, 30, 29, epd_bitmap_scroll);
if (scrollYpos >= -30) {
scrollYpos --;
}
else if (scrollYpos <= -28) {
scrollYpos = 128;
};
u8g2.setDrawColor(1);
if (bars == 16) {
u8g2.drawXBMP(20, 1, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 9, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 17, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 25, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 33, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 41, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 49, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 57, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 65, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 73, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 81, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 89, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 97, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 105, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 113, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 121, 24, 7, epd_bitmap_mainBar);
}
if (bars == 15) {
u8g2.drawXBMP(20, 9, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 17, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 25, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 33, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 41, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 49, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 57, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 65, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 73, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 81, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 89, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 97, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 105, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 113, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 121, 24, 7, epd_bitmap_mainBar);
}
if (bars == 14) {
u8g2.drawXBMP(20, 17, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 25, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 33, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 41, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 49, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 57, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 65, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 73, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 81, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 89, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 97, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 105, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 113, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 121, 24, 7, epd_bitmap_mainBar);
}
if (bars == 13) {
u8g2.drawXBMP(20, 25, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 33, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 41, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 49, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 57, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 65, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 73, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 81, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 89, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 97, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 105, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 113, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 121, 24, 7, epd_bitmap_mainBar);
}
if (bars == 12) {
u8g2.drawXBMP(20, 33, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 41, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 49, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 57, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 65, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 73, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 81, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 89, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 97, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 105, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 113, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 121, 24, 7, epd_bitmap_mainBar);
}
if (bars == 11) {
u8g2.drawXBMP(20, 41, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 49, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 57, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 65, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 73, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 81, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 89, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 97, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 105, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 113, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 121, 24, 7, epd_bitmap_mainBar);
}
if (bars == 10) {
u8g2.drawXBMP(20, 49, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 57, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 65, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 73, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 81, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 89, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 97, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 105, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 113, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 121, 24, 7, epd_bitmap_mainBar);
}
if (bars == 9) {
u8g2.drawXBMP(20, 57, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 65, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 73, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 81, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 89, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 97, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 105, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 113, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 121, 24, 7, epd_bitmap_mainBar);
}
if (bars == 8) {
u8g2.drawXBMP(20, 65, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 73, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 81, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 89, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 97, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 105, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 113, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 121, 24, 7, epd_bitmap_mainBar);
}
if (bars == 7) {
u8g2.drawXBMP(20, 73, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 81, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 89, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 97, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 105, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 113, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 121, 24, 7, epd_bitmap_mainBar);
}
if (bars == 6) {
u8g2.drawXBMP(20, 81, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 89, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 97, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 105, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 113, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 121, 24, 7, epd_bitmap_mainBar);
}
if (bars == 5) {
u8g2.drawXBMP(20, 89, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 97, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 105, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 113, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 121, 24, 7, epd_bitmap_mainBar);
}
if (bars == 4) {
u8g2.drawXBMP(20, 97, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 105, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 113, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 121, 24, 7, epd_bitmap_mainBar);
}
if (bars == 3) {
u8g2.drawXBMP(20, 105, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 113, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 121, 24, 7, epd_bitmap_mainBar);
}
if (bars == 2) {
u8g2.drawXBMP(20, 113, 24, 7, epd_bitmap_mainBar);
u8g2.drawXBMP(20, 121, 24, 7, epd_bitmap_mainBar);
}
if (bars == 1) {
u8g2.drawXBMP(20, 121, 24, 7, epd_bitmap_mainBar);
}
if ((bars == 0) && (shots_fired == mag_size)) {
u8g2.setDrawColor(boxBlink);
u8g2.drawBox(21, 0, 22, 128);
u8g2.setFont(u8g2_font_luBIS19_tr);
u8g2.setFontMode(1);
u8g2.setDrawColor(textBlink);
u8g2.drawStr(22, 21,"R");
u8g2.drawStr(22, 42,"E");
u8g2.drawStr(22, 63,"L");
u8g2.drawStr(19, 85,"O");
u8g2.drawStr(22, 106,"A");
u8g2.drawStr(20, 127,"D");
}
}while ( u8g2.nextPage() );
}