Перейти к содержимому

#4. Разработка модуля управления нагрузкой (отопителем) на Arduino Nano и твердотельном реле с помощью SMS.

Основная задача — необходимо собрать и запрограммировать блок управления твердотельным реле к которому будет подключаться нагрузка посредством SMS и отслеживание температуры.

Условия: прием модулем SMS только от одного абонента (чтобы ограничиться от спама и ложных команд), получение SMS о текущем состоянии реле и температуры, установка значения поддержания температуры в помещении (+гистерезис), переключение работы с блока управления на термостат.

Узлы блока: плата Arduino Nano, модуль GSM Neoway M590, блок питания 220В -> 5В 2А, твердотельное реле SSR-40DA, датчик температуры на DS18B20.

Схема:

Основные команды SMS:

  1. T=** (** — уставка температуры, по умолчанию установленно +3 градуса)
  2. Stat — получение состояние реле, текущей температуры и уставки.
  3. On — включение модуля управления
  4. Off — отключение модуля управления (модуль по умолчанию выключен)

В программе будет реализована возможность подключения двух реле R1 и R2, как и отображения их состояния в SMS по запросу Stat.

Полностью код для среды Arduino IDE:

#include <SoftwareSerial.h>
#include <microDS18B20.h>
#include "GyverRelay.h"

//#define SETPOINT 30.0 // установка (ставим на 25 градусов)
#define HYSTER 3  // ширина гистерезиса

GyverRelay regulator(REVERSE);  // установка, гистерезис, направление регулирования

MicroDS18B20<2> sensor1; //датчик на D2
SoftwareSerial mySerial(10, 11); //RX, TX пины

byte R1 = 9; //пин D9 реле 1
byte R2 = 8; //пин D8 реле 2
int val1 = 0; //переменная для хранения значения R1
int val2 = 0; //переменная для хранения значения R2
String tel = "+7**********"; //номер телефона куда будут отправляться данные
String availablePhone = "+7**********"; //номер телефона только с которого будут приниматься сообщения
int setTemperature = 3; //уставка температуры по умолчанию
bool state = false; //состояние включено/выключено

void setup() {
  delay(2000);  //задержка
  
  regulator.setpoint = setTemperature;    
  regulator.hysteresis = HYSTER;   
  regulator.k = 0.5;  // коэффициент обратной связи (подбирается по факту)
  
  pinMode(R1, OUTPUT);  //устанавливаем режим работы пина 8 как Выход
  digitalWrite(R1, LOW); //устанавливаем низкое значение пина 1
  pinMode(R2, OUTPUT);  //устанавливаем режим работы пина 9 как Выход
  digitalWrite(R2, LOW); //устанавливаем низкое значение пина 2
  Serial.begin(9600);  //инициируем последовательное соединение и задаем скорость передачи данных в бит/c
  mySerial.begin(9600);
  Serial.println("GSM NEOWAY M590");
  Serial.println();
  Serial.println("Turn on AOH:");
  mySerial.println("AT+CLIP=1");  //включить АОН
  delay(300);
  Serial.println("Text format sms:");
  mySerial.println("AT+CMGF=1"); // текстовый формат SMS
  delay(300);
  Serial.println("Mode GSM:");
  mySerial.println("AT+CSCS=\"GSM\"");  // кодировка текста - GSM
  delay(300);
  Serial.println("SMS to terminal:");
  mySerial.println("AT+CNMI=2,2,0,0,0"); // вывод смс в консоль
  delay(10000);

  sms(String("GSM NEOWAY M590 ON"), String(tel)); // отправка смс о включении модема

}

void loop() 
{ 
	if(mySerial.available()) //если модуль что-то послал
	{ //проверка всех условий  
		char ch = ' ';
		String val = "";
		
		while(mySerial.available()) //получение символов для чтения из последовательного порта
		{  
			ch = mySerial.read();
			val += char(ch); //собираем принятые символы в строку
			delay(3);
		}

		Serial.print("Neoway send> ");
		Serial.println(val);
		
		if(val.indexOf("+CMT") > -1) //если есть входящее sms
		{
			String phoneSend = val.substring(val.indexOf("+7"), val.indexOf("+7") + 12);
			Serial.println("PhoneSend: " + phoneSend);
			if (phoneSend == availablePhone){
				if(val.indexOf("On") > -1 || val.indexOf("on") > -1 || val.indexOf("ON") > -1) //если есть входящее sms
				{ 
					state = true;
					Serial.println("State ON");
				}
				
				if(val.indexOf("Off") > -1 || val.indexOf("off") > -1 || val.indexOf("OFF") > -1) //если есть входящее sms
				{ 
					state = false;
					Serial.println("State OFF");
				}	
				
				if(val.indexOf("T=") > -1) // смотрим, что за команда
				{
					setTemperature = val.substring(val.indexOf("T=")+2).toInt();
					regulator.setpoint = setTemperature;
					Serial.println("Set TEMP: " + setTemperature);
				}

				if(val.indexOf("Stat") > -1) // смотрим, что за команда
				{ 
					Serial.println("Stat1");
					val1 = digitalRead(R1);  //чтение значения пина на реле R1
					val2 = digitalRead(R2);  //чтение значения пина на реле R2
					Serial.println("Stat2");
					sensor1.requestTemp(); // запрос температуры
				 
					Serial.println("Stat3");
					String val1Str, val2Str;
					if (val1 == 0){
						val1Str = "Off";
					}
					else{
						val1Str = "On";
					}

					if (val2 == 0){
						val2Str = "Off";
					}
					else{
						val2Str = "On";
					}

					Serial.println("Stat4");
					String result = "R1:" + String (val1Str) + " " + "R2:" + String (val2Str) + " " + "Temp:" + String (sensor1.getTemp()) + " SetTemp: " + String(setTemperature);
					Serial.println("Stat5");
					sms(result, String(tel)); 
				}
			}
		}
	}
	regul();
	debug();
}

void sms(String text, String phone)  // отправка СМС
{
  Serial.println("Start SMS send");
  mySerial.println("AT+CMGS=\"" + phone + "\"");
  delay(500);
  mySerial.print(text);
  delay(500);
  mySerial.print((char)26);
  delay(500);
  Serial.println("SMS send OK");
  delay(2000);
}

void regul() {
	static uint32_t tmr;
	if (millis() - tmr > 500) {
		if (state){
			Serial.println(sensor1.getTemp());
			Serial.println(regulator.getResult());
			tmr = millis();
			sensor1.requestTemp(); // запрос температуры
			regulator.input = sensor1.getTemp(); // сообщаем регулятору текущую температуру
			digitalWrite(R1, regulator.getResult());   // отправляем на реле (ОС работает по своему таймеру)
		}
		else{
			digitalWrite(R1, LOW);
		}
	}
}
void debug() {
  static uint32_t tmr;
  if (millis() - tmr > 50) {
    tmr = millis();
    /*Serial.print(regulator.input);    // фактическая
    Serial.print(',');
    Serial.print(setTemperature);  // гистерезис
    Serial.print(',');
    Serial.print(setTemperature + HYSTER);  // гистерезис
    Serial.print(',');
    Serial.print(setTemperature - HYSTER);  // гистерезис
    Serial.print(',');
    Serial.println(regulator.output * 2 + 30); // сост. реле*/
  }
}

Фото модуля управления:

Подписаться
Уведомить о
guest

0 комментариев
Старые
Новые Популярные
0
Оставьте комментарий! Напишите, что думаете по поводу статьи.x