Step 7 Timer selbst programmieren

DrGonzo

Level-2
Beiträge
37
Reaktionspunkte
2
Zuviel Werbung?
-> Hier kostenlos registrieren
Hallo,

nach langem Hin und Her hab ich mich doch entschieden meine Frage hier im Forum zu stellen da ich selbst nicht mehr weiterkommen.

Ich habe eine Zeitfunktion selbst erstellt, bzw will sie selbst erstellen, was auch bedingt funktioniert.

U #SET
FP #hm1
SPB RUN

L #ZEIT
T #ZEIT_OUT
U #Q
R #Q
SAVE
BEA

RUN: U #TAKT
FP #hm2
L #ZEIT_OUT
L 1
-D
T #ZEIT_OUT
L #ZEIT_OUT
L 0
<D
SPBN ENDE
L 0
T #ZEIT_OUT

ENDE: L 0
L #ZEIT_OUT
==D
= #Q
SAVE

kurze Erklärung:

Auf "TAKT" leg ich den Taktmerker der Baugruppe .5
"SET" setzt die Zeit und lässt sie ablaufen
ZEIT und ZEIT_OUT sind DINT
Q wird gesetzt sobald ZEIT<0

Solang einer dieser Timer läuft ist alles kein Problem, sobald ich aber einen dazuschalte der paralell ablaufen soll werden beide Timer auf den Anfangszeitwert zurückgesetzt und bleiben stehn.

Ich programmier noch nicht allzu lange und es ist auch vielmehr zum lernen gedacht als zum einsetzen in ein Anwenderprogramm da es ja mit S7 Timern schon gute gibt. Ich einfach mal wissen ob ich irgendwas vergessen hab bezüglich Sprüngen und Schleifen.

Zusätzlich zählt der Timer immer eine Sekunde weniger als gewünscht.

Ich bin mit meinem Gehirnschmalz am Ende, villeicht hat einer ein paar nützliche Tipps. Danke!


MFG Gonzo
 
Da wirst du erstmal die Deklaration deiner Hilfsvariablen in deinem FB sowie ein Beispiel des Aufrufs von 2 FBs bei denen dein Problem auftritt....

Noch ne Frage müsste es bei Zeile 3 nicht SPBN heißen?
 
Zuviel Werbung?
-> Hier kostenlos registrieren
Durch die Flanke vor SPB RUN wird das Sprungziel RUN: nur jeweils einen Zyklus lang bearbeitet...
Lade und Transferoperationen werden unabhängig vom VKE durchgeführt.
Daher wird das was hinter RUN: steht jeden Zyklus komplett bearbeitet.
Ein ändern auf SPBN oder das enfernen der Flanke bewirkt nur das der "Zähler im Bruchteil einer Sekunde auf Null steht...
Ist das wirklich der korrekte Code den du schon einmal getestet hast?

Gruß, Toki
 
Die ersten Zeilen sollen den Timer im ersten Zyklus initialisieren indem er den Zeitwert auf die Variable lädt (die dann runterzählt) und nochmal sicherheitshalber den Ausgang rücksetzt, bevor er dann den FB mit BEA verlässt.

Im Moment wird der Rest vom FB durch das SPB aber nur im Falle der Flanke abgearbeitet. Ein ändern auf SpBN sollte also insofern schon stimmen.

Mit der fehlenden Sprung Marke nach #hm2 und das der Timer so nicht funktionieren kann hat Tokio natürlich vollkommen recht.
 
Code:
U #Takt                   //Signal 1
FP Mx.x                   //Mx.x hat Signal 0
SPBN weit                //VKE hat 1, also wird der Sprung nicht durchgeführt

L #Dint_Zählerwert   // Subtraktion wird nur einmal durchlaufen...
L 1
-D
T #Dint_Zählerwert

weit: nop 0

So würde die Subtraktion des Zählerwertes nur im "Takt" durchgeführt werden.
Korrigiere mal nach diesem Schema deine Lade/Transferoperationen.
 
deine flanke sind temporär. das funktioniert nicht.
aber selbst wenn die in_out sind läuft der baustein nicht

Code:
FUNCTION "Time_SE_DB_V1.2" : VOID
TITLE = SE
AUTHOR : Lischnew
FAMILY : 'TIMER'
NAME : 'Time-SE'
VERSION : 1.2

VAR_INPUT
  Takt : BOOL ; //positive Flanke. Sinnvoll sind z.B. 0,1 Sek., 1 Sek oder 1 Minute. 
  Run : BOOL ; //Zeit läuft wenn dieses Bit 1-Signal hat. bei 0 wird die Zeit auf TW gesetzt 
  TW : INT ; //Zeitwert. 
