Autor Thema: FB Ampelsteuerung (ST)  (Gelesen 742 mal)

Offline radar17892

  • Full Member
  • ***
  • Beiträge: 425
  • Think easy!
FB Ampelsteuerung (ST)
« am: März 19, 2017, 13:59:16 Nachmittag »
Hallo,
mal ein Projekt für die Ampelfans unter euch, die hier ab und zu mal auftauchen.  ;)
Ich habe das mal geschrieben um ST zu lernen.
Dachte, warum das ganze als Beispiel nicht weitergeben.

Die globalen Variablen:
VAR_GLOBAL
(*Ampelsteuerung*)
Arr_Schrittzeiten: ARRAY [0..9] OF BYTE := 5, 50, 20, 100, 40, 40, 100, 50, 70,10;
(*Schrittzeiten in 0,1s*)
i_AktSchritt : INT; (*aktiver Schritt*)
init: BOOL;
St_Ampel01 :St_Ampel; (*Bekanntgabe Struktur*)
x_FG_HMI :BOOL; (*VisuTaster Anforderung*)
x_FG_Taster AT %IX0.0 :BOOL; (*Taster Anforderung*)

x_FW_AmpROT AT %QX0.0 :BOOL; (*Ampel Fahrweg ROT *)
x_FW_AmpGELB AT %QX0.1 :BOOL; (*Ampel Fahrweg GELB *)
x_FW_AmpGRUEN AT %QX0.2 :BOOL; (*Ampel Fahrweg GRUEN *)
x_FG_AmpROT AT %QX0.3 :BOOL; (*Ampel Fussgänger ROT *)
x_FG_AmpGRUEN AT %QX0.4 :BOOL; (*Ampel Fussgänger GRUEN *)

END_VAR

Die angelegte Stuktur:
TYPE St_Ampel :
STRUCT
x_FWAmpROT :BOOL; (*Ampel Fahrweg ROT *)
x_FWAmpGELB :BOOL; (*Ampel Fahrweg GELB *)
x_FWAmpGRUEN :BOOL; (*Ampel Fahrweg GRUEN *)
x_FGAmpROT :BOOL; (*Ampel Fussgänger ROT *)
x_FGAmpGRUEN :BOOL; (*Ampel Fussgänger GRUEN *)
x_Trans : BOOL;

i_Schritt : INT;
i_Timer_ET01 :INT;
END_STRUCT
END_TYPE

Der FB:
FUNCTION_BLOCK FB_Ampel
(*
##############################################################
Programmbeschreibung:
Entwurf für eine Fussgängerampel mit einer CASE- Anweisung als Schrittkette
-automatische Initialisierung mit Blinken,
-kleiner Visu zum testen
es wird nur ein Timer verwendet, der mit verschiedenen Zeiten geladen wird
getestet: nur in der Simulation, aber OK
##############################################################
Änderungsindex
Name:TL Version:0.1 Datum: 06.06.2012 Grund: neu

##############################################################
*)
VAR_INPUT
x_Init: BOOL; (*Initbefehl*)
x_Anforderung :BOOL; (*Taster FG*)
Arr_Zeiten: ARRAY [0..9] OF BYTE; (*Schaltzeiten in Sec*)
END_VAR
VAR_OUTPUT
x_FW_ROT :BOOL; (*Ampel Fahrweg ROT *)
x_FW_GELB :BOOL; (*Ampel Fahrweg GELB *)
x_FW_GRUEN :BOOL; (*Ampel Fahrweg GRUEN *)
x_FG_ROT :BOOL; (*Ampel Fussgänger ROT *)
x_FG_GRUEN :BOOL; (*Ampel Fussgänger GRUEN *)
x_Trans : BOOL; (*Umschaltflanke "nächster Schritt"*)
i_Schritt : INT; (*Schrittnummer*)
i_ET_Schritt01s :INT; (*abgelaufene Schrittzeit in 0,1s*)
END_VAR
VAR
Steptimer : TON ;
Blinker: BLINK; (*Blinktakt*)
x_FrgTimer : BOOL;
Stepzeit: TIME := t#1s;
Blinkzeit: TIME := t#500ms;
i_Schritt_alt : INT;
b_Status_akt: BYTE; (*0= rt_FG; 1= gn_FG; 3= rt_FW; 4= ge_FW; 5= gn_FW; *)
x_ErrStep: BOOL; (*Fehler ungültige Schrittnummer*)

