Eine elegante automatische Treppenbeleuchtung (Teil2) - AZ-Delivery

Bienvenidos a la segunda parte de nuestra serie "elegante control de luz de escalera". Como siempre en la serie de proyectos, las siguientes partes se trata de mejorar o ampliar la función. Por parte de hoy, estamos mejorando la función primero.

Básicamente, nuestras escaleras van lentamente de abajo a arriba, si se introduce de arriba a abajo o viceversa, de abajo a arriba. Sin embargo, sería mejor si nuestras escaleras se encienden exactamente en la dirección como una luz corriente, en la que entramos en las escaleras y luego lentamente se apagan de nuevo.

Esto es precisamente de lo que se trata esta ampliación en la parte actual de la serie. La luz de la escalera sigue nuestros pasos tan pronto como entramos en las escaleras, independientemente de la dirección.

Los parámetros y el circuito pueden ser de la primera parte de la serie ser tomado. Es una extensión de software puro.

 

#define Num_Stages 15
#define Delay_Stages 10
#define Delay_ON_to_OFF 5

 

Num_Stages

Define el número de escaleras a iluminar (máximo 16, contando desde 0 hasta el inicio. Valor máximo: 15)

Delay_Stages

Período de desvanecimiento para cada paso de escalera -> cuanto menor sea el valor, mayor será el período, más lento.

Delay_ON_to_OFF

Período que pasa dejando las escaleras en el estado "encendido".

 

Después de que los valores se hayan personalizado según sus propias preferencias, el código extendido se puede cargar en el Arduino:

 

 

2019 Tobias Kuch GPL 3.0
incluír <Alambre.H>

#define PWM_Module_Base_Addr 0x40 10000000b El último bit del byte de dirección define la operación que se va a realizar. Cuando se establece en el módulo lógico 1 0x41 2
selecciona una operación de lectura mientras que un 0 lógico selecciona una operación de escritura.
#define OE_Pin  8           Pin para el activador de salida
#define CPU_LED_Pin 13
#define PIRA_Pin 2
#define PIRB_Pin 3

#define Num_Stages  15
#define Delay_Stages  5
#define Delay_ON_to_OFF  30  Mínimo Delay_ON_to_OFF en segundos
#define delay_per_Stage_in_ms 200

Int Pwm_Channel = 0;
Int Pwm_Channel_Brightness = 0;

Bool Motion_Trigger_Down_to_Up = Falso;
Bool Motion_Trigger_Up_to_Down = Falso;
Bool On_Delay = Falso;

interrumpir el control
Byte A60telSeconds24 = 0;
Byte Seconds24;

Isr(TIMER1_COMPA_vect)
{   A60telSeconds24++;   Si (A60telSeconds24 > 59)   {     A60telSeconds24 = 0;     Seconds24++;     Si (Seconds24 > 150)     {       Seconds24 = 0;     }   }
}

Vacío ISR_PIR_A()
{   Bool PinState = digitalRead(PIRA_Pin);   Si (PinState)   {     Si (!(Motion_Trigger_Up_to_Down) Y !(Motion_Trigger_Down_to_Up))     {       digitalWrite(CPU_LED_Pin, Alto);       Motion_Trigger_Down_to_Up = Verdad;     } PIR A activado   } Más   {     digitalWrite(CPU_LED_Pin, Bajo);   }
}

Vacío ISR_PIR_B()
{   Bool PinState = digitalRead(PIRB_Pin);   Si (PinState)   {     Si (!(Motion_Trigger_Down_to_Up) Y !(Motion_Trigger_Up_to_Down))     {       digitalWrite(CPU_LED_Pin, Alto);       Motion_Trigger_Up_to_Down = Verdad;     } PIR B activado   } Más   {     digitalWrite(CPU_LED_Pin, Bajo);   }
}