END_VAR
VAR_OUTPUT
  Out : BOOL ; 
END_VAR
VAR_IN_OUT
  DW : INT ; //Datenwort in dem die Zeit gespeichert wird. (DW wird dekrementiert) 
END_VAR
BEGIN
NETWORK
TITLE =
      U     #Run; 
      SPB   RUN; 
      L     #TW; 
      T     #DW; 
      CLR   ; 
      =     #Out; 
      SAVE  ; 
      BEA   ; 
RUN:  UN    #Takt; 
      SPB   ENDE; 
      L     #DW; 
      L     1; 
      -I    ; 
      T     #DW; 
      L     #DW; 
      L     0; 
      >I    ; 
      SPB   OK; 
      L     0; 
      T     #DW; 
OK:   NOP   0; 
ENDE: L     0; 
      L     #DW; 
      ==I   ; 
      =     #Out; 
      SAVE  ; 
END_FUNCTION
FUNCTION "Time_SA_DB_V1.2" : VOID
TITLE = SA
AUTHOR : Lischnew
FAMILY : 'TIMER'
NAME : 'Time-SA'
VERSION : 1.2

VAR_INPUT
  Takt : BOOL ; //positive Flanke. Sinnvoll sind z.B. 0,1 Sek., 1 Sek oder 1 Minute. 
  Run : BOOL ; //Zeit läuft wenn dieses Bit 1-Signal hat. bei 0 wird die Zeit auf TW gesetzt 
  TW : INT ; //Zeitwert. 
  Reset : BOOL ; //Zeit zurücksetzen
END_VAR
VAR_OUTPUT
  out : BOOL ; 
END_VAR
VAR_IN_OUT
  DW : INT ; //Datenwort in dem die Zeit gespeichert wird. (DW wird dekrementiert) 
END_VAR
BEGIN
NETWORK
TITLE = 
      U     #Run; 
      SPBN  RUN; 
      SAVE  ; 
      S     #out; 
      L     #TW; 
      T     #DW; 
RUN:  U     #Takt; 
      UN    #Run; 
      UN    #Reset; 
      SPBN  ENDE; 
      L     #DW; 
      L     1; 
      -I    ; 
      T     #DW; 
      L     #DW; 
      L     0; 
      >I    ; 
      SPB   OK; 
      L     0; 
      T     #DW; 
OK:   NOP   0; 
ENDE: L     0; 
      L     #DW; 
      <I    ; 
      =     #out; 
      UN    #Reset; 
      SPB   res; 
      L     0; 
      T     #DW; 
      CLR   ; 
      =     #out; 
res:  U     #out; 
      SAVE  ; 
END_FUNCTION
 
Zuletzt bearbeitet:
Zuviel Werbung?
-> Hier kostenlos registrieren
Selbst für Blödsinn wär ich im Moment empfänglich ;)

:EDIT: Hab das Programm mal auf ne reale CPU übertragen, beide Bausteine laufen nicht paralell. Sobald an beiden SET eine 1 liegt wird der Zeitwert zurück auf den Anfangswert gesetzt und läuft nicht weiter.
 
Zuletzt bearbeitet:
Ok der Baustein in deinem Projekt ist auf jeden Fall nicht der den du oben gepostet hast.
Du hast die Sprünge ergänzt.
Dein Fehler liegt sicherlich darin das du Temp-Variablen für deine Flanken genutzt hast...
Lege die mal auf globale Variablen.

Gruß, Toki
 
bei set kommt die positive flanke und es wird 1 mal nach run gesprungen.
ansonsten immer das nach dem spb. und da kommt dann das bea.

mach aus den flanken in_out variablen und aus dem spb ein spbn.

oder schau dir die beiden bausteine an die ich gepostet habe ist eine SE und eine SA zeit
 
Zuviel Werbung?
-> Hier kostenlos registrieren
Allerdings kommst du dann dahin wo ich eben schon war, dein Programm wird garnicht mehr abgearbeitet.
Siehe Post #3.
Nachdem du alle Flankenmerker ausgetauscht hast, nimm die obere Flanken mal wieder raus, dann hast auf jeden Fall eine Funktion die
bis Null runterzählt und den Ausgang schaltet.

Gruß, Toki
 
Es läuft!

Ein RiesenFEHLER wie mir jetzt auch auffällt ist es gewesen die Flankenmerker Temporär zu speichern da sie bei erneutem Aufruf des Bausteins ja weg sind.
Das hat anscheinend die ganze Struktur des Programms durcheinandergeworfen.

Danke für die hilfreichen Posts.
 
Zurück
Oben