correcciones y sensor PotenciometroI2C

main
Gerardo 2025-07-10 00:11:39 +02:00
parent 99b5299938
commit 108675e4a7
11 changed files with 641 additions and 6 deletions

View File

@ -28,7 +28,7 @@ class Actuador: public DomoEspSensorReceiver
topic[0]=0; topic[0]=0;
for(int i=0; i<MAX_ACTIVADORES; i++) for(int i=0; i<MAX_ACTIVADORES; i++)
{ {
activador[i].sen=0; activador[i].sen=NULL;
} }
} }
void set(char* topic_id, char* topic_id_out, char* _valSend) void set(char* topic_id, char* topic_id_out, char* _valSend)

View File

@ -11,6 +11,7 @@
#include "SensorLcd.h" #include "SensorLcd.h"
#include "SensorBuzzer.h" #include "SensorBuzzer.h"
#include "SensorBMP180.h" #include "SensorBMP180.h"
#include "SensorPotenI2c.h"
#include "SensorRF.h" #include "SensorRF.h"
#include "SensorSplitter.h" #include "SensorSplitter.h"
@ -41,7 +42,39 @@ class AutomatismoPulsador//automatismo para encender luz con interruptor o pulsa
}; };
//---------------------------------------------------------------------------------------------------------------------------------------------- //----------------------------------------------------------------------------------------------------------------------------------------------
class AutomatismoPulsarBoton//automatismo para simular pulsado de boton
{
Actuador presenciaOn;
Actuador presenciaOff;
//Actuador nivelLuzOff;
float fnivelLuz;
public:
AutomatismoPulsarBoton()
{
strcpy(presenciaOn.id, "PresOn");
strcpy(presenciaOff.id, "PresOff");
//strcpy(nivelLuzOff.id, "luzOff");
}
void inicia(ISensorManager* man, DomoEspSensorReceiver* timerIn, DomoEspSensorReceiver* out )
{
presenciaOn.set(timerIn->topic, out->topic, "1");
presenciaOn.AddActivador(timerIn,'>',0, 1);//nivel de luz bajo
presenciaOn.AddActivador(out,'<',1, 0);//out apagada
presenciaOff.set(timerIn->topic, out->topic,"0");
presenciaOff.AddActivador(timerIn,'<',1,1);//out encendido
presenciaOff.AddActivador(out,'>',0,0);//out encendido
man->Add(&presenciaOn);
//man->Add(&nivelLuzOff);
man->Add(&presenciaOff);
}
};
//----------------------------------------------------------------------------------------------------------------------------------------------
//automatismo para luz con sensor de presencia y de nivel de luz //automatismo para luz con sensor de presencia y de nivel de luz
class AutomatismoPresencia//automatismo para encender luz con presencia class AutomatismoPresencia//automatismo para encender luz con presencia
{ {

View File

@ -0,0 +1,97 @@
/* ### description ###
Library file for using a DS1803 dual digital potentiometer with an arduino.
please see 'README.txt' for more information
Copyright (C) <2020> <Chris Nichols. github/return5>
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
//-------------------------------------------- headers --------------------------------------------
#include "PotenciometroI2C.h" //header file for DS1803 library
//-------------------------------------------- prototypes -----------------------------------------
//function checks to make sure only a valid wiper was selected
static int checkValidWiper(const int wiper);
//function checks to makes sure value is a valid value in the range [0,255]
static int checkValidValue(const int value);
//-------------------------------------------- code -----------------------------------------------
//function checks to make sure only a valid wiper was selected
static int checkValidWiper(const int wiper) {
char c[26]; //holds string to be printed
switch(wiper) {
case WIPER_0: //FALLTHROUGH
case WIPER_1: //FALLTHROUGH
case WIPER_BOTH:
return 1; //valid wiper so return 1;
default:
snprintf(c,26,"%#04x is incorrect wiper.",wiper); //format the string to print
Serial.println(c); //print the string to serial monitor
return 0; //invalid wiper so return 0;
}
}
//function checks to makes sure value is a valid value in the range [0,255]
static int checkValidValue(const int value) {
char c[22]; //holds string to be printed
if(value<0 || value>255)
{
snprintf(c,22,"%d is out of range.",value); //format the string to print
Serial.println(c); //print the string to serial monitor
return 0; //incorrect value so return 0;
}
return 1;
}
//function to set value of wiper. takes in which address of device, wiper to write to and the value to write to it.
void setWiper(const ADDRESS address,const int wiper, const int value) {
if(checkValidWiper(wiper) && checkValidValue(value)) { //if both value and wiper are valid
char c[25]; //holds string to be printed
Wire.beginTransmission(address); //begin transmiting to potentiometer at ADRESS
Wire.write(wiper); //tell it which wiper to write to
Wire.write(value); //write the value to the wiper
Wire.endTransmission(); //end transmission to the DS1803
snprintf(c,25,"writing %d to wiper %#04x",value,wiper); //format the string to print
Serial.println(c); //print string to serial monitor
}
}
//function which reads the current value for both wipers at given address and prints values to the serial monitor
void readWipers(const ADDRESS address, int *vals) {
int wiper = 0; //shows which wiper is being read.
char c[32]; //hold formatted string.
Wire.requestFrom(address,2);//write the value to the wiper
for(int i=0; i<50; i++)
{
while(Wire.available()) {
// slave may send less than requested
if(wiper<2)
vals[wiper]=(int)Wire.read();
snprintf(c,15,"read w %d: %d",wiper++,(int)Wire.read()); //format the string before printing
Serial.println(c); // print the formatted string
}
delay(10);
}
}
//function which starts serial communication and starts i2c communication with potentiometer
void initDS1803() {
Serial.begin(9600); //serial communication at 9600 baud
Wire.begin(); //init wire.h library and join the i2c bus
}

View File

@ -0,0 +1,157 @@
/* ### description ###
Library file for using a DS1803 dual digital potentiometer with an arduino.
please see 'README.txt' for more information
Copyright (C) <2020> <Chris Nichols. github/return5>
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
#ifndef DS1803_H //guard against including the file more than once
#define DS1803_H
//-------------------------------------------- headers --------------------------------------------
#include "Arduino.h" //give access to the arduino
#include <Wire.h> //allow library to use the arduino's I2C functions
//-------------------------------------------- define ---------------------------------------------
#define WIPER_0 0xA9 //write to wiper one
#define WIPER_1 0xAA //write to wiper two
#define WIPER_BOTH 0xAF //write to both wipers at once
//---------------------------------------------- enums ---------------------------------------------------
//address of DS1803 based on the address lines A2,A1,A0.
//A_000 == address of DS1803 when A2,A1,A0 are all 0.
//A_101 is address of DS1803 when A2 = 1, A1 = 0, and A0 = 1.
enum ADDRESS_LIST {A_000 = 0x28, A_001, A_010, A_011, A_100, A_101,A_110,A_111};
//---------------------------------------------- typedefs ------------------------------------------------
typedef enum ADDRESS_LIST ADDRESS;
//-------------------------------------------- prototypes -----------------------------------------
//function to set value of wiper. takes in address of device, which wiper to write to and the value to write to it.
void setWiper(const ADDRESS address, const int wiper, const int value);
//function which reads the current value for both wipers at given address and prints them to the serial monitor of the arduino
void readWipers(const ADDRESS address, int *vals);//int vals[2]
//function which starts serial communications and starts i2c communication with potentiometer
void initDS1803();
class PotenciometroI2C
{
float corte;
ADDRESS id;
public:
PotenciometroI2C()
{
corte=20;
id=A_000;
}
void Configura(int _addres, float _corte=20)
{
corte=20;
switch (_addres)
{
case 0:
id=A_000;
break;
case 1:
id=A_001;
break;
case 2:
id=A_010;
break;
case 3:
id=A_011;
break;
case 4:
id=A_100;
break;
case 5:
id=A_101;
break;
case 6:
id=A_110;
break;
case 7:
id=A_111;
break;
default:
id=A_000;
break;
}
}
int getvi()
{
int vals[2];
readWipers(id, vals);
int vmax = vals[0];
int valor = (int)((vmax)*100. / 255 + 0.5);
valor = (int)getEscala(valor);
return valor;
}
void setv(int vol)
{
vol = setEscala(vol);
//vol=101-vol;//se invierte
vol = vol;
vol = (2.55 * (vol));
if (vol > 255)
vol = 255;
setWiper(id, WIPER_0, vol);
setWiper(id, WIPER_1, vol);
}
private:
float setEscala(float i) {
float corte_max = 100 - corte;
Serial.print("setEscala to ");
Serial.print(i);
float res = i;
if (i < corte) {
res = i * (corte_max + 1) / corte;
} else {
res = corte_max + 1 + ((i - corte) * corte / (corte_max));
}
Serial.print(" set escala out: ");
Serial.println(res);
Serial.print(" get: ");
Serial.println(getEscala(res));
return res;
}
float getEscala(float i) {
float corte_max = 100 - corte;
float res = i;
if (i < corte_max) {
res = i * (corte) / corte_max;
} else {
res = corte + ((i - corte_max) * corte_max / corte);
}
return res;
}
};
#endif

View File

@ -33,14 +33,21 @@ class SensorDHT: public DomoEspSensorReceiver
#ifdef DEBUG_PS #ifdef DEBUG_PS
Serial.println("ProcesaDHT"); Serial.println("ProcesaDHT");
#endif #endif
float ta,ha;
for(int i=0; i<4; i++) for(int i=0; i<4; i++)
{ {
if (dht.read2(pin, &t, &h, NULL) != SimpleDHTErrSuccess) if (dht.read2(pin, &ta, &ha, NULL) != SimpleDHTErrSuccess)
{ {
delay(20); delay(20);
continue; continue;
} }
break; else
{
t=ta;
h=ha;
break;
}
} }
if(tiempo==2) if(tiempo==2)
{ {

View File

@ -0,0 +1,95 @@
#ifndef SensorPotenI2cDef
#define SensorPotenI2cDef 1
#include "defines.h"
#include "PotenciometroI2C.h"
class SensorPotenI2c: public DomoEspSensorReceiver
{
float val;
PotenciometroI2C poten;
bool negado;
public:
virtual float getVal()
{
return (float)val;
}
SensorPotenI2c()
{
val=0;
topic[0]=0;
negado=false;
}
void IniciaWire(uint8_t _pin_SDA, uint8_t _pin_SCL)
{
Wire.begin(_pin_SDA, _pin_SCL);
initDS1803();
}
void set( char* topic_id, int valdef,bool _negado=false)
{
val=valdef;
negado=_negado;
strcpy(topic, topic_id);
}
virtual void procesa(IMqttManager * man, int tiempo)
{
if(tiempo==2)
{
#ifdef DEBUG_PS
Serial.print("SensorPotenI2c ");
Serial.println(val);
#endif
//loguea------------
//char buffer_t[MAXTOPICVAR];
//char buffer_p[MAXTOPICVAR];
sprintf(buffer_p, "%d", (int)val);
sprintf(buffer_t, "%s/get",topic);
man->MqttSend(buffer_t, buffer_p);
}
}
virtual void SubscribeMqtt(IMqttManager* man){
//char buffer_t[MAXTOPICVAR];
sprintf(buffer_t, "%s/set",topic);
man->MqttSubs(buffer_t);
}
virtual void OnMqtt(IMqttManager * man, char* _topic, char* payload, int tipo)
{
if(tipo!=Topic::SET)
return;
if(!strcmp(_topic, topic))
{
if(payload[0]=='X')
val=100-val;
else
val=atoi(payload);
if(val<0)
val=0;
else if(val>100)
val=100;
//cambia estado relleH
setPotenciometro();
//loguea------------
//char buffer_t[MAXTOPICVAR];
//char buffer_p[MAXTOPICVAR];
sprintf(buffer_p, "%d", (int)val);
sprintf(buffer_t, "%s/get",topic);
man->MqttSend(buffer_t, buffer_p);
}
}
void setPotenciometro()
{
if(negado)
poten.setv(100-val);
else
poten.setv(val);
};
};
#endif

View File

@ -166,7 +166,7 @@ class ConfCocina: public DomoEspConfig
lampara.set(D2, "casa/cocina/lam",0,0); lampara.set(D2, "casa/cocina/lam",0,0);
presencia.set(D5, "casa/cocina/movPul",0); presencia.set(D5, "casa/cocina/movPul",0);
tpresencia.set("casa/cocina/mov",0, 60); tpresencia.set("casa/cocina/mov",0, 60);
enable.set("casa/cocina/luzAuto"); enable.set("casa/cocina/luzAuto", 1);
interruptor.set( D1, "casa/cocina/inter", false); interruptor.set( D1, "casa/cocina/inter", false);
actp1.set("casa/cocina/movPul", "casa/cocina/mov","1"); actp1.set("casa/cocina/movPul", "casa/cocina/mov","1");
@ -375,9 +375,70 @@ class ConfPulSalon: public DomoEspConfig
}; };
class ConfigAltavozCocina: public DomoEspConfig
{
SensorDout ampli;
SensorDout altavoz;
SensorDout radio;
SensorPotenI2c poten;
SensorTimer pulso;
AutomatismoPulsarBoton pulsador;
public:
ConfigAltavozCocina()
{
strcpy(ssidWifi,"IdhunAux");//nombre wifi
strcpy(ideEsp,"Esp8266_Av_cocian");//idenitificador del esp (sera único)
ampli.set(D4,"casa/cocina/aux",0,1);
altavoz.set(D3,"casa/cocina/alt",0,1);
radio.set(D5,"casa/cocina/arad",0);
poten.set("casa/cocina/volu",50, 0);
pulso.set("casa/cocina/rad",1,1);
}
virtual void inicia(ISensorManager* man)
{
poten.IniciaWire(D2, D1);
pulsador.inicia(man,&pulso, &radio);
man->Add(&pulso);
man->Add(&radio);
man->Add(&altavoz);
man->Add(&ampli);
man->Add(&poten);
}
};
class ConfLamSalon: public DomoEspConfig
{
SensorDout lambiente;
SensorDout lchimenea;
public:
ConfLamSalon()
{
strcpy(ssidWifi,"Idhun");//nombre wifi
strcpy(ideEsp,"Esp8266_lamSalon");//idenitificador del esp (sera único)
Confdespacho ConfiguracionActual;
lchimenea.set(D1,"casa/Salon/LChime",1, 0);
lambiente.set(D2,"casa/Salon/LAmb",1, 0);
}
virtual void inicia(ISensorManager* man)
{
man->Add(&lambiente);
man->Add(&lchimenea);
}
};
ConfigAltavozCocina ConfiguracionActual;
#endif #endif

View File

@ -12,7 +12,7 @@
//sens-------------------- //sens--------------------
#define MAXSENS 16 //maximo de sensores totales #define MAXSENS 16 //maximo de sensores totales
//actuador //actuador
#define MAX_ACTIVADORES 5//maximo de activadores por actuador #define MAX_ACTIVADORES 8//maximo de activadores por actuador
#define MAX_CHAR_ENVIO 16 #define MAX_CHAR_ENVIO 16
//MELODIA---------------------- //MELODIA----------------------

View File

@ -0,0 +1,43 @@
#include <Arduino.h>
#include "Ctimer.h"
//**************************************************************************************************************************************************
Ctimer::Ctimer()
{
t=0;
}
void Ctimer::set(int incremento_seg)
{
incre=1000*incremento_seg;
}
void Ctimer::setmilis(int milis)
{
incre=milis;
}
void Ctimer::inicia()
{
t=millis();
}
bool Ctimer::onTimer()
{
unsigned long ta=millis();
if(ta<t)
return true;
if((t+incre)>=ta)
return false;
return true;
}
bool Ctimer::onTimerReset()
{
unsigned long ta=millis();
if(ta<t)
{
t=ta;
return true;
}
if((t+incre)>=ta)
return false;
t=ta;
return true;
}
//**************************************************************************************************************************************************

15
DomoEspSensorExt/Ctimer.h Normal file
View File

@ -0,0 +1,15 @@
class Ctimer
{
unsigned long t;
unsigned long incre;
public:
Ctimer();
void set(int incremento_seg);
void setmilis(int milis);
void inicia();//inicia contador de incremento
bool onTimer();//devuelve true si ha pasado el tiempo
bool onTimerReset();//pasa incremento y si ha pasado se reinicia
};

View File

@ -0,0 +1,127 @@
#include <ESP8266WiFi.h>
#include <ESP8266HTTPClient.h>
#include <WiFiClient.h>
#include "Ctimer.h"
HTTPClient http;
WiFiClient wifiClient;
char ssidWifi[24];//nombre wifi al que conectar
char keyWifi[32];//key wifi a conectar
char bufAux[32];//key wifi a conectar
String ideEsp;//identificador unico por esp
String hostMQTT;
Ctimer tReporte;
bool enviaData=false;
int DataSensor=0;
bool sensorIn=false;
int PinSensor;
void configuracion()
{
strcpy(ssidWifi,"Idhun");//nombre wifi
strcpy(keyWifi,"Ardileorca1234.");//key wifi
hostMQTT="192.168.2.50";//servidor mqttBroker
strcpy(ssidWifi,"IdhunAux");//nombre wifi
ideEsp="Esp_ext_01";//idenitificador del esp (sera único)
tReporte.set(60);
sensorIn=false;
PinSensor=5;
}
bool conectaWifi()
{
if(WiFi.status() == WL_CONNECTED)
return true;
Serial.print("Conectando wifi");
WiFi.begin(ssidWifi, keyWifi);
int i=0;
while(WiFi.status() != WL_CONNECTED) {
i++;
delay(1000);
Serial.print(".");
if(i>20)
{
Serial.println("Error conexion wifi");
return false;
}
}
Serial.println("Conectado");
return true;
}
int EnviaPost(char *data)
{
String URL = hostMQTT+"/"+ideEsp;
http.begin(wifiClient, URL);
http.addHeader("Content-Type", "text/plain");
http.POST(data);
String payload = http.getString();
Serial.println(payload);
http.end();
return payload.toInt();
}
bool leeSensor()
{
int val=digitalRead(PinSensor);
bool result=val!=DataSensor;
DataSensor=result;
return result;
}
void reinicia()
{
ESP.wdtEnable(1);
int i=0;
while(i<60){
i++;
delay(1000);
};
}
void SetSensor(int val)
{
digitalWrite(PinSensor, val);
DataSensor=val;
}
char* GetData()
{
sprintf(bufAux, "%d", DataSensor);
return bufAux;
}
void setup() {
Serial.begin(115200);
configuracion();
tReporte.inicia();
}
void loop()
{
bool envia=false;
if(sensorIn)
envia = envia|| leeSensor();
envia = envia|| tReporte.onTimerReset();
if(envia)
{
if(!conectaWifi())
{
reinicia();
}
int resul=EnviaPost(GetData());
if(!sensorIn)
SetSensor(resul);
}
}