Непосредственное выполнение работы:
Для простоты сначала соберите схему с одним светодиодом.
Необходимые материалы:
Возьмите все необходимые материалы. Удобно расположите микроконтроллер, фотомодуль с фоторезистором, макетную плату. Аккуратно, без сильных нажимов, во избежании поломки материалов, подсоедините каждый элемент как показано на схеме. Внимательно проверьте, правильно ли подключены элементы, проверьте полярность элементов, посмотрите, заземлена ли цепь.
Схема лабораторной установки:
Датчик освещённости: VCC -> A1, GND - GND, D0 -> 5V. Светодиод подключается, например, к 13 пину.
Разработка скетча.
Создаём новый скетч и называем его, например, Lamppost. Проверяем правильность выбранных плат и порта.
Записываем необходимые директивы:
#define PIN_LED 13
#define PIN_PHOTO_SENSOR A1
В функции setup() инициализируем 13й пин для управления светодиодом:
void setup() {
Serial.begin(9600);
pinMode(PIN_LED, OUTPUT);
}
Изменение яркости светодиода осуществлено при помощи ШИМ. На пин со светодиодом посылаются значения от 0 до 255 с помощью функции analogWrite()
void loop() {
int val = analogRead(PIN_PHOTO_SENSOR);
Serial.println(val);
int ledPower = map(val, 0, 1023, 0, 255);
analogWrite(PIN_LED, ledPower);
}
Про функцию map() можете прочитать здесь.
Задание: измените схему так, чтобы яркость изменяли 6 светодиодов. Они должы быть подключены параллельно друг другу.
Разработка "умного освещения".
Для дальнейшей работы Вам необходимо ознакомиться с платформой NodeMCU, переписать скетч с учётом её особенностей, а также повторить лабораторную работу с использованием данной платформы.
Для управления "умным освещением" с помощью приложения Alterozoom Вам необходимо скачать его c официального сайта. Чтобы получить лицензию, пишите на почту branislava.jankovic.1998@ gmail.com
Повторите эту и эту лабораторную работу.
Чтобы иметь возможность управлять нашим освещением из приложения, нужно изменить скетч: добавить необходимые библиотеки, функции и пр..
#include <ARpcArduStrHlp.h>
#include <ARpcDevice.h>
#include <ARpcDeviceState.h>
#include <ARpcIDevEventsCallback.h>
#include <ARpcIMessageCallback.h>
#include <ARpcIWriteCallback.h>
#include <ARpcRealDeviceMessageDispatch.h>
#include <ARpcSrvReady.h>
#include <ARpcStarNetDevice.h>
#include <ARpcStarNetEndPoint.h>
#include <ARpcStarNetEndPointDevice.h>
#include <ARpcStarNetStreamWriter.h>
#include <ARpcStreamParser.h>
#include <ARpcStreamWriter.h>
#include <ARpcUuid.h>
#include <BearSSLHelpers.h>
#include <CertStoreBearSSL.h>
#include <ESP8266WiFi.h>
#include <ESP8266WiFiAP.h>
#include <ESP8266WiFiGeneric.h>
#include <ESP8266WiFiMulti.h>
#include <ESP8266WiFiScan.h>
#include <ESP8266WiFiSTA.h>
#include <ESP8266WiFiType.h>
#include <WiFiClient.h>
#include <WiFiClientSecure.h>
#include <WiFiClientSecureAxTLS.h>
#include <WiFiClientSecureBearSSL.h>
#include <WiFiServer.h>
#include <WiFiServerSecure.h>
#include <WiFiServerSecureAxTLS.h>
#include <WiFiServerSecureBearSSL.h>
#include <WiFiUdp.h>
#include <ESP8266HTTPClient.h>
uint16_t port=4081;
WiFiServer server(port);
WiFiClient client;
IPAddress bCastSenderIp;
WiFiUDP bCastCli;
bool connecting=false;
const char* ssid="SSID_cети";
const char* password="пароль";
unsigned long lastSyncMillis=0;
const char *deviceName="lamppost";
const ARpcUuid deviceId("{e84c3446-f8cc-4de8-9306-c44ebff10dad}"); // эта часть вариативна
const char *interfaceStr="<controls>"
"<group title=\"LAMPPOST_SETTINGS\">"
"<control title=\"MAX LIGHT UP\" command=\"maxlightup\"/>"
"<control title=\"MAX LIGHT DOWN\" command=\"maxlightdown\"/>"
"<control title=\"MIN LIGHT UP\" command=\"minlightup\"/>"
"<control title=\"MIN LIGHT DOWN\" command=\"minlightdown\"/>"
"</group>"
"</controls>";
const char *sensorsDef="<sensors>"
"<sensor name=\"light\" type=\"f32_sv_d3\"/>"
"</sensors>";
class NetWriteCb :public ARpcIWriteCallback
{
public:
void writeData(const char *d,unsigned long sz)override
{
client.write(d,sz);
}
void writeStr(const char *str)override
{
client.print(str);
}
void writeStr(const __FlashStringHelper *str)override
{
client.print(str);
}
}netCb;
class SerialWriteCb :public ARpcIWriteCallback
{
public:
void writeData(const char *d,unsigned long sz)override
{
Serial.write(d,sz);
}
void writeStr(const char *str)override
{
Serial.print(str);
}
void writeStr(const __FlashStringHelper *str)override
{
Serial.print(str);
}
}serialCb;
ARpcDevice wifiDev(300,&netCb,&deviceId,deviceName);
ARpcDevice serialDev(300,&serialCb,&deviceId,deviceName);
float sLight[3];
void writeLight() {
sLight[0]=minlight;
sLight[1]=light;
sLight[2]=maxlight;
wifiDev.disp().writeMeasurementB("light",sLight,3);
}
//callback-класс для обработки команд, вызывается библиотекой ARpc
class EventsCb :public ARpcIDevEventsCallback
{
public:
explicit EventsCb(ARpcDevice *d)
{
dev=d;
}
virtual void processCommand(const char *cmd,const char *args[],unsigned char argsCount)
{
byte cmdOK = 1;
byte cmdLight = 0;
if (strcmp(cmd,"maxlightup") ==0) { if (maxlight < 800) { maxlight = maxlight + settingStep; cmdLight = 1; }}
else if(strcmp(cmd,"maxlightdown") ==0) { if (maxlight > 200) { maxlight = maxlight - settingStep; cmdLight = 1; }}
else if(strcmp(cmd,"minlightup") ==0) { if (minlight < 800) { minlight = minlight + settingStep; cmdLight = 1; }}
else if(strcmp(cmd,"minlightdown") ==0) { if (minlight > 200) { minlight = minlight - settingStep; cmdLight = 1; }}
else {
wifiDev.disp().writeErr("Unknown cmd");
cmdOK = 0;
}
if (cmdOK == 1) {
if (cmdLight == 1) writeLight();
wifiDev.disp().writeOk();
}
}
virtual void onSyncMsg()
{
lastSyncMillis=millis();
}
private:
ARpcDevice *dev;
}serialEcb(&serialDev),wifiEcb(&wifiDev);
class SrcReadyCb :public ARpcISrvReadyCallback
{
public:
void processSrvReadyMsg(const ARpcUuid &srvId,const char *srvName)
{
serialDev.disp().writeInfo("Server detected: ",bCastSenderIp.toString().c_str(),srvName);
if(client.connected()||connecting)return;
serialDev.disp().writeInfo("Connecting to server...");
connecting=true;
client.connect(bCastSenderIp,port);
for(int i=0;i<20;++i)
{
if(client.connected())
break;
delay(100);
}
serialDev.disp().writeInfo("Connected to server");
connecting=false;
wifiDev.resetParser();
lastSyncMillis=millis();
}
}srvReadyCb;
ARpcSrvReady srvReadyParser(200,&srvReadyCb);
void connectWifi()
{
WiFi.begin(ssid,password);
while(WiFi.status()!=WL_CONNECTED)
{
delay(500);
serialDev.disp().writeInfo("Wifi connecting");
}
serialDev.disp().writeInfo("WiFi connected");
}
int step = 0;
void setup() {
pinMode(PIN_LED, OUTPUT);
delay(2000);
Serial.begin(9600);
wifiDev.disp().installDevEventsHandler(&wifiEcb);
wifiDev.disp().setControls(interfaceStr);
wifiDev.disp().setSensors(sensorsDef);
serialDev.disp().installDevEventsHandler(&serialEcb);
serialDev.disp().setControls(interfaceStr);
serialDev.disp().setSensors(sensorsDef);
connectWifi();
bCastCli.begin(port);
// Start the server
server.begin();
serialDev.disp().writeInfo("Server started");
// Print the IP address
serialDev.disp().writeInfo(WiFi.localIP().toString().c_str());
serialDev.resetStream();
}
void checkBCastCli()
{
static int sz=0;
sz=bCastCli.parsePacket();
if(sz>0)
{
bCastSenderIp=bCastCli.remoteIP();
for(int i=0;i<sz;++i)
srvReadyParser.putByte(bCastCli.read());
}
}
void checkWifiClient()
{
if(client)
{
if(!client.connected())
{
serialDev.disp().writeInfo("Client connection lost");
client=server.available();
if(client)
{
serialDev.disp().writeInfo("Take next pending incoming connection");
lastSyncMillis=millis();
wifiDev.resetStream();
wifiDev.resetParser();
}
delay(100);
}
else
{
while(client.available())
wifiDev.putByte(client.read());
}
}
else
{
client=server.available();
if(client)
{
serialDev.disp().writeInfo("Take next pending incoming connection");
lastSyncMillis=millis();
wifiDev.resetStream();
wifiDev.resetParser();
}
delay(100);
}
}
В функцию loop() добавляем следующие строчки:
while(Serial.available())
serialDev.putByte(Serial.read());
if(WiFi.status()!=WL_CONNECTED)
connectWifi();
checkBCastCli();
checkWifiClient();
if(((millis()-lastSyncMillis)>12000)&&client.connected())
{
client.stop();
checkWifiClient();
}
delay(50);