END_VAR

############################################################################


CASE i_Schritt OF
0: (* Initialisierung *)
i_Schritt := 1;
b_Status_akt := 0;
1: (*Sicherheit nach Initialisierung  ACHTUNG *)
x_FrgTimer := NOT x_Trans;
IF Steptimer.Q THEN
i_Schritt := 2;
END_IF
IF Blinker.OUT THEN b_Status_akt := 2#00010001;
ELSE b_Status_akt := 2#00000000;
END_IF
2: (*Sicherheit nach Initialisierung  STOP ALLE *)
x_FrgTimer := NOT x_Trans;
IF Steptimer.Q THEN
i_Schritt := 3;
END_IF
b_Status_akt := 2#00001001;
3: (* Start ROT / ROT normales Programm *)
x_FrgTimer := NOT x_Trans;
IF Steptimer.Q THEN
i_Schritt := 4;
END_IF
b_Status_akt := 2#00001001;
4: (* Start GELB / ROT *)
x_FrgTimer := NOT x_Trans;
IF Steptimer.Q THEN
i_Schritt := 5;
x_FrgTimer := FALSE;
END_IF
b_Status_akt := 2#00010001;
5: (* Phase GRUEN  warten bis Anforderung *)
IF x_Anforderung THEN
x_FrgTimer := TRUE;
ELSE ;
END_IF
IF Steptimer.Q THEN
x_FrgTimer := FALSE;
i_Schritt := 6;
END_IF
b_Status_akt := 2#00100001;
6: (* Phase GELB  Fahrzeuge *)
x_FrgTimer := NOT x_Trans;
IF Steptimer.Q THEN
i_Schritt := 7;
END_IF
b_Status_akt := 2#00010001;
7: (* ROT Fahrzeuge / GRUEN Fussgänger *)
x_FrgTimer := NOT x_Trans;
IF Steptimer.Q THEN
i_Schritt := 8;
END_IF
b_Status_akt := 2#00001010;
8: (*ROT Fahrzeuge / GRUEN blinken Fussgänger *)
x_FrgTimer := NOT x_Trans;
IF Steptimer.Q THEN
i_Schritt := 9;
END_IF
IF Blinker.OUT THEN b_Status_akt := 2#00001010;
ELSE b_Status_akt := 2#00001000;
END_IF
9: (* ROT Fahrzeuge / ROT Fussgänger *)
x_FrgTimer := NOT x_Trans;
IF Steptimer.Q THEN
i_Schritt := 3;
END_IF
b_Status_akt := 2#00001001;
ELSE
x_ErrStep := TRUE;
END_CASE
(*Initialisierung von aussen*)
IF x_Init THEN
i_Schritt := 0;
x_FrgTimer := FALSE;
x_ErrStep := FALSE;
END_IF
(* Schrittdaten laden*)
Stepzeit := (BYTE_TO_TIME (Arr_Zeiten[i_Schritt]) *100);
(*Umschaltflanke "nächster Schritt" erzeugen*)
IF i_Schritt <> i_Schritt_alt THEN
x_Trans := TRUE;
ELSE x_Trans := FALSE;
END_IF
i_Schritt_alt := i_Schritt;
(*Schrittimer mit Zeiten aus Array  steuern*)
Steptimer(IN:= (x_FrgTimer AND NOT x_Trans) , PT:= Stepzeit , Q=> , ET=> );
i_ET_Schritt01s := TIME_TO_INT(Steptimer.ET / 100);
(*Blinktakt erzeugen*)
Blinker(ENABLE:= (i_Schritt = 1) OR (i_Schritt = 8), TIMELOW:= Blinkzeit, TIMEHIGH:= Blinkzeit, OUT=> );
(*Ausgänge zuweisen*)
x_FG_ROT := b_Status_akt.0;
x_FG_GRUEN := b_Status_akt.1;
x_FW_ROT := b_Status_akt.3;
x_FW_GELB := b_Status_akt.4;
x_FW_GRUEN := b_Status_akt.5;

have a lot of fun!
Weil Einfach einfach Einfach ist!