FUNCTION FC 40 : VOID
TITLE =
VERSION : 0.1
VAR_INPUT
EW : WORD ;
END_VAR
VAR_OUTPUT
MW : WORD ;
END_VAR
BEGIN
NETWORK
TITLE =
L #EW;
T #MW;
NOP 0;
END_FUNCTION
ORGANIZATION_BLOCK OB 1
TITLE = Hauptprogramm
AUTHOR : KAI
FAMILY : SPSFORUM
NAME : SEGMENT
VERSION : 1.0
VAR_TEMP
OB1_EV_CLASS : BYTE ; //Bits 0-3 = 1 (Coming event), Bits 4-7 = 1 (Event class 1)
OB1_SCAN_1 : BYTE ; //1 (Cold restart scan 1 of OB 1), 3 (Scan 2-n of OB 1)
OB1_PRIORITY : BYTE ; //Priority of OB Execution
OB1_OB_NUMBR : BYTE ; //1 (Organization block 1, OB1)
OB1_RESERVED_1 : BYTE ; //Reserved for system
OB1_RESERVED_2 : BYTE ; //Reserved for system
OB1_PREV_CYCLE : INT ; //Cycle time of previous OB1 scan (milliseconds)
OB1_MIN_CYCLE : INT ; //Minimum cycle time of OB1 (milliseconds)
OB1_MAX_CYCLE : INT ; //Maximum cycle time of OB1 (milliseconds)
OB1_DATE_TIME : DATE_AND_TIME ; //Date and time OB1 started
END_VAR
BEGIN
NETWORK
TITLE =
CALL FC 40 (
EW := PEW 752,
MW := MW 10);
NOP 0;
NETWORK
TITLE =
CALL FC 40 (
EW := PEW 754,
MW := MW 12);
NOP 0;
END_ORGANIZATION_BLOCK
Variablen im Temp-Bereich sind nur für einen Aufruf gültig,
da eine Mittelwertbildung ja Werte über mehrere Zyklen erfordert,
ist das mit Variablen im TEMP Bereich definitiv nicht zu machen.
Oder nur mit diversen Effekten.
Manuel bin ich, er der fragt nennt sich mzva.
Mfg
Manuel
NW1
U #start
SPBN goon
NW2
//put PEW in pointer format
L #PEW
SLD 3
T #pPEW
NW3
L PEW [#pPEW]
T #PEW_int
NW4
// PEW to real
L #PEW_int
ITD
DTR
T #PEW_value_real
// increase quantity
L #quantity
L 1
+I
T #quantity
// integer to real for calc
L #quantity
ITD
DTR
T #quantity_real
NW5
// value-last average
L #PEW_value_real
L #last_average_real
-R
// divide by quantity
L #quantity_real
/R
// result + last average
L #last_average_real
+R
T #average
// result to last average
L #average
T #last_average_real
NW6
goon: NOP 0
CALL "average_value"
start :="measure_02_in_op"
init :="init_calc_values"
PEW :=280
average :="data_log".current_ST29
quantity :="data_log".quantity_values_ST29
min_value:="data_log".min_current_ST29
max_value:="data_log".max_current_ST29
Code:NW1 U #start SPBN goon NW2 //put PEW in pointer format L #PEW SLD 3 T #pPEW NW3 L PEW [#pPEW] T #PEW_int NW4 // PEW to real L #PEW_int ITD DTR T #PEW_value_real // increase quantity L #quantity L 1 +I T #quantity // integer to real for calc L #quantity ITD DTR T #quantity_real NW5 // value-last average L #PEW_value_real [COLOR=red]L #last_average_real[/COLOR] -R // divide by quantity L #quantity_real /R // result + last average [COLOR=red]L #last_average_real[/COLOR] +R T #average // result to last average L #average [COLOR=red]T #last_average_real[/COLOR] NW6 goon: NOP 0
FUNCTION "average_value" : VOID
TITLE =
//average=last average+((value-last average)/quantity)
AUTHOR : mz
VERSION : 0.1
VAR_INPUT
start : BOOL ;
init : BOOL ;
PEW : INT ;
END_VAR
VAR_OUTPUT
average : REAL ;
quantity : INT ;
min_value : REAL ;
max_value : REAL ;
END_VAR
VAR_TEMP
pPEW : DINT ;
PEW_int : INT ;
PEW_value_real : REAL ;
last_average_real : REAL ;
quantity_real : REAL ;
END_VAR
BEGIN
NETWORK
TITLE =
U #start;
SPBN goon;
NETWORK
TITLE =
//change PEW with 2x 2x 2x (=8) to pointer format
//load PEW, 32bit, real
//put PEW in pointer format
L #PEW;
SLD 3;
T #pPEW;
NETWORK
TITLE =
L PEW [#pPEW];
T #PEW_int;
NETWORK
TITLE =
//values to real format
// PEW to real
L #PEW_int;
ITD ;
DTR ;
T #PEW_value_real;
// increase quantity
L #quantity;
L 1;
+I ;
T #quantity;
//
// integer to real for calc
L #quantity;
ITD ;
DTR ;
T #quantity_real;
NETWORK
TITLE =
//average=last average+((PEW_value-last average)/quantity)
// value-last average
L #PEW_value_real;
L #last_average_real;
-R ;
// divide by quantity
L #quantity_real;
/R ;
// result + last average
L #last_average_real;
+R ;
T #average;
// result to last average
L #average;
T #last_average_real;
NETWORK
TITLE =
//check min value
L #PEW_value_real;
L #min_value;
<R ;
SPB min;
SPA jp;
NETWORK
TITLE =
//adjust min value
min: L #PEW_value_real;
T #min_value;
NETWORK
TITLE =
//check max value
jp: L #PEW_value_real;
L #max_value;
>R ;
SPB max;
SPA nojp;
NETWORK
TITLE =
//adjust max value
max: L #PEW_value_real;
T #max_value;
NETWORK
TITLE =
nojp: NOP 0;
SPA goon;
NETWORK
TITLE =
goon: U #init;
SPB init;
SPA done;
NETWORK
TITLE =
//reset values
init: L 0;
// T #PEW_value_real
// T #last_average_real
// T #quantity_real
// T #average
T #quantity;
L 3.402823e+038;
T #min_value;
L -3.402823e+038;
T #max_value;
NETWORK
TITLE =
done: NOP 0;
END_FUNCTION
Danke an alle, Kai hast recht mit last average, werd ich wohl dann als In/Out anlegen.
Dies erklaert aber noch nicht mein eigentliches Problem. Der FC nimmt nur ein und denselben PEW wert zum rechnen.
mzva
die Ausgänge einer Funktion müssen bei jedem Aufruf der Funktion beschrieben werden! Du überspringst die Zuweisungen bedingt. Bei einem FB ginge das, bei einer FC nicht!
FUNCTION FC 40 : VOID
TITLE =
VERSION : 0.1
VAR_INPUT
PEW : INT ;
START : BOOL ;
END_VAR
VAR_OUTPUT
MW : WORD ;
END_VAR
VAR_TEMP
pPEW : DINT ;
END_VAR
BEGIN
NETWORK
TITLE =
U #START;
SPBN GOON;
L #PEW;
SLW 3;
T #pPEW;
L PEW [#pPEW];
T #MW;
GOON: NOP 0;
END_FUNCTION
ORGANIZATION_BLOCK OB 1
TITLE = Hauptprogramm
AUTHOR : KAI
FAMILY : SPSFORUM
NAME : SEGMENT
VERSION : 1.0
VAR_TEMP
OB1_EV_CLASS : BYTE ; //Bits 0-3 = 1 (Coming event), Bits 4-7 = 1 (Event class 1)
OB1_SCAN_1 : BYTE ; //1 (Cold restart scan 1 of OB 1), 3 (Scan 2-n of OB 1)
OB1_PRIORITY : BYTE ; //Priority of OB Execution
OB1_OB_NUMBR : BYTE ; //1 (Organization block 1, OB1)
OB1_RESERVED_1 : BYTE ; //Reserved for system
OB1_RESERVED_2 : BYTE ; //Reserved for system
OB1_PREV_CYCLE : INT ; //Cycle time of previous OB1 scan (milliseconds)
OB1_MIN_CYCLE : INT ; //Minimum cycle time of OB1 (milliseconds)
OB1_MAX_CYCLE : INT ; //Maximum cycle time of OB1 (milliseconds)
OB1_DATE_TIME : DATE_AND_TIME ; //Date and time OB1 started
END_VAR
BEGIN
NETWORK
TITLE =
CALL FC 40 (
PEW := 752,
START := E 0.0,
MW := MW 10);
NETWORK
TITLE =
CALL FC 40 (
PEW := 754,
START := E 0.1,
MW := MW 12);
END_ORGANIZATION_BLOCK
Code:FUNCTION "average_value" : VOID TITLE = //average=last average+((value-last average)/quantity) AUTHOR : mz VERSION : 0.1 VAR_INPUT start : BOOL ; init : BOOL ; PEW : INT ; END_VAR [COLOR=red]VAR_OUTPUT[/COLOR] average : REAL ; [COLOR=red]quantity : INT[/COLOR] ; min_value : REAL ; max_value : REAL ; END_VAR VAR_TEMP pPEW : DINT ; PEW_int : INT ; PEW_value_real : REAL ; last_average_real : REAL ; quantity_real : REAL ; END_VAR BEGIN NETWORK TITLE = U #start; SPBN goon; NETWORK TITLE = //change PEW with 2x 2x 2x (=8) to pointer format //load PEW, 32bit, real //put PEW in pointer format L #PEW; SLD 3; T #pPEW; NETWORK TITLE = L PEW [#pPEW]; T #PEW_int; NETWORK TITLE = //values to real format // PEW to real L #PEW_int; ITD ; DTR ; T #PEW_value_real; // increase quantity [COLOR=red]L #quantity[/COLOR]; L 1; +I ; [COLOR=red]T #quantity;[/COLOR] // // integer to real for calc [COLOR=red]L #quantity[/COLOR]; ITD ; DTR ; T #quantity_real; NETWORK TITLE = //average=last average+((PEW_value-last average)/quantity) // value-last average L #PEW_value_real; L #last_average_real; -R ; // divide by quantity L #quantity_real; /R ; // result + last average L #last_average_real; +R ; T #average; // result to last average L #average; T #last_average_real; NETWORK TITLE = //check min value L #PEW_value_real; L #min_value; <R ; SPB min; SPA jp; NETWORK TITLE = //adjust min value min: L #PEW_value_real; T #min_value; NETWORK TITLE = //check max value jp: L #PEW_value_real; L #max_value; >R ; SPB max; SPA nojp; NETWORK TITLE = //adjust max value max: L #PEW_value_real; T #max_value; NETWORK TITLE = nojp: NOP 0; SPA goon; NETWORK TITLE = goon: U #init; SPB init; SPA done; NETWORK TITLE = //reset values init: L 0; // T #PEW_value_real // T #last_average_real // T #quantity_real // T #average [COLOR=red]T #quantity[/COLOR]; L 3.402823e+038; T #min_value; L -3.402823e+038; T #max_value; NETWORK TITLE = done: NOP 0; END_FUNCTION
Also bei meinem FC funktioniert das Überspringen der Ausgangszuweisung ohne Probleme.
E0.0=1 -> MW10 = PEW572
E0.0=0 -> MW10 = letzter Wert, wird nicht aktualisiert
E0.1=1 -> MW12 = PEW574
E0.1=0 -> MW12 = letzter Wert, wird nicht aktualisiert
"Ueberlaufen" sollte nicht (real).
Ok, unter Umständen, wie auch in deinem Beispiel, wird es funktionieren.Also bei meinem FC funktioniert das Überspringen der Ausgangszuweisung ohne Probleme...
We use cookies and similar technologies for the following purposes:
Do you accept cookies and these technologies?
We use cookies and similar technologies for the following purposes:
Do you accept cookies and these technologies?