Pracą kotłowni zarządza Arduino Mega 2560. Próbuję zintegrować to z Home Assistantem przy pomocy MySensors. Chciałbym mieć podgląd temperatur z czujników podłączonych do Arduino, oraz sterować przekaźnikami, które chciałbym dołożyć. Korzystając z instrukcji na stronie Ethernet Gateway połączyłem systemy przy pomocy karty sieciowej W5100. Zmodyfikowałem sketch Temperature Sensor i udało mi się odczytac parametry czujników w HA. Po zaadaptowaniu sketchu Example with button uzyskałem możliwość sterowania z poziomu HA przekaźnikiem podpiętym do Arduino. Oba sketche indywidualnie działają bez problemów. Gdy każdy z nich indywidualnie zintegruje ze sketchem sterującym kotłownią również wszystko działa. Nie mogę sobie jednak poradzić z połączeniem odczytu temperatur i sterowania przekaźnikiem w jednym programie. Próbowałem różnych modyfikacji, jednak ogarniam to na poziomie kopiuj-wklej i albo program się nie kompiluje, albo czujniki i przekaźniki nie są widoczne w HA.
Sketch wygląda tak:
#define MY_DEBUG // Enable debug prints to serial monitor
#define MY_GATEWAY_W5100 // Enable gateway ethernet module type
#define MY_IP_ADDRESS 192,168,68,130 // Enable MY_IP_ADDRESS here if you want a static ip address (no DHCP)
#define MY_PORT 5003 // The port to keep open on node server mode / or port to contact in client mode
#define MY_MAC_ADDRESS 0xDE, 0xAD, 0xBE, 0xEF, 0xFE, 0xED
#define MY_INCLUSION_MODE_FEATURE // Enable inclusion mode
#define MY_INCLUSION_MODE_DURATION 60 // Set inclusion mode duration (in seconds)
#define MY_DEFAULT_LED_BLINK_PERIOD 300 // Set blinking period
#define MY_REPEATER_FEATURE
#if defined(MY_USE_UDP)
#include <EthernetUdp.h>
#endif
#include <Ethernet.h>
#include <MySensors.h>
#include <Bounce2.h>
#include <DallasTemperature.h>
#include <OneWire.h>
#define RELAY_PIN 4 // Arduino Digital I/O pin number for relay
#define BUTTON_PIN 3 // Arduino Digital I/O pin number for button
#define CHILD_ID 1 // Id of the sensor child
#define RELAY_ON 0
#define RELAY_OFF 1
#define COMPARE_TEMP 1 // Send temperature only if changed? 1 = Yes 0 = No
#define ONE_WIRE_BUS A5 // Pin where dallase sensor is connected
#define MAX_ATTACHED_DS18B20 16
#define LED1pin 13 // LED1 do pinu 13
Bounce debouncer = Bounce();
int oldValue=0;
bool state;
MyMessage msg(CHILD_ID,V_LIGHT);
MyMessage msg(0,V_TEMP); // Initialize temperature message
unsigned long SLEEP_TIME = 3000; // Sleep time between reads (in milliseconds)
OneWire oneWire(ONE_WIRE_BUS); // Setup a oneWire instance to communicate with any OneWire devices (not just Maxim/Dallas temperature ICs)
DallasTemperature sensors(&oneWire); // Pass the oneWire reference to Dallas Temperature.
DeviceAddress Koc = { 0x28, 0x9E, 0xB1, 0xB5, 0xD, 0x0, 0x0, 0x3E };
DeviceAddress Kocp = { 0x28, 0xFF, 0x25, 0x96, 0x28, 0x20, 0x1B, 0x47 };
DeviceAddress Buf1 = { 0x28, 0xFF, 0xF7, 0x95, 0x28, 0x20, 0x1B, 0x12 };
float lastTemperature[MAX_ATTACHED_DS18B20];
int numSensors=0;
bool receivedConfig = false;
bool metric = true;
void before()
{
sensors.begin(); // Startup up the OneWire library
}
void setup()
{
// Setup the button
pinMode(BUTTON_PIN,INPUT);
// Activate internal pull-up
digitalWrite(BUTTON_PIN,HIGH);
// After setting up the button, setup debouncer
debouncer.attach(BUTTON_PIN);
debouncer.interval(5);
// Make sure relays are off when starting up
digitalWrite(RELAY_PIN, RELAY_OFF);
// Then set relay pins in output mode
pinMode(RELAY_PIN, OUTPUT);
// Set relay to last known state (using eeprom storage)
state = loadState(CHILD_ID);
digitalWrite(RELAY_PIN, state?RELAY_ON:RELAY_OFF);
}
void presentation() {
// Send the sketch version information to the gateway and Controller
sendSketchInfo("Relay & Button", "1.0");
numSensors = sensors.getDeviceCount(); // Fetch the number of attached temperature sensors
for (int i=0; i<numSensors && i<MAX_ATTACHED_DS18B20; i++) // Present all sensors to controller
{
present(i, S_TEMP);
}
// Register all sensors to gw (they will be created as child devices)
present(CHILD_ID, S_LIGHT);
}
/*
* Example on how to asynchronously check for new messages from gw
*/
void loop()
{
sensors.requestTemperatures(); // Fetch temperatures from Dallas sensors
debouncer.update();
// Get the update value
int value = debouncer.read();
if (value != oldValue && value==0) {
send(msg.set(state?false:true), true); // Send new state and request ack back
}
oldValue = value;
int16_t conversionTime = sensors.millisToWaitForConversion(sensors.getResolution()); // query conversion time and sleep until conversion completed
sleep(conversionTime); // sleep() call can be replaced by wait() call if node need to process incoming messages (or if node is repeater)
for (int i=0; i<numSensors && i<MAX_ATTACHED_DS18B20; i++) // Read temperatures and send them to controller
{
float temperature = static_cast<float>(static_cast<int>((getControllerConfig().isMetric?sensors.getTempCByIndex(i):sensors.getTempFByIndex(i)) * 10.)) / 10.; // Fetch and round temperature to one decimal
// Only send data if temperature has changed and no error
#if COMPARE_TEMP == 1
if (lastTemperature[i] != temperature && temperature != -127.00 && temperature != 85.00)
{
#else
if (temperature != -127.00 && temperature != 85.00)
{
#endif
send(msg.setSensor(i).set(temperature,1)); // Send in the new temperature
lastTemperature[i]=temperature; // Save new temperatures for next compare
}
}
sleep(SLEEP_TIME);
}
void receive(const MyMessage &message) {
// We only expect one type of message from controller. But we better check anyway.
if (message.isAck()) {
Serial.println("This is an ack from gateway");
}
if (message.type == V_LIGHT) {
// Change relay state
state = message.getBool();
digitalWrite(RELAY_PIN, state?RELAY_ON:RELAY_OFF);
// Store state in eeprom
saveState(CHILD_ID, state);
// Write some debug info
Serial.print("Incoming change for sensor:");
Serial.print(message.sensor);
Serial.print(", New status: ");
Serial.println(message.getBool());
}
}
Przy próbie kompilacji pojawiają się takie błędy:
MySensors_przekaznik_czujnik:36:14: error: redefinition of 'MyMessage msg'
C:\Users\Paweł\Desktop\MySensors\MySensors_przekaznik_czujnik\MySensors_przekaznik_czujnik.ino:35:11: note: 'MyMessage msg' previously declared here
exit status 1
redefinition of 'MyMessage msg'
Rozumiem, ze parametr “MyMessage msg” może być użyty tylko raz, jednak sketch dla czujników temperatury ma inne wartości i dla przekaźników inne. Jak to poprawnie połączyć?