Programmatore orario su pannelli Weintek

Il programmatore orario (o timer, schedulatore) è un dispositivo elettrico, elettronico, informatico o meccanico in grado di svolgere automaticamente una o più azioni a intervalli di tempo prefissati, consentendo l’entrata in funzione o l’arresto di apparecchi o congegni. Gran parte delle più comuni automazioni residenziali e commerciali è svolta dai programmatori orari per ottimizzare i consumi e facilitare l’attività giornaliera. Pertanto la scelta dipende soprattutto da cosa si vuole ottenere.

Su tutti i pannelli Weintek tramite l’oggetto Scheduler è implementata la possibilità di gestire più programmatori orari con impostazione oraria giornaliera e/o settimanale. In questo articolo vedremo come realizzare con EasyBuilderPro la gestione di un programmatore orario settimanale. L’oggetto Scheduler è molto versatile e inserendo in un progetto più oggetti è sicuramente possibile soddisfare tutte le esigenze. Ma a vantaggio dei programmatori più esperti e comunque per quelle applicazioni dove l’oggetto Scheduler non soddisfa tutte le esigenze nell’articolo realizziamo anche un esempio di schedulatore basato su macro. E’ possibile eseguire il download del programma dimostrativo che contiene tutti gli esempi riportato nell’articolo.

Panoramica pannelli Weintek

Programma HMIScheduler

Questo programma è stato ricavato da un esempio disponibile in download dal sito Weintek ho solo eseguito piccole modifiche nella parte grafica. Il programma uutilizza l’oggetto Scheduler e permette l’impostazione degli orari di attivazione e disattivazione ed i giorni della settimana cui si riferiscono. sul fronte di attivazione del tasto Update setting le impostazioni sono acquisite dallo scheduler (In caso di errore si attiva la lampada di notifica).

Al raggiungimento dell’orario impostato in Start time se il giorno corrisponde a quello selezionato si attiverà l’uscita Action e se è attivo il comando End Time al raggiungimento dell’orario impostato in End time l’uscita si disattiverà. Naturalmente se occorre avere più schedulazioni basterà inserire un oggetto Scheduler per ogni schedulazione e definire gli oggetti di impostazione dei valori.

Screenshot programma HMIScheduler

HMISchedulerByMacro

Dopo avere visto come utilizzare l’oggetto Scheduler per gestire un programmatore orario, vediamo come sia possibile grazie al potente linguaggio macro realizzare un programmatore orario settimanale direttamente da macro.

Nella pagina grafica avremo degli oggetti Numeric input che permettono l’impostazione degli orari che sono salvati in variabili RW_A e quindi sono mantenute allo spegnimento. Siccome la memorizzazione delle variabili è temporizzata il tasto Salva ne forza il salvataggio immediato.

La macro Scheduler eseguita ogni secondo confronta il valore di ora attuale con i valori impostati ed attiva il comando in base alle impostazioni effettuate, di seguito il listato della macro utilizzata.

Screenshot programma HMISchedulerByMacro
Macro “Scheduler”
macro_command main()

// ------------------------------------------------------------------------------
// DICHIARAZIONE VARIABILI
// ------------------------------------------------------------------------------
// Eseguo dichiarazione variabili.

bool Command=false //Comando
bool WeekFlag[7]={false, false, false, false, false, false, false} //Attivazioni (Lunedì -> Domenica)
short Dummy=0 //Variabile di appoggio
short Year=0, Month=0, Day=0, Hour=0, Minute=0, Second=0, WeekDay=0
int StartTime[7]={0, 0, 0, 0, 0, 0, 0} //Start time (S) (Lunedì -> Domenica)
int StopTime[7]={0, 0, 0, 0, 0, 0, 0} //Stop time (S) (Lunedì -> Domenica)
int TimeNow=0 //Valore ora attuale (S)

// ------------------------------------------------------------------------------
// LETTURA RTC
// ------------------------------------------------------------------------------
// Eseguo lettura valore RTC.

