Vai al contenuto
PLC Forum


In una FB puntare a una variabile array


Messaggi consigliati

Inserito:

Buongiorno a tutti

in un progetto step 7 per 300 ho creato un FB in cui ho generato nella parte STAT un array chiamata SG di 100 campi di tipo Real. ( indirizzo da 52.0 a 452.0)

in più ho creato sempre in STAT una variabile chiamata INDEX di tipo Dint. (Indirizzo 456)

 

ora vorrei semplicemente  al variare del valore di INDEX, (da 1 a 100) andare a leggere o scrivere il il valore contenuto nell'array corrispondente.

 

questa operazione l'ho già fatta sul 1500 con il tia e non ho avuto grossi problemi, ora il cliente, vuole aggiornare anche i vecchi programmi fatti con il 300, ho provato e riprovato, ma mi dà sempre errore, ho letto varie discussioni e anche alcune guide che ci sono sul forum, ma davvero non riesco a capire come devo scrivere queste (credo) semplici istruzioni.

grazie in anticipo per l'eventuale supporto.

 


Inserita:

zgDpwQ0.png

 

ow0EPfB.png

 

Questi screen credo siano già abbastanza chiari.

Comunque basta che ti leggi i dati LD, puntati ovviamente dove ti interessa.

Nell'esempio ho rispettato i tuoi vari offset, quindi SG che inizia a 52 e INDEX a 456.

 

Ciao! ;)

Inserita:

Il 300 purtroppo supporta quel tipo di indirizzamento solo in SCL.

Quindi, o fai una funzione in SCL e lavori direttamente con gli indici dell'array come nel 1200/1500, oppure devi passare all'uso dei puntatori in AWL.

Qui sotto metto due esempi, uno per la lettura e uno per la scrittura di valori dell'array usando i puntatori.

 

Esempio lettura valore dall'array

      LAR1  P##MyArray           // Carico nel registro indirizzi l'indirizzo di partenza dell'array
      L     #idVarArray          // Nr. variabile dell'array (0 = prima variabile)
      ITD                        // Converte da INT a DINT
      SLD   5                    // Sposta a sx di 5 posizioni perché l'array è costituito da variabili REAL (32 bit)
      +AR1                       // Somma indirizzo relativo della variabile al registro indirizzi
      L D [ AR1 , P#0.0 ]        // Leggi il valore della variabile dell'array
      T     #Value               // Scrivi il valore in "Value"

 

Esempio scrittura valore nell'array

      LAR1  P##MyArray           // Carico nel registro indirizzi l'indirizzo di partenza dell'array
      L     #idVarArray          // Nr. variabile dell'array (0 = prima variabile)
      ITD                        // Converte da INT a DINT
      SLD   5                    // Sposta a sx di 5 posizioni perché l'array è costituito da variabili REAL (32 bit)
      +AR1                       // Somma indirizzo relativo della variabile al registro indirizzi
      L     #Value               // Carica il vaklore da scrivere
      T D [ AR1 , P#0.0 ]        // Scrivi il valore nella variabile dell'array

 

Dove le variabili sono:
MyArray: Array di REAL

idVarArray: INT

Value: REAL

Inserita:

Perfetto, molto chiaro,  :clap:

 

ovvero all'interno del FB non devo utilizzare il simbolico che ho dato al gruppo array, ma vado a puntare all'area di memoria che corrisponde, giusto?

 

Perfetto grazie, domani provo (sono già dal cliente e con il fuso ho già finito)

 

una cosa però, nell'esempio i campi dell'array li hai "forzati" a mano per poi poterli leggere con il puntatore, se volessi anche scriverli con il puntatore credo che tutta la parte da "L #INDEX" in poi rimanga uguale tranne le ultime due righe che dovranno essere:

L MD2 ( o un'aria di memoria dove intendo appoggiare il valore che intendo scrivere

T LD [AR1, P#0.0]

 

corretto? 

Comunque grazie molto semplice ed esaustivo, spero di aver capito bene..:)

Inserita:

Scusate nel frattempo non avevo visto la risposta di batta

ok domani faccio un po' di prove comunque mi avete semplificato un po' l'argomento...

è tutta la mattina che leggo varie discussioni a riguardo...

 

grazie mille

 

Inserita:

Tieni presente che, nell'esempio di "DesmoGiec", l'array è nell'area delle variabili locali (TEMP).
Se il tuo array è nell'area STAT, al posto di LD devi scrivere DID.

 

Nel mio esempio invece ho scritto solo D (ad indicare che si tratta di una doppia word) senza specificare l'area dati, perché l'area dati è specificata nel registro indirizzi.

 

La mia idea però è che ti converrebbe fare tutto in SCL.

Inserita:

Ok grazie mille

mi sono già messo al lavoro, anche perchè poi nell'FB ci sono altri puntamenti da fare ( praticamente se il valore che sto scrivendo è inferiore di quelli sottostanti li dovrò forzare allo stesso valore, idem se il valore che sto scrivendo sarà maggiore di quelli posizionati sopra, praticamente dalla posizione 0 alla cento si devono avere valori sempre in ordine crescente) ma risolto l'inghippo di capire come scrivere il resto credo sia abbastanza semplice....

 

grazie mille ancora :worthy: mi avete fatto svoltare la giornata

Inserita:

Ciao a tutti,bazzico un pò con i plc, ******

 

 

*******

N. d. M.

 

Non ti puoi accodare ad un'altra discussione. Apri una discussione tua sull'argomento.

  • 3 months later...
ifachsoftware
Inserita:

Io per questi problemi userei l'SCL 

 

FUNCTION_BLOCK "Test"
{ S7_Optimized_Access := 'TRUE' }
VERSION : 0.1
   VAR_INPUT 
      Write : Bool;
      PosIndex : DInt := cMinIndex;
   END_VAR

   VAR_IN_OUT 
      Value : Real;
   END_VAR

   VAR RETAIN
      AryReal { ExternalAccessible := 'False'; ExternalVisible := 'False'; ExternalWritable := 'False'} : Array[#cMinIndex..#cMaxIndex] of Real;
      Index { ExternalAccessible := 'False'; ExternalVisible := 'False'; ExternalWritable := 'False'} : DInt;
   END_VAR

   VAR CONSTANT 
      cMinIndex : DInt := 1;
      cMaxIndex : DInt := 100;
   END_VAR


BEGIN
	IF #PosIndex < #cMinIndex OR #PosIndex > #cMaxIndex THEN
	    // Errore fuori dai limiti
	    RETURN;
	END_IF;
	
	IF #Write THEN
	    #AryReal[#PosIndex] := #Value;
	ELSE
	    #Value := #AryReal[#PosIndex];
	END_IF;
END_FUNCTION_BLOCK

 

Inserita:

Occhio alle date.;)

  • Livio Orsini locked this discussione
Ospite
Questa discussione è chiusa alle risposte.
×
×
  • Crea nuovo/a...