Adaptación de código dimmeo luces

Tema en 'Programación' iniciado por car127, 31 Ago 2017.

  1. car127

    car127

    Mensajes:
    3
    Registrado:
    31 Ago 2017
    Ubicación:
    Chile
    Hola, estoy tratando de adaptar este codigo de trosdejos de un dimmer con 2 canales (luz dia y luz luna)
    http://todomarino.com/forum/temas/dimmer-con-2-canales-luz-día-y-luz-
    luna.120475/
    conocimientos de arduino muy basico mas que nada copiar algun codigo y ver su funcionamiento agradeceria su alluda
    Algunos datos: windows 10 , arduino mega 2650 (chino) , arduino ide 1.8.3
    lo que dice car127 es lo que e modificado
    esta parte marcada asi car127 ******************
    me marca este error al compilar
    request for member 'begin' in 'rtc', which is of non-class type 'DS3231()'


    #include <Wire.h>
    #include <DS3231.h> //car127
    //#include "RTClib.h"
    #define DS3231_I2C_ADDRESS 0x68 //car127
    DS3231 rtc(); //car127
    //RTC_DS1307 RTC;
    void setup () {
    Serial.begin(9600); // Establece la velocidad de datos del puerto serie
    Wire.begin(); // Inicia el puerto I2C
    rtc.begin(); //car127 Inicia la comunicacin con el RTC
    //RTC.begin(); // Inicia la comunicaci�n con el RTC
    rtc.adjust(DateTime(__DATE__, __TIME__)); // Establece la fecha y hora //car127
    //RTC.adjust(DateTime(__DATE__, __TIME__)); // Establece la fecha y hora
    }
    void loop () {
    //DateTime now = RTC.now(); // Obtiene la fecha y hora del RTC
    DateTime now = rtc.now(); // Obtiene la fecha y hora del RTC //car127
    Serial.print(now.year(), DEC);
    Serial.print('/');
    Serial.print(now.month(), DEC);
    Serial.print('/');
    Serial.print(now.day(), DEC);
    Serial.print(' ');
    Serial.print(now.hour(), DEC);
    Serial.print(':');
    Serial.print(now.minute(), DEC);
    Serial.print(':');
    Serial.print(now.second(), DEC);
    Serial.println();
    delay(1000); // La informacion se actualiza cada 1 seg.
    }*/
    #include <Wire.h> // Incluye la libreria Wire
    #include <DS3231.h> //car127
    //#include "RTClib.h" // Incluye la libreria RTClib
    #include <LiquidCrystal_I2C.h> //car127
    //#include <LiquidCrystal.h>
    #define LUZ 3 // Pin para encender las tiras de leds
    #define LUNA 11 // Este es el pin para Enceder-Apagar la luz de luna
    #define LED 16 // Es el pin A2 conectado a un led que se enciende mientras dure el amanecer-anochecer y luz de luna encendido-apagado
    #define tierra 17 // El pin 17 es el Analogico A3 que conecto a tierra para tener otra toma de tierra y conetarla al circuito electr�nico

    // Atencion: Si al ICL 7667 le metemos por PWM un analogWrite(pinPWM, 0) saldra toda la potencia. Si metemos un 255 apagara la salida.
    int minutoanterior=0, minuto=0; // Borrar cuando se borre la impresion de fecha y hora en Loop()
    LiquidCrystal_I2C lcd(0x3F,16,2); //car127
    //LiquidCrystal lcd(8, 12, 9, 4, 5, 6, 7);
    // Lista de variables para el LCD
    const float divisor=0.39; // divisor para operar el porcentaje de la intensidad
    const int numeroDeMenus=3;
    const int numeroMaximoDeSubmenus=5;
    int hora_amanecer=10, hora_anochecer=21, intensidad_max_dia=128, luz_luna_ON=20, luz_luna_OFF=9, intensidad_max_luna=128; // para la intensidad el valor minimo es 255 (apagado) y el maxino es 0 (100%)
    char tituloMenu[numeroDeMenus][16] = {
    "Elige opcion:",
    "1 Luz de dia ",
    "2 Luz de luna"};

    byte numeroDeSubmenus[numeroDeMenus] = {1,5,5};
    char tituloSubmenu[numeroDeMenus][numeroMaximoDeSubmenus][16] =
    {
    "","","","","",
    "Set Amanecer","Set Anochecer","Intensidad Max","Encender Dia","Apagar Dia",
    "Set LuzLuna ON","Set LuzLuna OFF","Intensidad Max","Encender Luna","Apagar Luna",
    };
    int adc_key_val[5] ={
    50, 200, 400, 600, 800 };
    int NUM_KEYS = 5;
    int adc_key_in;
    int key=-1; // 0= boton derecha; 1= boton arriba; 2=boton abajo; 3=boton izquierda 4=boton select
    int oldkey=-1;
    boolean luzEncendida=true;
    boolean cursorActivo=false;
    unsigned long time;
    int x=0;
    int y=0;
    // Fin Lista de variables para LCD
    boolean encendido = false; // Variable para saber si la pantalla LED esta encendida
    boolean encendidoluna = false; // Variable para saber si la luz de luna esta encendida
    int intensidad_parcial_dia=255, intensidad_parcial_luna=255; // valor para subir/bajar la intensidad de forma progresiva
    long espera = 30000; // Intervalo de espera para el ir subiendo-bajando la intensidad (milisegundos)
    long previousMillis = 0; // valor que almacena tiempo
    unsigned long currentMillis; // Guardo el tiempo actual para ir comparando con previousMillis
    DS3231 rtc(); //car127
    //RTC_DS1307 RTC; // Crea el objeto RTC
    DateTime now; // Creo la variable global now para guardar la hora del objeto RTC
    const char *nombreDia[7] = {
    "L", "M", "X", "J", "V", "S",
    "D"
    };
    void setup()
    {
    Serial.begin(9600);
    pinMode(LUZ, OUTPUT);
    pinMode(LUNA, OUTPUT);
    pinMode(tierra, OUTPUT);
    digitalWrite(tierra, LOW); // Conecto este pin a Tierra
    // pinMode(INTERRUPTOR, INPUT);
    pinMode(LED, OUTPUT);
    Serial.println("empiezo el programa");
    analogWrite(LUZ, 255); // me aseguro de que PWM es 255 (leds apagados)
    analogWrite(LUNA, 255); // me aseguro de que PWM es 255 (leds apagados)
    Wire.begin(); // Establece la velocidad de datos del bus I2C
    rtc.begin(); // car127 ******************
    //RTC.begin(); // Establece la velocidad de datos del RTC

    lcd.clear();
    lcd.begin(16, 2);
    lcd.setCursor(0,0);
    lcd.print("Muevase con las ");
    lcd.setCursor(0,1);
    lcd.print("teclas direccion");
    delay(1000);
    lcd.clear();
    lcd.setCursor(0,0);
    lcd.print("Menu principal");
    lcd.setCursor(0,1);
    lcd.print(tituloMenu[x]);
    time = millis();
    }
    void amanecer()
    {
    currentMillis = millis();
    if(currentMillis - previousMillis > espera)
    {
    previousMillis = currentMillis; // guardo el �ltimo valor de para volver a esperar el tempo de la variable "espera"
    if (intensidad_parcial_dia >= intensidad_max_dia)
    {
    digitalWrite(LED, HIGH); // Enciendo el led para saber que estoy en un bucle de encendido
    analogWrite(LUZ, intensidad_parcial_dia); //Como mucho subo la intensidad hasta 125 (50%), aqui regulo la intensidad maxima
    intensidad_parcial_dia -=5;
    }
    }
    if (intensidad_parcial_dia < intensidad_max_dia)
    {
    digitalWrite(LED, LOW); // Apago el led cuando finaliza el bucle de encedido
    encendido=true; //Pongo el valor a 1 para no volver a ejecutar esta funcion
    }
    }
    void anochecer()
    {
    currentMillis = millis();
    if(currentMillis - previousMillis > espera)
    {
    previousMillis = currentMillis; // guardo el �ltimo valor de para volver a esperar el tempo de la variable "espera"
    if (intensidad_parcial_dia <= 255)
    {
    digitalWrite(LED, HIGH); // Enciendo el led para saber que estoy en un bucle de encendido
    analogWrite(LUZ, intensidad_parcial_dia); //Poco a poco voy quitando intensidad
    intensidad_parcial_dia +=5;
    }
    }
    if (intensidad_parcial_dia > 255)
    {
    digitalWrite(LED, LOW); // Apago el led cuando finaliza el bucle de apagado
    encendido=false; //Pongo el valor a 0 para no volver a ejecutar esta funcion
    }
    }
    void encenderluzdeluna()
    {
    if (encendidoluna == false)
    {
    digitalWrite(LED, HIGH); // Enciendo el led para saber que estoy en un bucle de encendido
    for(intensidad_parcial_luna ; intensidad_parcial_luna >= intensidad_max_luna; intensidad_parcial_luna -=5) { //aqui regulo la intensidad maxima que es el valor intensidad_max_luna
    analogWrite(LUNA, intensidad_parcial_luna);
    delay(15000); //cada 15 segundos aumenta el valor en +5.
    // aqui uso el delay() porque es poco tiempo el que se lleva este bucle para su ejecucion
    }
    digitalWrite(LED, LOW); // Apago el led al finalizar el bucle de encendido
    encendidoluna=true;
    }
    }
    void apagarluzdeluna()
    {
    if (encendidoluna == true)
    {
    digitalWrite(LED, HIGH); // Enciendo el led para saber que estoy en un bucle de apagado
    for(intensidad_parcial_luna ; intensidad_parcial_luna <=255 ; intensidad_parcial_luna +=5) {
    analogWrite(LUNA, intensidad_parcial_luna);
    delay(15000); //cada 15 segundos aumenta el valor en +5.
    // aqui uso el delay() porque es poco tiempo el que se lleva este bucle para su ejecucion
    }
    digitalWrite(LED, LOW); // Apago el led
    encendidoluna=false;
    }
    }

    void luzdedia()
    {
    if (encendido==false && (now.hour()==hora_amanecer)) // Enciende
    {
    amanecer();
    }

    if (encendido==true && (now.hour()>=hora_anochecer)) // Se comienza el apagado
    {
    anochecer();
    }
    }
    void luzdeluna()
    {
    switch (now.day()) {
    case 21:
    if (now.hour()==luz_luna_ON && encendidoluna==false) {
    encenderluzdeluna(); // Activamos la luz de luna
    }
    break;
    case 22 ... 26:
    if ((now.hour()<luz_luna_OFF || now.hour()>=luz_luna_ON) && encendidoluna==false){
    encenderluzdeluna();
    }
    if (now.hour()==luz_luna_OFF && encendidoluna==true) {
    apagarluzdeluna();
    }
    break;
    case 27:
    if (now.hour()<luz_luna_OFF && encendidoluna==false){
    encenderluzdeluna();
    }
    if (now.hour()==luz_luna_OFF && encendidoluna==true) {
    apagarluzdeluna();
    }
    break;
    }
    }
    void actualiza_lcd()
    {
    // Si han pasado mas de 15 segundos apagamos la luz y volvemos al menu inicial donde mostraremos Fecha y hora
    if (millis()-time > 15000) {
    pinMode(10, OUTPUT);
    digitalWrite(10, LOW);
    luzEncendida=false;
    lcd.clear();
    x=0;
    y=0;
    lcd.setCursor(0,0); // Escribo Fecha y hora en la primera linea
    lcd.print(nombreDia[now.dayOfWeek()-1]);
    lcd.print(" ");
    escribe_cero(now.day());
    lcd.print(now.day());
    lcd.print("/");
    escribe_cero(now.month());
    lcd.print(now.month());
    lcd.print("/");
    lcd.print(now.year()-2000); //Solo imprimo los dos ultimos digitos del a�o
    lcd.print(" ");
    escribe_cero(now.hour());
    lcd.print(now.hour());
    lcd.print(":");
    escribe_cero(now.minute());
    lcd.print(now.minute());
    lcd.setCursor(0,1); // Escribo en la segunda fila
    lcd.print(tituloMenu[x]);
    }
    // Si han pasado mas de 10 segundos apagamos la luz
    if (millis()-time > 10000) {
    pinMode(10, OUTPUT);
    digitalWrite(10, LOW);
    luzEncendida=false;
    }
    // Si han pasado mas de 5 segundos apagamos el cursor
    if (millis()-time > 5000) {
    lcd.noBlink();
    cursorActivo=false;
    }
    leerTecla();
    }
    void escribe_cero(int num) // funcion para poner un cero delante de la hora minuto si es menor de 10
    {
    if (num<10) lcd.print("0");
    }
    void leerTecla()
    {
    delay(50); // Espera para evitar los rebotes de las pulsaciones
    adc_key_in = analogRead(0); // Leemos el valor de la pulsacion
    key = get_key(adc_key_in); // Obtenemos el boton pulsado
    if (key != oldkey)
    {
    time = millis();
    if (!luzEncendida) { // Al pulsar cualquier tecla encendemos la pantalla
    pinMode(10, INPUT);
    luzEncendida=true;
    }
    else { // si la pantalla esta encendida seguimos funcionando normalmente
    oldkey = key;
    if (key >=0){ // Si se ha pulsado cualquier tecla
    lcd.blink(); // Mostramos el cursor parpadeando
    cursorActivo=true;
    }
    if (key == 0){ // Se ha pulsado la tecla derecha
    x++;
    if (x>numeroDeMenus-1) x=numeroDeMenus-1;
    y=0;
    }
    if (key == 1) { // Se ha pulsado la tecla arriba
    y--;
    if (y < 0) y=0;
    }
    if (key == 2) { // Se ha pulsado la tecla abajo
    y++;
    if (y > numeroDeSubmenus[x]-1) y=numeroDeSubmenus[x]-1;

    }
    if (key == 3) { // Se ha pulsado la tecla izquierda
    x--;
    if (x<0) x=0;
    y=0;
    }
    lcd.clear();
    lcd.setCursor(0,0);
    lcd.print(tituloMenu[x]);
    lcd.setCursor(0,1);
    lcd.print(tituloSubmenu[x][y]);

    if (key == 4){ // Se ha pulsado la tecla de seleccion

    modificar_valores(x,y);
    }
    }
    }

    }
    // Convertimos el valor leido en analogico en un numero de boton pulsado
    int get_key(unsigned int input)
    {
    int k;
    for (k = 0; k < NUM_KEYS; k++)
    {
    if (input < adc_key_val[k])
    {
    return k;
    }
    }
    if (k >= NUM_KEYS)k = -1; // Error en la lectura
    return k;
    }
    void modificar_valores(int menu, int submenu)
    {
    switch (menu)
    {
    case 0: break; // en este punto no hay opciones
    case 1: // menu de Luz dia
    {
    switch (submenu)
    {
    case 0: // Cambiar hora de amanecer
    {
    lcd.clear();
    lcd.setCursor(0,0);
    lcd.print("Hora Amanecer:");
    lcd.setCursor(4,1);
    imprime_hora(hora_amanecer);
    hora_amanecer=set_valor(hora_amanecer);
    }
    break;
    case 1: // Cambiar hora de anochecer
    {
    lcd.clear();
    lcd.setCursor(0,0);
    lcd.print("Hora Anochecer:");
    lcd.setCursor(4,1);
    imprime_hora(hora_anochecer);
    hora_anochecer=set_valor(hora_anochecer);
    }
    break;
    case 2: // Cambiar intensidad
    {
    lcd.clear();
    lcd.setCursor(0,0);
    lcd.print("Intensidad:");
    lcd.setCursor(4,1);
    imprime_intensidad(intensidad_max_dia);
    intensidad_max_dia=set_valor(intensidad_max_dia);
    if (encendido == true)
    {
    analogWrite(LUZ, intensidad_max_dia); //Ponemos la nueva intensidad en la salida PWM
    intensidad_parcial_dia=intensidad_max_dia;
    }
    }
    break;
    case 3: // Encender luces
    {
    // intensidad_parcial_dia=255; // para forzar encendido aunque ya est� encendido descomnetar estas dos l�neas
    // encendido = false;
    while (encendido==false)
    {
    amanecer();
    }
    }
    break;
    case 4: // Apagar luces
    {
    while (encendido==true)
    {
    anochecer();
    }
    }
    break;
    } // fin switch submenu
    }
    break;
    case 2: // menu de luz de luna
    {
    switch (submenu)
    {
    case 0: // Cambiar hora de amanecer
    {
    lcd.clear();
    lcd.setCursor(0,0);
    lcd.print("Salida luna:");
    lcd.setCursor(4,1);
    imprime_hora(luz_luna_ON);
    luz_luna_ON=set_valor(luz_luna_ON);
    }
    break;
    case 1: // Cambiar hora de anochecer
    {
    lcd.clear();
    lcd.setCursor(0,0);
    lcd.print("Apagado Luna:");
    lcd.setCursor(4,1);
    imprime_hora(luz_luna_OFF);
    luz_luna_OFF=set_valor(luz_luna_OFF);
    }
    break;
    case 2: // Cambiar intensidad
    {
    lcd.clear();
    lcd.setCursor(0,0);
    lcd.print("Intensidad Luna:");
    lcd.setCursor(4,1);
    imprime_intensidad(intensidad_max_luna);
    intensidad_max_luna=set_valor(intensidad_max_luna);
    if (encendidoluna == true)
    {
    analogWrite(LUNA, intensidad_max_luna); //Ponemos la nueva intensidad en la salida PWM
    intensidad_parcial_luna=intensidad_max_luna;
    }
    }
    break;
    case 3: // Encender luna
    {
    encenderluzdeluna();
    }
    break;
    case 4: // Apagar luces
    {
    apagarluzdeluna();
    }
    break;
    } // fin switch submenu
    }
    break;
    } // fin switch menu
    }
    int set_valor(int valor) // funcion para sumar/restar unidades a las horas y a la intensidad
    {
    boolean enMenu = true;
    do
    {
    delay(50); // Espera para evitar los rebotes de las pulsaciones
    adc_key_in = analogRead(0); // Leemos el valor de la pulsacion
    key = get_key(adc_key_in); // Obtenemos el boton pulsado
    if (key != oldkey)
    {
    time = millis();
    if (!luzEncendida) { // Al pulsar cualquier tecla encendemos la pantalla
    pinMode(10, INPUT);
    luzEncendida=true;
    }
    else { // si la pantalla esta encendida seguimos funcionando normalmente
    oldkey = key;
    if (key >=0){ // Si se ha pulsado cualquier tecla
    lcd.blink(); // Mostramos el cursor parpadeando
    cursorActivo=true;
    }
    if (key == 0){

    lcd.setCursor(4,1);
    if (y != 2) // si estamos cambiando una hora
    {
    valor++;
    imprime_hora(valor);
    }
    else
    {
    valor--;
    imprime_intensidad(valor); // si estamos imprimiendo una intensidad
    }

    }
    if (key == 3){

    lcd.setCursor(4,1);
    if (y != 2) // si estamos cambiando una hora
    {
    valor--;
    imprime_hora(valor);
    }
    else
    {
    valor++;
    imprime_intensidad(valor); // si estamos imprimiendo una intensidad
    }

    }
    if (key == 4){
    enMenu = false;
    }
    } // fin else
    }//fin if
    } while (enMenu); // fin do while

    return valor;
    }
    void imprime_hora(int hora) //solo imprime las horas, ni minutos ni segundos, para ajusta hora de encendido y apagado
    { // los minutos no me interesa ajustarlos
    if (hora<10){
    lcd.print("0");
    lcd.print(hora);
    lcd.print(":00");
    }
    else {
    lcd.print(hora);
    lcd.print(":00");
    }
    }
    void imprime_intensidad(int i) //Imprime la intensidad de 0-100%
    {
    float resultado;
    resultado=100-(i*divisor);
    lcd.print(resultado);
    lcd.print("%");
    }
    void loop()
    {
    actualiza_lcd();
    now = rtc.now(); // car127 Obtiene la fecha y hora del RTC
    // now = RTC.now(); // Obtiene la fecha y hora del RTC
    luzdedia();
    luzdeluna();
    }
     
  2. carmamezo

    carmamezo

    Mensajes:
    4
    Registrado:
    5 Sep 2019
    Ubicación:
    Leioa
    Hola,
    Estás usando la clase DS3231, esa clase está creada con unos miembros (funciones, datos, operadores...) concretos que no son los que tú estás usando en tu código.
    Puedes ver los miembros que tiene esa clase aquí https://github.com/NorthernWidget/DS3231/blob/master/DS3231.cpp
    Al hacer "DS3231 rtc" estás creando una clase de tipo DS3231 con nombre rtc. Pero más tarde haces "rtc.begin()" y si te fijas en el enlace que te he pasado, la clase DS3231 no tiene una función begin() dentro, por lo que te da error. La clase DS3231 no tiene que ser inicializada de ninguna manera para funcionar. Tienes un ejemplo en la misma web https://github.com/NorthernWidget/DS3231/blob/master/examples/DS3231_test/DS3231_test.pde
    La parte de "#define DS3231_I2C_ADDRESS 0x68" tampoco es necesaria dado que la librería ya tiene inicializada la dirección del reloj como "#define CLOCK_ADDRESS 0x68".

    Ahora bien, si te fijas la librería RTCLib.h (https://github.com/adafruit/RTClib/blob/master/RTClib.cpp) contiene la capacidad para comunicar con varios relojes (entre ellos el DS3231), por lo que lo único que tendrías que hacer es dejar la librería RTClib.h como estaba sin comentar, quitar la librería DS3231.h (dado que la RTClib se encargará de comunicar con el DS3231 y no la necesitas), deberás crear un reloj específico a tu chip "RTC_DS3231 rtc" en vez de "DS3231 rtc" y todo lo demás estará bien, incluido el begin() y el define (aunque es "DS3231_ADDRESS" y no "DS3231_I2C_ADDRESS", de todas formas está definido así en la librería y no sería necesaria) dado que en la librería RTClib si existe una clase llamada RTC_DS3231 con una función begin() y también la definición de la dirección con ese nombre.

    Un saludo
     
    Última edición: 6 Sep 2019