GetData(WeekDay, "Local HMI", LW, 9023, 1)
GetData(Year, "Local HMI", LW, 9022, 1)
GetData(Month, "Local HMI", LW, 9021, 1)
GetData(Day, "Local HMI", LW, 9020, 1)
GetData(Hour, "Local HMI", LW, 9019, 1)
GetData(Minute, "Local HMI", LW, 9018, 1)
GetData(Second, "Local HMI", LW, 9017, 1)

// Calcolo ora attuale in secondi

TimeNow=(Hour*3600)+(Minute*60)+Second //Valore ora attuale (S)

// ------------------------------------------------------------------------------
// LETTURA PROGRAMMAZIONI
// ------------------------------------------------------------------------------
// Eseguo lettura ora start, appoggio su variabile temporanea per calcolo.

GetData(Dummy, "Local HMI", RW_A, 100, 1) //Start ora (Lunedi)
StartTime[0]=Dummy //Start time (S) (Lunedi)
GetData(Dummy, "Local HMI", RW_A, 101, 1) //Start minuti (Lunedi)
StartTime[0]=(StartTime[0]*3600)+(Dummy*60) //Start time (S) (Lunedi)
GetData(Dummy, "Local HMI", RW_A, 102, 1) //Start secondi (Lunedi)
StartTime[0]=StartTime[0]+Dummy //Start time (S) (Lunedi)

GetData(Dummy, "Local HMI", RW_A, 103, 1) //Start ora (Martedi)
StartTime[1]=Dummy //Start time (S) (Martedi)
GetData(Dummy, "Local HMI", RW_A, 104, 1) //Start minuti (Martedi)
StartTime[1]=(StartTime[1]*3600)+(Dummy*60) //Start time (S) (Martedi)
GetData(Dummy, "Local HMI", RW_A, 105, 1) //Start secondi (Martedi)
StartTime[1]=StartTime[1]+Dummy //Start time (S) (Martedi)

GetData(Dummy, "Local HMI", RW_A, 106, 1) //Start ora (Mercoledi)
StartTime[2]=Dummy //Start time (S) (Mercoledi)
GetData(Dummy, "Local HMI", RW_A, 107, 1) //Start minuti (Mercoledi)
StartTime[2]=(StartTime[2]*3600)+(Dummy*60) //Start time (S) (Mercoledi)
GetData(Dummy, "Local HMI", RW_A, 108, 1) //Start secondi (Mercoledi)
StartTime[2]=StartTime[2]+Dummy //Start time (S) (Mercoledi)

GetData(Dummy, "Local HMI", RW_A, 109, 1) //Start ora (Giovedi)
StartTime[3]=Dummy //Start time (S) (Giovedi)
GetData(Dummy, "Local HMI", RW_A, 110, 1) //Start minuti (Giovedi)
StartTime[3]=(StartTime[3]*3600)+(Dummy*60) //Start time (S) (Giovedi)
GetData(Dummy, "Local HMI", RW_A, 111, 1) //Start secondi (Giovedi)
StartTime[3]=StartTime[3]+Dummy //Start time (S) (Giovedi)

GetData(Dummy, "Local HMI", RW_A, 112, 1) //Start ora (Venerdi)
StartTime[4]=Dummy //Start time (S) (Venerdi)
GetData(Dummy, "Local HMI", RW_A, 113, 1) //Start minuti (Venerdi)
StartTime[4]=(StartTime[4]*3600)+(Dummy*60) //Start time (S) (Venerdi)
GetData(Dummy, "Local HMI", RW_A, 114, 1) //Start secondi (Venerdi)
StartTime[4]=StartTime[4]+Dummy //Start time (S) (Venerdi)

GetData(Dummy, "Local HMI", RW_A, 115, 1) //Start ora (Sabato)
StartTime[5]=Dummy //Start time (S) (Sabato)
GetData(Dummy, "Local HMI", RW_A, 116, 1) //Start minuti (Sabato)
StartTime[5]=(StartTime[5]*3600)+(Dummy*60) //Start time (S) (Sabato)
GetData(Dummy, "Local HMI", RW_A, 117, 1) //Start secondi (Sabato)
StartTime[5]=StartTime[5]+Dummy //Start time (S) (Sabato)

