class Emulator
{
- enum {Status_Stopped = 0x01,
- Status_Heating = 0x10,
- Status_Cooling = 0x20,
- Status_HoldingLimit = 0x30,
- Status_HoldingTime = 0x40,
- Status_HoldingCurrent = 0x50};
+ enum {
+ Status_Stopped = 0x01,
+ Status_Heating = 0x10,
+ Status_Cooling = 0x20,
+ Status_HoldingLimit = 0x30,
+ Status_HoldingTime = 0x40,
+ Status_HoldingCurrent = 0x50
+ };
enum {
Error_CoolingRate = (1<<0),
Error_OpenCircuit = (1<<1),
};
public:
- Emulator()
+ Emulator(Stream *stream)
{
+ mStream = stream;
mIndex = 0;
mStatus = Status_Stopped;
mErrorCode = Error_NoError;
++p;
}
mLimit = v;
- Serial.write('\r');
+ mStream->write('\r');
}
void Command_R(const char *cmd)
++p;
}
mRamp = v;
- Serial.write('\r');
+ mStream->write('\r');
}
void Command_T()
{
- char buffer[12];
- Serial.write(mStatus);
- Serial.write(mErrorCode);
- sprintf(buffer, "++++%04x", mTemp);
- Serial.write((const uint8_t *)buffer, 8);
- Serial.write('\r');
+ uint8_t buffer[12];
+ buffer[0] = mStatus;
+ buffer[1] = mErrorCode;
+ sprintf((char *)&buffer[2], "++++%04x\r", mTemp);
+ mStream->write((const uint8_t *)buffer, 11);
}
void Command_S()
{
mStatus = (mTemp > mLimit) ? Status_Cooling : Status_Heating;
- Serial.write('\r');
+ mStream->write('\r');
}
void Command_E()
{
mStatus = Status_Stopped;
- Serial.write('\r');
+ mStream->write('\r');
}
void Command_O()
{
else
mStatus = Status_HoldingTime;
}
- Serial.write('\r');
+ mStream->write('\r');
}
// Tick is called once per second
virtual void Error(uint8_t code, const char *message)
{
mErrorCode = code;
+ mStream->print(code, HEX);
+ mStream->print(": ");
+ mStream->println(message);
}
- virtual void Emit(const char *s) = 0;
+ bool IsHeating() const { return mStatus == Status_Heating; }
+ bool IsCooling() const { return mStatus == Status_Cooling; }
+ bool IsPumping() const { return false; }
protected:
+ Stream *mStream;
char mBuffer[10];
uint8_t mIndex;
// Copyright (c) 2013 Pat Thoyts <patthoyts@users.sourceforge.net>
//
#include <Arduino.h>
-#include <Ports.h>
#include <avr/pgmspace.h>
+#include <MilliTimer.h>
+#include <LEDPulse.h>
#include "Emulator.h"
-class Emulator2 : public Emulator
+const int LED_HEARTBEAT = 11; // R1: PB1 | OC1A (green)
+const int LED_COOLING = 10; // R2: PB2 | OC1B (blue)
+const int LED_HEATING = 9; // R3: PB3 | OC2A (red)
+const int LED_PUMPING = 6; // R4: PD6 | OC0A (amber)
+
+static Emulator emulator(&Serial);
+static MilliTimer emulatorTimer;
+static MilliTimer heartbeatTimer;
+static LEDPulse heartbeatLed(LED_HEARTBEAT);
+
+inline void pinInit(int pin, int state)
{
-public:
- void Emit(const char *s)
- {
- Serial.print(s);
- Serial.print('\r');
- }
- void Error(uint8_t code, const char *msg)
- {
- Serial.println(msg);
- }
-};
-static Emulator2 emulator;
-static MilliTimer timer1;
+ pinMode(pin, OUTPUT);
+ digitalWrite(pin, state);
+}
void setup()
{
- pinMode(13, OUTPUT);
- digitalWrite(13, HIGH);
+ pinInit(LED_HEARTBEAT, LOW);
+ pinInit(LED_COOLING, LOW);
+ pinInit(LED_HEATING, LOW);
+ pinInit(LED_PUMPING, LOW);
Serial.begin(19200, SERIAL_8N1);
}
void loop()
{
+ if (heartbeatTimer.poll(10))
+ {
+ heartbeatLed.Next();
+ }
+
int count = Serial.available();
- if (count > 0) {
- for (int n = 0; n < count; ++n) {
+ if (count > 0)
+ {
+ for (int n = 0; n < count; ++n)
+ {
char c = Serial.read();
emulator.Add(c);
- //Serial.print(c, HEX);
}
- //Serial.println(".");
}
- if (timer1.poll(1000)) {
+
+ if (emulatorTimer.poll(1000))
+ {
emulator.Tick();
- //Serial.println("tick");
- PORTB ^= _BV(PINB5);
+ digitalWrite(LED_HEATING, emulator.IsHeating() ? HIGH : LOW);
+ digitalWrite(LED_COOLING, emulator.IsCooling() ? HIGH : LOW);
+ digitalWrite(LED_PUMPING, emulator.IsPumping() ? HIGH : LOW);
}
}