Transmitting a structure to the PLC with Delphi

Task

A structure is to be written into the PLC by the .NET application. The elements in the structure have different data types.

Description

The structure we want to write into the PLC:

TYPE PLCStruct
STRUCT
  intVal   : INT;  (*Offset 0*) 
  dintVal  : DINT; (*Offset 2*) 
  byteVal  : SINT; (*Offset 6*)  
  lrealVal : LREAL;(*Offset 7*) 
  realVal  : REAL; (*Offset 15 --> Total size 19 Bytes*) 
END_STRUCT
END_TYPE

 

The AdsStream object is initialized with a size of 19 bytes in the write event method. This is equivalent to the size of the data type PLCStruct in the SPS. A BinaryWriter is used to write the data from the textboxes to the stream. After setting the stream position to 0 the individual fields are written to the stream. Finally, the total stream is written into the SPS with the help of   TcAdsClient.Write.

 

 

Delphi Prism (Embarcadero Prism XE2, Oxygene for .NET) program

namespace Sample02;

interface

uses
  System.Drawing,
  System.Collections,
  System.Collections.Generic,
  System.Windows.Forms,
  System.ComponentModel, System.IO, TwinCAT.Ads;

type
  /// <summary>
  /// Summary description for MainForm.
  /// </summary>
  MainForm = partial class(System.Windows.Forms.Form)
  private
    method btnWrite_Click(sender: System.Object; e: System.EventArgs);
    method MainForm_Load(sender: System.Object; e: System.EventArgs);
    method MainForm_FormClosing(sender: System.Object; e: System.Windows.Forms.FormClosingEventArgs);
    tcClient  : TcAdsClient;
    hVar      : Integer;
  protected
    method Dispose(disposing: Boolean); override;
  public
    // TYPE PLCStruct :
    // STRUCT
    //    intVal    : INT; 2 byte, signed integer
    //    dintVal       : DINT; 4 byte, signed integer
    //    sintVal       : SINT; 1 byte, signed integer
    //    lrealVal: LREAL; 8 byte, floating point value
    //    realVal       : REAL; 4 byte, floating point value
    // END_STRUCT
    // END_TYPE
    // Length of all PLC structure members = 19 byte (x86, byte alignment)
    const MAX_ADSSTREAM_SIZE = 19;// SIZEOF(PLCStruct), Max. byte length of PLC structure
    constructor;
  end;

implementation

{$REGION Construction and Disposition}
constructor MainForm;
begin
  //
  // Required for Windows Form Designer support
  //
  InitializeComponent();

  //
  // TODO: Add any constructor code after InitializeComponent call
  //
end;

method MainForm.Dispose(disposing: Boolean);
begin
  if disposing then begin
    if assigned(components) then
      components.Dispose();

    //
    // TODO: Add custom disposition code here
    //
  end;
  inherited Dispose(disposing);
end;
{$ENDREGION}

method MainForm.btnWrite_Click(sender: System.Object; e: System.EventArgs);
begin
  try
    // Create stream which holds the data
    var dataStream := new AdsStream(MAX_ADSSTREAM_SIZE);
    // Create BinaryWriter
    var binWrite := new BinaryWriter(dataStream);
    // Reset stream to start position
    dataStream.Position := 0;
    // Write structure member data to the stream
    binWrite.Write(System.Int16.Parse(tbInt.Text));
    binWrite.Write(System.Int32.Parse(tbDint.Text));
    binWrite.Write(System.SByte.Parse(tbSInt.Text));
    binWrite.Write(System.Double.Parse(tbLReal.Text));
    binWrite.Write(System.Single.Parse(tbReal.Text));
    // Write stream to the PLC
    tcClient.Write(hVar,dataStream)
  except
    on err: Exception do
      MessageBox.Show(err.Message, err.Source)
  end;
end;

method MainForm.MainForm_FormClosing(sender: System.Object; e: System.Windows.Forms.FormClosingEventArgs);
begin
  try
    // Release PLC variable handle
    tcClient.DeleteVariableHandle(hVar)
  except
    on err: Exception do
      MessageBox.Show(err.Message, err.Source)
  end;
  // Close connection
  tcClient.Dispose();
end;

method MainForm.MainForm_Load(sender: System.Object; e: System.EventArgs);
begin
  try
    // Create instance of class TcAdsClient
    tcClient := new TcAdsClient();
    // Create connection with Port 801 on local PC
    tcClient.Connect(801);
    // Create PLC variable handle
    hVar := tcClient.CreateVariableHandle('MAIN.PLCVar')
  except
    on err: Exception do
      MessageBox.Show(err.Message, err.Source)
  end;
end;

end.

PLC program

TYPE PLCStruct :
STRUCT
    intVal : INT;
    dintVal : DINT;
    sintVal : SINT;
    lrealVal : LREAL;
    realVal : REAL;
END_STRUCT
END_TYPE
PROGRAM MAIN
VAR
    PLCVar:PLCStruct;
END_VAR

 

Requirements

Language / IDE

Unpack the sample program

Delphi Prism (Embarcadero Prism XE2, Oxygene for .NET)

Sample02.exe

Delphi for .NET (Borland Developer Studio 2006)

Sample02.exe