GetData(Dummy, "Local HMI", RW_A, 118, 1) //Start ora (Domenica)
StartTime[6]=Dummy //Start time (S) (Domenica)
GetData(Dummy, "Local HMI", RW_A, 119, 1) //Start minuti (Domenica)
StartTime[6]=(StartTime[6]*3600)+(Dummy*60) //Start time (S) (Domenica)
GetData(Dummy, "Local HMI", RW_A, 120, 1) //Start secondi (Domenica)
StartTime[6]=StartTime[6]+Dummy //Start time (S) (Domenica)

// Eseguo lettura ora stop, appoggio su variabile temporanea per calcolo.

GetData(Dummy, "Local HMI", RW_A, 130, 1) //Stop ora (Lunedi)
StopTime[0]=Dummy //Stop time (S) (Lunedi)
GetData(Dummy, "Local HMI", RW_A, 131, 1) //Stop minuti (Lunedi)
StopTime[0]=(StopTime[0]*3600)+(Dummy*60) //Stop time (S) (Lunedi)
GetData(Dummy, "Local HMI", RW_A, 132, 1) //Stop secondi (Lunedi)
StopTime[0]=StopTime[0]+Dummy //Stop time (S) (Lunedi)

GetData(Dummy, "Local HMI", RW_A, 133, 1) //Stop ora (Martedi)
StopTime[1]=Dummy //Stop time (S) (Martedi)
GetData(Dummy, "Local HMI", RW_A, 134, 1) //Stop minuti (Martedi)
StopTime[1]=(StopTime[1]*3600)+(Dummy*60) //Stop time (S) (Martedi)
GetData(Dummy, "Local HMI", RW_A, 135, 1) //Stop secondi (Martedi)
StopTime[1]=StopTime[1]+Dummy //Stop time (S) (Martedi)

GetData(Dummy, "Local HMI", RW_A, 136, 1) //Stop ora (Mercoledi)
StopTime[2]=Dummy //Stop time (S) (Mercoledi)
GetData(Dummy, "Local HMI", RW_A, 137, 1) //Stop minuti (Mercoledi)
StopTime[2]=(StopTime[2]*3600)+(Dummy*60) //Stop time (S) (Mercoledi)
GetData(Dummy, "Local HMI", RW_A, 138, 1) //Stop secondi (Mercoledi)
StopTime[2]=StopTime[2]+Dummy //Stop time (S) (Mercoledi)

GetData(Dummy, "Local HMI", RW_A, 139, 1) //Stop ora (Giovedi)
StopTime[3]=Dummy //Stop time (S) (Giovedi)
GetData(Dummy, "Local HMI", RW_A, 140, 1) //Stop minuti (Giovedi)
StopTime[3]=(StopTime[3]*3600)+(Dummy*60) //Stop time (S) (Giovedi)
GetData(Dummy, "Local HMI", RW_A, 141, 1) //Stop secondi (Giovedi)
StopTime[3]=StopTime[3]+Dummy //Stop time (S) (Giovedi)

GetData(Dummy, "Local HMI", RW_A, 142, 1) //Stop ora (Venerdi)
StopTime[4]=Dummy //Stop time (S) (Venerdi)
GetData(Dummy, "Local HMI", RW_A, 143, 1) //Stop minuti (Venerdi)
StopTime[4]=(StopTime[4]*3600)+(Dummy*60) //Stop time (S) (Venerdi)
GetData(Dummy, "Local HMI", RW_A, 144, 1) //Stop secondi (Venerdi)
StopTime[4]=StopTime[4]+Dummy //Stop time (S) (Venerdi)

