Skip to content

Instantly share code, notes, and snippets.

@toxicantidote
Last active March 8, 2024 10:25
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save toxicantidote/76de0a92cd471c7a746325a81903f1f7 to your computer and use it in GitHub Desktop.
Save toxicantidote/76de0a92cd471c7a746325a81903f1f7 to your computer and use it in GitHub Desktop.
Compressor interfacing for new fridge controller
// pins where things are connected
#define PIN_INTERRUPT 2
#define PIN_LED_R 11
#define PIN_LED_G 10
#define PIN_LED_B 9
#define PIN_STATUS 13
#define PIN_RELAY_1 A0
#define PIN_RELAY_2 A1
// let the compiler know to expect flash count changes anytime
volatile unsigned char flash_count = 0;
// initialise other state variables
unsigned char last_flash_count = 0;
unsigned long last_flash_time = 0;
unsigned long keep_alive = 0;
char cmdByte;
void setup() {
// set the pins to input or output as needed
pinMode(PIN_INTERRUPT, INPUT_PULLUP);
pinMode(PIN_RELAY_1, OUTPUT);
pinMode(PIN_RELAY_2, OUTPUT);
pinMode(PIN_LED_R, OUTPUT);
pinMode(PIN_LED_G, OUTPUT);
pinMode(PIN_LED_B, OUTPUT);
pinMode(PIN_STATUS, OUTPUT);
digitalWrite(PIN_STATUS, LOW);
// cycle the RGB LED through red-green-blue
digitalWrite(PIN_LED_R, HIGH);
digitalWrite(PIN_LED_G, LOW);
digitalWrite(PIN_LED_B, LOW);
delay(200);
digitalWrite(PIN_LED_R, LOW);
digitalWrite(PIN_LED_G, HIGH);
digitalWrite(PIN_LED_B, LOW);
delay(200);
digitalWrite(PIN_LED_R, LOW);
digitalWrite(PIN_LED_G, LOW);
digitalWrite(PIN_LED_B, HIGH);
delay(200);
digitalWrite(PIN_LED_R, HIGH);
digitalWrite(PIN_RELAY_1, LOW);
digitalWrite(PIN_RELAY_2, LOW);
// attach the interrupt to watch for a falling edge on the interrupt pin
attachInterrupt(digitalPinToInterrupt(PIN_INTERRUPT), isr_flash, FALLING);
// start the UART
Serial1.begin(9600);
}
void loop() {
// turn off interrupts while getting the flash count so that the interrupt
// handler doesn't run while we are getting the value
noInterrupts();
unsigned char fc = flash_count;
interrupts();
// get the current time (since starting)
unsigned long now = millis();
unsigned long age = now - last_flash_time;
unsigned long ka_age = now - keep_alive;
// send a keepalive roughly every second
if (ka_age > 1000) {
Serial1.print(F("PING"));
keep_alive = now;
}
// give a 250ms buffer after a flash sequence before considering 'finished'.
// (250ms on, 250ms off)
if ((age > 750) || (fc > 5)) {
noInterrupts();
flash_count = 0;
fc = 0;
last_flash_count = 0;
interrupts();
}
// if the flash count has increased since last loop, reset the timer
if (fc > last_flash_count) {
last_flash_time = now;
last_flash_count = fc;
}
// look for data on the serial line
for (int i = 0; i < Serial1.available(); i++) { // if serial data is available to read
digitalWrite(PIN_STATUS, HIGH); // turn on the inbuilt led
cmdByte = Serial1.read(); // read it
if (cmdByte == 0x0A || cmdByte == 0x53) { // if the character is an S or a newline
Serial1.flush(); // clear the input buffer
if (fc > 0) { // if there is an error..
Serial1.print(F("STATUS ERROR ")); // start with an error message
Serial1.print(fc); // then number of flashes
Serial1.print(F(" "));
// and then a description of the error
if (fc == 1) {
Serial1.println(F("Battery low"));
} else if (fc == 2) {
Serial1.println(F("Fan fault or excessive restarts"));
} else if (fc == 3) {
Serial1.println(F("Compressor blockage"));
} else if (fc == 4) {
Serial1.println(F("Compressor overload"));
} else if (fc == 5) {
Serial1.println(F("Over temperature"));
} else {
Serial1.println(F("Unknown error"));
}
} else { // if there is no error
Serial1.println(F("STATUS OKAY"));
}
} else if (cmdByte == 0x31) { // if 1 is received
// set the compressor to low speed and led to green
digitalWrite(PIN_RELAY_1, LOW);
digitalWrite(PIN_RELAY_2, LOW);
digitalWrite(PIN_LED_R, LOW);
digitalWrite(PIN_LED_G, HIGH);
digitalWrite(PIN_LED_B, LOW);
Serial1.println(F("COMPRESSOR LOW"));
} else if (cmdByte == 0x30) { // if 0 is received
// set the compressor to off and led to red
digitalWrite(PIN_RELAY_1, HIGH);
digitalWrite(PIN_RELAY_2, LOW);
digitalWrite(PIN_LED_R, HIGH);
digitalWrite(PIN_LED_G, LOW);
digitalWrite(PIN_LED_B, LOW);
Serial1.println(F("COMPRESSOR OFF"));
} else if (cmdByte == 0x32) {// if 2 is received
// set the compressor to high speed and the led to blue
digitalWrite(PIN_RELAY_1, LOW);
digitalWrite(PIN_RELAY_2, HIGH);
digitalWrite(PIN_LED_R, LOW);
digitalWrite(PIN_LED_G, LOW);
digitalWrite(PIN_LED_B, HIGH);
Serial1.println(F("COMPRESSOR HIGH"));
} else { // if the command is unknown
// show some help
Serial1.println(F("Unknown command. Commands:"));
Serial1.println(F("S or newline - Get fault status"));
Serial1.println(F("0 - Compressor off"));
Serial1.println(F("1 - Compressor low speed"));
Serial1.println(F("2 - Compressor high speed"));
}
// turn off the onboard led once the command has been processed
digitalWrite(PIN_STATUS, LOW);
}
// flush the serial buffer
Serial1.flush();
}
// called by the falling edge interrupt on the fault pin
void isr_flash () {
// keep it short and sweet, just increment the flash counter
flash_count++;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment