Go Down

Topic: Pico de luz con PWM (Read 992 times) previous topic - next topic

Mikms

si, porque solución mediante programación no tiene, ya probé con al menos 5 tipos distintos de programaciones nuevas y siempre hace eso, antes o después lo hace, por tanto me deja claro que el problema es de ahí, que por algún motivo realmente no limita los 255, o que si se sube más una vez llegado a esos 255, termina sucediendo eso.

surbyte

Como no va a tener solución. Este tipo de cosas tiene solución.

La solución inicial es usar byte en lugar de int. Eso ya te lo expliqué, no me queda claro si lo probaste o no.


Mikms

#17
Feb 22, 2020, 10:32 am Last Edit: Feb 22, 2020, 10:48 am by Mikms
Claro que lo probé, y hasta el scketch que pusiste y te respondí que lo volvía a hacer como con int, y que con el que pusiste los pulsadores solo actuaban como eso... como simples pulsadores que encendian la luz al pulsar y al soltar se apagaba y nada más.
He estado probando otros, haciendo unos nuevos y simples que solo tenian los tres pulsadores y un led y nada más para ver si el problema venia por otro lado, con int, con byte, y el resultado termina siendo el mismo, unas veces lo hace antes, tan solo llega al máximo, otras después de sobrepasar por unos segundos el máximo, etc.

Probé limitando el pulsador de subir a 190 en vez de 250, pero más de lo mismo, y lo único que si he sacado con todo esto es que si le digo apagarse del tirón con el botón 3 (apagar), o sea irse a 0, lo va a hacer, pero si antes le bajo brillo con el botón 2 (bajar brillo) y después apago, no lo va a hacer nunca siempre y cuando le baje lo suficiente que realmente no se sabe cuanto seriá necesario al no saber realmente cuanta variación hay en ese pico, y que si no lo llevo a tope, lo dejo aunque sea en 240, tampoco hace ese pico aunque lo apague directamente, pero no funciona eso de limitar el botón con si se pulsa el botón y PWM es <240 o se lo que sea (120 mismo), porque por algún motivo lo hace.

También probé diciéndole que si PWM es 240 o mayor, que sea 240 y tampoco funciona, de hecho en puerto serial lo marca correctamente, pero el pico ese no desaparece.

Y otra cosa que he comprobado es que con arduino lo hace a veces más suave, aunque lo hace, pero en cambio ese mismo programa puesto en Attiny (85 a 1mhz) lo hace mucho más brusco y acusado.

Por ahí estuve leyendo que es algo que pasa por el reloj interno que hay en esos pines de millis y cosas asi, aunque realmente lo desconozco, y aunque eliminé todo el tema de millis y parpadeos, e incluso el led rojo de aviso, dejando todo simple... sigue con lo mismo.

Soluciones...

No llevarlo al tope que se tenga asignado (si es a 200 no llegar a 200, si es a 250 no llegar a 250)
o apagarlo mediante el botón de bajar brillo, como ya lo tenia anteriormente.

surbyte

Ok. Si puedo lo pruebo físicamente a ver si aprecio lo que mencionas.

Mikms

en un led se ve mas suave (logicamente) y ademas hay que fijarse justo cuando arranca la luz al pulsar SUBIR (despues de ya sabes, eso de subir al maximo y apagar), pero si ya le pones un transistor y un led mayor que de luz... es realmente molesto, pero con no subir al máximo o bajando luz en vez de apagar es como no lo hace, pero gracias de todas maneras por vuestra ayuda e interés, de verdad es de agradecer

surbyte

Tengo una pequeña tira led RGB no recuerdo si de 10 Leds. Pensaba probarlo con esa tira.
Tienen un MOSFET para cada canal.

Mikms

Bueno, la solucion de momento va a ser que no suba más de 140 o 150, que así no lo hace, o lo hace muy leve.

cascovida

Hola. Saludos a todos.
He intentado copiar tu idea. Espero haberala entendido bien.
De momento solo lo he probado con un Mega y un led. Pero a mi me funciona este sketch:

Code: [Select]
#define LED 45
#define BUTTON_UP 39
#define BUTTON_DOWN 43
#define BUTTON_STOP 41
byte pwm = 255;
byte step = 15; // Valor en que aumenta o disminuye el pwm.
                // Con 15 son 18 pasos.
byte state = 1;
unsigned long debounceTime = 0, wait_millis = 200; // Para debounce del botón.

void setup () {
    pinMode(BUTTON_UP, INPUT_PULLUP);
    pinMode(BUTTON_DOWN, INPUT_PULLUP);
    pinMode(BUTTON_STOP, INPUT_PULLUP);
    pinMode(LED, OUTPUT);
    Serial.begin(115200); //Depuración
}

void loop() {
    if (state) {
        analogWrite(LED, pwm);
    } else {
        analogWrite(LED, 0);
    }
    readButton();
    Serial.println(pwm);// Depuración.
}