GetData(Dummy, "Local HMI", RW_A, 145, 1) //Stop ora (Sabato)
StopTime[5]=Dummy //Stop time (S) (Sabato)
GetData(Dummy, "Local HMI", RW_A, 146, 1) //Stop minuti (Sabato)
StopTime[5]=(StopTime[5]*3600)+(Dummy*60) //Stop time (S) (Sabato)
GetData(Dummy, "Local HMI", RW_A, 147, 1) //Stop secondi (Sabato)
StopTime[5]=StopTime[5]+Dummy //Stop time (S) (Sabato)

GetData(Dummy, "Local HMI", RW_A, 148, 1) //Stop ora (Domenica)
StopTime[6]=Dummy //Stop time (S) (Domenica)
GetData(Dummy, "Local HMI", RW_A, 149, 1) //Stop minuti (Domenica)
StopTime[6]=(StopTime[6]*3600)+(Dummy*60) //Stop time (S) (Domenica)
GetData(Dummy, "Local HMI", RW_A, 150, 1) //Stop secondi (Domenica)
StopTime[6]=StopTime[6]+Dummy //Stop time (S) (Domenica)

// Lettura abilitazioni settimanali

GetData(WeekFlag[0], "Local HMI", RW_A_Bit, 101, 1) //Attivazione (Lunedi)
GetData(WeekFlag[1], "Local HMI", RW_A_Bit, 102, 1) //Attivazione (Martedi)
GetData(WeekFlag[2], "Local HMI", RW_A_Bit, 103, 1) //Attivazione (Mercoledi)
GetData(WeekFlag[3], "Local HMI", RW_A_Bit, 104, 1) //Attivazione (Giovedi)
GetData(WeekFlag[4], "Local HMI", RW_A_Bit, 105, 1) //Attivazione (Venerdi)
GetData(WeekFlag[5], "Local HMI", RW_A_Bit, 106, 1) //Attivazione (Sabato)
GetData(WeekFlag[6], "Local HMI", RW_A_Bit, 107, 1) //Attivazione (Domenica)

// ------------------------------------------------------------------------------
// CONTROLLO ATTIVAZIONE
// ------------------------------------------------------------------------------
// Il giorno della settimana da RTC è espresso nel modo
// Value range: 0 ~ 6, stand for Sunday ~ Saturday
// Mentre gli array di definizione sono espressi da Lunedi ~ Domenica

if (WeekDay == 0) then
    WeekDay=6
else
    WeekDay=WeekDay-1
end if

// Controllo se giorno della settimana attuale è attivo.

if (WeekFlag[WeekDay]) then

    // Attivo comando su tempo di start.

    if (TimeNow >= StartTime[WeekDay]) then
        Command=true
    end if

    // Disattivo comando su tempo di stop.
    
    if (TimeNow >= StopTime[WeekDay]) then
        Command=false
    end if
end if

// Aggiornamento comando

SetData(Command, "Local HMI", LB, 100, 1)
end macro_command

Usiamo uno SlimLine “HMISchedulerOnSlimLine”

Abbiamo visto come i terminali operatore possano gestire temporizzatori orari, ma effettuata la temporizzazione è necessario disporre di una uscita di comando quindi occorre che il terminale sia connesso ad I/O remoto od a un PLC. Ma se si utilizza un PLC (Ad esempio uno SlimLine come questo) perchè non gestire le temporizzazioni direttamente con il PLC delegando al terminale la sola interfaccia utente, così la schedulazione è gestita anche a terminale spento.

Per l’esempio abbiamo utilizzato la stessa pagina di terminale vista nell’esempio precedente ma le impostazioni ora sono trasferite direttamente in variabili tamponate di tipo UINT del PLC. Un programma in linguaggio ST molto simile alla macro Scheduler vista precedentemente gestirà la schedulazione. Affinchè il valore di Data/Ora visualizzato sul pannello coincida con quello del PLC occorre testare l’esempio su di un pannello reale e non in simulazione su PC.