Vacío Init_PWM_Module(Byte PWM_ModuleAddr)
{   pinMode(OE_Pin, Salida);   pinMode(CPU_LED_Pin, Salida);   digitalWrite(OE_Pin, Alto); Pin de activación de salida BAJO activo (OE).   Alambre.beginTransmisión(PWM_ModuleAddr); Iniciar la transferencia de datos   Alambre.Escribir(0x00);                       //   Alambre.Escribir(0x06);                       Restablecimiento de software   Alambre.endTransmission();                 Detener comunicación - Enviar bit de parada   Retraso(400);   Alambre.beginTransmisión(PWM_ModuleAddr); Iniciar la transferencia de datos   Alambre.Escribir(0x01);                       Seleccionar el registro del modo 2 (registro de comandos)   Alambre.Escribir(0x04);                       Configurar chip: 0x04: salida de polo muerto 0x00: Salida de drenaje abierta.   Alambre.endTransmission();                 Detener comunicación - Enviar bit de parada   Alambre.beginTransmisión(PWM_ModuleAddr); Iniciar la transferencia de datos   Alambre.Escribir(0x00);                      Seleccionar el registro del modo 1 (registro de comandos)   Alambre.Escribir(0x10);                      Configurar SleepMode   Alambre.endTransmission();                Detener comunicación - Enviar bit de parada   Alambre.beginTransmisión(PWM_ModuleAddr); Iniciar la transferencia de datos   Alambre.Escribir(0xFE);                       Seleccione PRE_SCALE registrarse   Alambre.Escribir(0x03);                       Establezca Prescaler. La frecuencia máxima de PWM es de 1526 Hz si el PRE_SCALEer el operador se establece en "0x03h". Estándar: 200 Hz   Alambre.endTransmission();                 Detener comunicación - Enviar bit de parada   Alambre.beginTransmisión(PWM_ModuleAddr); Iniciar la transferencia de datos   Alambre.Escribir(0x00);                       Seleccionar el registro del modo 1 (registro de comandos)   Alambre.Escribir(0xA1);                       Configurar chip: ERrlaube Todas las direcciones I2C de la llamada, utilice el reloj interno, / permita la característica del incremento automático   Alambre.endTransmission();                 Detener comunicación - Enviar bit de parada
}


Vacío Init_PWM_Outputs(Byte PWM_ModuleAddr)
{   digitalWrite(OE_Pin, Alto); Pin de activación de salida BAJO activo (OE).   Para ( Int Z = 0; Z < 16 + 1; Z++)   {     Alambre.beginTransmisión(PWM_ModuleAddr);     Alambre.Escribir(Z * 4 + 6);      Seleccione PWM_Channel_ON_L registrarse     Alambre.Escribir(0x00);                     Valor para el registro anterior     Alambre.endTransmission();     Alambre.beginTransmisión(PWM_ModuleAddr);     Alambre.Escribir(Z * 4 + 7);      Seleccione PWM_Channel_ON_H registrarse     Alambre.Escribir(0x00);                     Valor para el registro anterior     Alambre.endTransmission();     Alambre.beginTransmisión(PWM_ModuleAddr);     Alambre.Escribir(Z * 4 + 8);   Seleccione PWM_Channel_OFF_L registrar     Alambre.Escribir(0x00);        Valor para el registro anterior     Alambre.endTransmission();     Alambre.beginTransmisión(PWM_ModuleAddr);     Alambre.Escribir(Z * 4 + 9);  Seleccione PWM_Channel_OFF_H registrarse     Alambre.Escribir(0x00);             Valor para el registro anterior     Alambre.endTransmission();   }   digitalWrite(OE_Pin, Bajo); Pin de activación de salida BAJO activo (OE).
}

Vacío Configuración()
{   Initalización   Serial.Comenzar(9600);   pinMode(PIRA_Pin, Entrada);   pinMode(PIRB_Pin, Entrada);   Serial.Comenzar(9600);   Alambre.Comenzar(); Initalisia I2C Bus A4 (SDA), A5 (SCL)   Init_PWM_Module(PWM_Module_Base_Addr);   Init_PWM_Outputs(PWM_Module_Base_Addr);   noInterrupts();   adjuntarInterrupt(0, ISR_PIR_A, cambio);   adjuntarInterrupt(1, ISR_PIR_B, cambio);   TCCR1A = 0x00;   TCCR1B = 0x02;   TCNT1 = 0;      Inicializar registro con 0   OCR1A =  33353;      Predocumentos Registro de Comparación de Salida   TIMSK1 |= (1 << OCIE1A);  Activar interrupción de comparación de temporizadores   Interrumpe();
}