void readButton() {
    //Falta considerar el caso de que se apriete mas de un botón a la vez y el
    //desbordamiento con un paso que no sea múltiplo de 255.
   
    if (millis() - debounceTime > wait_millis) { //Debounce.
        debounceTime = millis();
        if (digitalRead(BUTTON_STOP) == LOW) {
            state = 0;
            return;
        }
        else if (digitalRead(BUTTON_DOWN) == LOW) {
            state = 1 ;
            if( pwm  > 0) { //Evitar desbordamientos.
                pwm -= step;
            }
            return;
        }
        else if(digitalRead(BUTTON_UP) == LOW){
            state = 1;
            if( pwm  < 255) {
                pwm += step;
            }
            return;
        }
    }
    return;// No se ha pulsado ningún botón.
}


Estoy grabando los fuses a un 328 para que corra a 1MHz. A ver si también funciona con esa configuración

Mikms

gracias por tu ayuda cascovida, con el mio te aseguro  que no hay manera, antes o despues o dependiendo a que punto lo lleves lo sigue haciendo, así que tengo que probar el tuyo, que además se ve más preparado y completo que el que yo tengo.

cascovida

No, hombre. Gracias a ti que te estoy copiando la idea. Te advierto que soy bastante novato en C++. Me defiendo mejor en Python. El debouncing de la función seguro que es mejorable
Ahora estoy intentando implementar esta idea https://www.luisllamas.es/como-usar-correccion-gamma-en-fuentes-de-luz-con-arduino/ para que la transición de la intensidad de la luz sea mas suave. Saludos.

cascovida

#25
Feb 29, 2020, 03:21 pm Last Edit: Feb 29, 2020, 03:30 pm by cascovida
Hola otra vez. Al final el programa me ha quedado asi:

Code: [Select]
#define LED 45
#define BUTTON_UP 39
#define BUTTON_DOWN 43
#define BUTTON_STOP 41

// Tabla para adecuar el brillo del led al ojo humano.
// https://www.luisllamas.es/como-usar-correccion-gamma-en-fuentes-de-luz-con-arduino/
const static byte PROGMEM GammeTable8[] = {
   0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
   0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  1,  1,  1,  1,
   1,  1,  1,  1,  1,  1,  1,  1,  1,  2,  2,  2,  2,  2,  2,  2,
   2,  3,  3,  3,  3,  3,  3,  3,  4,  4,  4,  4,  4,  5,  5,  5,
   5,  6,  6,  6,  6,  7,  7,  7,  7,  8,  8,  8,  9,  9,  9, 10,
   10, 10, 11, 11, 11, 12, 12, 13, 13, 13, 14, 14, 15, 15, 16, 16,
   17, 17, 18, 18, 19, 19, 20, 20, 21, 21, 22, 22, 23, 24, 24, 25,
   25, 26, 27, 27, 28, 29, 29, 30, 31, 32, 32, 33, 34, 35, 35, 36,
   37, 38, 39, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 50,
   51, 52, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 66, 67, 68,
   69, 70, 72, 73, 74, 75, 77, 78, 79, 81, 82, 83, 85, 86, 87, 89,
   90, 92, 93, 95, 96, 98, 99,101,102,104,105,107,109,110,112,114,
   115,117,119,120,122,124,126,127,129,131,133,135,137,138,140,142,
   144,146,148,150,152,154,156,158,160,162,164,167,169,171,173,175,
   177,180,182,184,186,189,191,193,196,198,200,203,205,208,210,213,
   215,218,220,223,225,228,231,233,236,239,241,244,247,249,252,255 };

byte pwm = 0;
byte step = 15; // Valor en que aumenta o disminuye el pwm.
byte state = 0;
unsigned long debounceTime = 0, wait_millis = 200; // Para debounce del botón.

void setup () {
    pinMode(BUTTON_UP, INPUT_PULLUP);
    pinMode(BUTTON_DOWN, INPUT_PULLUP);
    pinMode(BUTTON_STOP, INPUT_PULLUP);
    pinMode(LED, OUTPUT);
    Serial.begin(115200);
}

void loop() {
    if (state) {
        analogWrite(LED, CorrectGamma_Table8(pwm));
    } else {
        analogWrite(LED, 0);
    }
    readButton();
    Serial.println(pwm);// Depuración.
}

byte CorrectGamma_Table8(byte value) {
   return pgm_read_byte(&GammeTable8[value]);
}

void readButton() {
    //Falta considerar el caso de que se apriete mas de un botón a la vez y el
    //desbordamiento con un paso que no sea múltiplo de 255.
    
    if (millis() - debounceTime > wait_millis) { //Debounce.
        debounceTime = millis();
        if (digitalRead(BUTTON_STOP) == LOW) {
            state = 0;
            return;
        }
        else if (digitalRead(BUTTON_DOWN) == LOW) {
            state = 1 ;
            if( pwm  > 0) { //Evitar desbordamientos.
                pwm -= step;
            }
            return;
        }
        else if(digitalRead(BUTTON_UP) == LOW){
            state = 1;
            if( pwm  < 255) {
                pwm += step;
            }
            return;
        }
    }
    return;// No se ha pulsado ningún botón.
}


La intensidad de la luz se comporta de una manera mucho más suave. A ver si esta tarde puede hacer un montaje con mosfet y el 328 a 1MHz a ver que tal queda.
Saludos.

Go Up