Programma LogicLab “Scheduler”
PROGRAM Scheduler
VAR
    i : UDINT; (* Auxiliary counter *)
    TimeNow : UDINT; (* Actual time (S) *)
    WeekDay : USINT; (* Day of week (0:Moday - 6:Sunday) *)
    StartTime : ARRAY[0..6] OF UDINT; (* Start time (S) *)
    StopTime : ARRAY[0..6] OF UDINT; (* Stop time (S) *)
    EToDate : SysETimeToDate; (* Epoch time to date conversion *)
END_VAR

// *****************************************************************************
// PROGRAM "Scheduler"
// *****************************************************************************
// Program manages a weekly scheduler. The values can be set by a Weintek HMI.
// -----------------------------------------------------------------------------

    // -------------------------------------------------------------------------
    // DAY OF WEEK
    // -------------------------------------------------------------------------
    // Convert Epoch to Date/Time.

    EToDate(EpochTime:=SysDateTime); //Epoch time to date conversion
    IF NOT(EToDate.Done) THEN RETURN; END_IF;

    // WeekDay means 0:Sunday - 6:Saturday
    // The definition arrays are expressed 0:Monday - 6:Sunday
    // The WeekDay must be converted.

    IF (EToDate.WeekDay = 0) THEN
        WeekDay:=6; //Day of week (0:Moday - 6:Sunday)
    ELSE
        WeekDay:=EToDate.WeekDay-1; //Day of week (0:Moday - 6:Sunday)
    END_IF;

    // -------------------------------------------------------------------------
    // CHECK TIMES
    // -------------------------------------------------------------------------
    // Compares the time now with preset values and manage command.

    Command:=FALSE; //Output command    
    IF NOT(VBitTest(WDSelector, WeekDay)) THEN RETURN; END_IF;

    // Calculates the a start time.

    StartTime[0]:=(TO_UDINT(StartMondayH)*3600)+(StartMondayM*60)+StartMondayS;
    StartTime[1]:=(TO_UDINT(StartTuesdayH)*3600)+(StartTuesdayM*60)+StartTuesdayS;
    StartTime[2]:=(TO_UDINT(StartWednesdayH)*3600)+(StartWednesdayM*60)+StartWednesdayS;
    StartTime[3]:=(TO_UDINT(StartThursdayH)*3600)+(StartThursdayM*60)+StartThursdayS;
    StartTime[4]:=(TO_UDINT(StartFridayH)*3600)+(StartFridayM*60)+StartFridayS;
    StartTime[5]:=(TO_UDINT(StartSaturdayH)*3600)+(StartSaturdayM*60)+StartSaturdayS;
    StartTime[6]:=(TO_UDINT(StartSundayH)*3600)+(StartSundayM*60)+StartSundayS;

    // Calculates the a stop time.

    StopTime[0]:=(TO_UDINT(StopMondayH)*3600)+(StopMondayM*60)+StopMondayS;
    StopTime[1]:=(TO_UDINT(StopTuesdayH)*3600)+(StopTuesdayM*60)+StopTuesdayS;
    StopTime[2]:=(TO_UDINT(StopWednesdayH)*3600)+(StopWednesdayM*60)+StopWednesdayS;
    StopTime[3]:=(TO_UDINT(StopThursdayH)*3600)+(StopThursdayM*60)+StopThursdayS;
    StopTime[4]:=(TO_UDINT(StopFridayH)*3600)+(StopFridayM*60)+StopFridayS;
    StopTime[5]:=(TO_UDINT(StopSaturdayH)*3600)+(StopSaturdayM*60)+StopSaturdayS;
    StopTime[6]:=(TO_UDINT(StopSundayH)*3600)+(StopSundayM*60)+StopSundayS;

    // Manage command according time set.

    TimeNow:=MOD(SysDateTime, 86400); //Actual time (S)
    IF (TimeNow >= StartTime[WeekDay]) THEN Command:=TRUE; END_IF;
    IF (TimeNow >= StopTime[WeekDay]) THEN Command:=FALSE; END_IF;

// [End of file]
Was this article helpful?