Vacío Down_to_Up_ON()
{   Pwm_Channel = 0;   Pwm_Channel_Brightness = 0;   Mientras (Pwm_Channel < Num_Stages + 1)   {     Alambre.beginTransmisión( PWM_Module_Base_Addr);     Alambre.Escribir(Pwm_Channel * 4 + 8);   Seleccione PWM_Channel_0_OFF_L registrarse     Alambre.Escribir((Byte)Pwm_Channel_Brightness & 0xff);        Valor para el registro anterior     Alambre.endTransmission();     Alambre.beginTransmisión( PWM_Module_Base_Addr);     Alambre.Escribir(Pwm_Channel * 4 + 9);  Seleccione PWM_Channel_0_OFF_H registrar     Alambre.Escribir((Pwm_Channel_Brightness >> 8));             Valor para el registro anterior     Alambre.endTransmission();     Si (Pwm_Channel_Brightness < 4095)     {       Pwm_Channel_Brightness = Pwm_Channel_Brightness + Delay_Stages;       Si (Pwm_Channel_Brightness > 4095) {         Pwm_Channel_Brightness = 4095;       }     } Más Si ( Pwm_Channel < Num_Stages + 1)     {       Pwm_Channel_Brightness = 0;       Retraso(delay_per_Stage_in_ms);       Pwm_Channel++;     }   }
}

Vacío Down_to_Up_OFF()
{   Pwm_Channel = 0;   Pwm_Channel_Brightness = 4095;   Mientras (Pwm_Channel < Num_Stages + 1)   {     Alambre.beginTransmisión( PWM_Module_Base_Addr);     Alambre.Escribir(Pwm_Channel * 4 + 8);   Seleccione PWM_Channel_0_OFF_L registrarse     Alambre.Escribir((Byte)Pwm_Channel_Brightness & 0xff);        Valor para el registro anterior     Alambre.endTransmission();     Alambre.beginTransmisión(PWM_Module_Base_Addr);     Alambre.Escribir(Pwm_Channel * 4 + 9);  Seleccione PWM_Channel_0_OFF_H registrar     Alambre.Escribir((Pwm_Channel_Brightness >> 8));             Valor para el registro anterior     Alambre.endTransmission();     Si (Pwm_Channel_Brightness > 0)     {       Pwm_Channel_Brightness = Pwm_Channel_Brightness - Delay_Stages;       Si (Pwm_Channel_Brightness < 0) {         Pwm_Channel_Brightness = 0;       }     } Más Si ( Pwm_Channel < Num_Stages + 1)     {       Pwm_Channel_Brightness = 4095;       Retraso(delay_per_Stage_in_ms);       Pwm_Channel++;     }   }
}

Vacío Up_to_DOWN_ON()
{   Pwm_Channel = Num_Stages;   Pwm_Channel_Brightness = 0;   Mientras (Pwm_Channel > -1)   {     Alambre.beginTransmisión( PWM_Module_Base_Addr);     Alambre.Escribir(Pwm_Channel * 4 + 8);   Seleccione PWM_Channel_0_OFF_L registrarse     Alambre.Escribir((Byte)Pwm_Channel_Brightness & 0xff);        Valor para el registro anterior     Alambre.endTransmission();     Alambre.beginTransmisión(PWM_Module_Base_Addr);     Alambre.Escribir(Pwm_Channel * 4 + 9);  Seleccione PWM_Channel_0_OFF_H registrar     Alambre.Escribir((Pwm_Channel_Brightness >> 8));             Valor para el registro anterior     Alambre.endTransmission();     Si (Pwm_Channel_Brightness < 4095)     {       Pwm_Channel_Brightness = Pwm_Channel_Brightness + Delay_Stages;       Si (Pwm_Channel_Brightness > 4095) {         Pwm_Channel_Brightness = 4095;       }     } Más Si ( Pwm_Channel >= 0)     {       Pwm_Channel_Brightness = 0;       Retraso(delay_per_Stage_in_ms);       Pwm_Channel--;       Si ( Pwm_Channel < 0)       {         Pwm_Channel = 0;         Romper;       }     }   }
}



Vacío Up_to_DOWN_OFF()
{   Pwm_Channel = Num_Stages;   Pwm_Channel_Brightness = 4095;   Mientras (Pwm_Channel > -1)   {     Alambre.beginTransmisión(PWM_Module_Base_Addr);     Alambre.Escribir(Pwm_Channel * 4 + 8);   Seleccione PWM_Channel_0_OFF_L registrarse     Alambre.Escribir((Byte)Pwm_Channel_Brightness & 0xff);        Valor para el registro anterior     Alambre.endTransmission();     Alambre.beginTransmisión(PWM_Module_Base_Addr);     Alambre.Escribir(Pwm_Channel * 4 + 9);  Seleccione PWM_Channel_0_OFF_H registrar     Alambre.Escribir((Pwm_Channel_Brightness >> 8));             Valor para el registro anterior     Alambre.endTransmission();     Si (Pwm_Channel_Brightness > 0)     {       Pwm_Channel_Brightness = Pwm_Channel_Brightness - Delay_Stages;       Si (Pwm_Channel_Brightness < 0) {         Pwm_Channel_Brightness = 0;       }     } Más Si ( Pwm_Channel >= 0)     {       Pwm_Channel_Brightness =  4095;       Retraso(delay_per_Stage_in_ms);       Pwm_Channel--;       Si ( Pwm_Channel < 0)       {         Pwm_Channel = 0;         Romper;       }     }   }
}





Vacío Bucle()
{   Si ((Motion_Trigger_Down_to_Up) Y !(On_Delay) )   {     Seconds24 = 0;     On_Delay = Verdad;     Down_to_Up_ON();   }   Si ((On_Delay) Y (Seconds24 > Delay_ON_to_OFF) Y (Motion_Trigger_Down_to_Up) )   {     Down_to_Up_OFF();     Motion_Trigger_Down_to_Up = Falso;     On_Delay = Falso;     Seconds24 = 0;   }   Si ((Motion_Trigger_Up_to_Down) Y !(On_Delay) )   {     Seconds24 = 0;     On_Delay = Verdad;     Up_to_DOWN_ON();   }   Si ((On_Delay) Y (Seconds24 > Delay_ON_to_OFF) Y (Motion_Trigger_Up_to_Down))   {     Up_to_DOWN_OFF();     Motion_Trigger_Up_to_Down = Falso;     On_Delay = Falso;     Seconds24 = 0;   }
}

 

 

Les deseo mucha diversión reconstruyendo este proyecto y hasta la siguiente parte.

 

 

Für arduinoProjekte für fortgeschritteneSensoren

6 comentarios

Peter Wenk

Peter Wenk

Hallo Freunde im Blog,
ich habe mir die Treppenbeleuchtung auf dem Steckbrett nachgebaut und es funktioniert wunderbar.
Jetzt würde ich gern die helligkeit aller leds reduzieren. Es müsste doch über die PWM Taktung funktionieren also nicht mit 100% sondern nach wunsch nur 50% Taktung.
Kann mir einer helfen wie ich den Skretch umschreiben muss?
Würde mich über Hilfe freuen.
LG
Peter

Maik

Maik

@Thomas
Realisiere das doch mit einer separaten Steuerung, dann kannst Du dir den Flur nach deinen Wünschen ausleuchten.

Strotty

Strotty

Hallo,

ich bekomme bei ISR folgende Fehlermeldung:
exit status 1
expected unqualified-id before string constant
kann mir jemand einen Tipp geben?

Thomas

Thomas

Das Treppenlicht ist eine wirklich tolle Idee, mit der ich schon viele Jahre liebäugele. Aber wie es immer so ist, das, was man sucht, findet man dann doch in der Form nicht und sich zu kompletter Eigenentwicklung aufzuraffen bleibt bei mir meist auf der Strecke. Ich habe nun auch mit dem Kommentar bis zum 2. Teil gewartet, da mir im 1. Teil die Beschränkung auf die eine „Einschaltrichtung“ auffiel und die erwartungsgemäß nun ergänzt wurde. Jetzt würde ich gerne meine Idee anbringen, die mit dem Rettungsdienst-Kommentar von Wolfgang konform geht:
Unser Flur im 1. OG ist nachts erbärmlich dunkel und auf dem Weg durch den Flur auch ohne Treppenbenutzung wäre es super, wenn eben am oberen Ende der Treppe die Beleuchtung der obersten Stufe mit einem zusätzlichen (dritten) Sensor verbunden wäre, der eben nur die eine Stufe schaltet, wenn sich jemand oben im Flur bewegt. Damit hat man dann nachts ausreichend Orientierung im Flur und es ist als Funktion abgegrenzt von der Treppenbenutzung. Aber die Stufe sollte trotzdem wie in der beschriebenen Lösung integriert bleiben.
Ein Ausschalten am Ende des „Treppenganges“ wäre für mich nicht sinnvoll, da es wegen mehrerer Bewohner und Hund zwangsläufig zu Situation kommen wird, wo jemand dann im Dunklen auf der Treppe steht.

Markus

Markus

Was ist wenn ich mir auf der hälfte der Treppe einfällt ich muss noch mal runter ?

Wolfgang Hauf

Wolfgang Hauf

Hi,
du hast in der ersten Zeile die “#” vergessen !!

Deja un comentario

Todos los comentarios son moderados antes de ser publicados