Codesys#Let’s use SoftMotion!

In this article, TURCK’s TBEN-L5-PLC-11 Codesys PLC and Codesys SoftMotion are used to control Delta’s ASDA-A3 Servo drive via EtherCAT.

Come on, let’s enjoy FA.

Reference Link

Beckhoff#Let’s use Delta ASDA-A3!

CODESYS SoftMotion

CODESYS SoftMotion is a motion control tool for controllers with PLCopen® functionality and CAM integrated into the IEC61131-3 programming system CODESYS.

With CODESYS SoftMotion, everything from single-axis to multi-axis motion to CAM can be developed directly with logic applications in the familiar IEC 61131-3 programming environment. Motion controllers with CODESYS SoftMotion can implement motion functions in the form of a toolkit integrated into the PLC development system.

The runtime system CODESYS Control SoftMotion must be implemented in the motion controller in order to program it with the CODESYS SoftMotion toolkit.

Platform requirements:

When using the CODESYS SoftMotion controller, users have a variety of options when it comes to implementing motion tasks. For example, they can use the provided PLCopen motion POU or take advantage of the full functionality of the IEC 61131-3 development system.

  • Must be supported by CODESYS Control (minimum 32 bits recommended on FPU).
  • Application requires sufficient performance to compute position, velocity, and acceleration data.
  • Application requires hard real-time performance with low jitter values.

CODESYS SoftMotion contains…

CODESYS SoftMotion includes the following Packages…

  • Certified PLCopen POU for single and multi-axis operation
  • Certified PLCopen POUs for add-on functions such as diagnostics, stop and CAM controllers
  • Additional POUs for various tasks such as dynamic data monitoring, error follow-up, CAM and CAM controller operation
  • Visualization templates for quick and easy commissioning of POUs using CODESYS visualization
  • Visualization elements for online modification of CAMs and CAM controllers
  • Integrated graphical CAM editor with extensive configuration options
  • Support of virtual and logical axes
  • Integrated drivers for numerous CAN, CANopen® and EtherCAT® drives
  • Configuration of drives as standard field devices
  • Example of a CODESYS SoftMotion project

Servo ASDA-A3?

The Servo used in this project will be Delta’s ASDA-A3 series Servo.

Layout

EtherCAT Mode

The ASDA-A3 servo system can use EtherCAT mode, and the pin assignments of the two EtherCAT connectors (CN6) are identical.

Note that the IN connector can be connected to the controller (master) or the previous servo drive for receiving, and the OUT connector can only be connected to the next servo drive for output. Incorrect connection will result in loss of communication.

Connection Example

The figure below shows an example of connecting multiple ASDA-A3 servo systems on an EtherCAT network.

Specification

This is the EtherCAT version of the ASDA-A3 servo system.

Architecture

The EtherCAT architecture of the servo drive is as follows

  • Communication profile: This protocol includes communication objects (PDO, SDO, SYNC, and emergency objects) and the associated communication object dictionary.
  • DS402: Device profile for drive and motion control, defining the behavior of each motion mode and the object parameter settings required to execute it.

Synchronous mode

Delta servo drives support two synchronous modes: Free Mode and DC-Synchronous mode.

Free Run mode (Asynchronous)

In Free Run mode, the master and slave stations operate asynchronously. Each station has a separate clock that calculates time, and the master and slave clocks are not synchronized. The transmission of commands and feedback between master and slave is based on sequential order rather than precise time synchronization. For example, the master sends a PDO at time T1 and the slave receives the PDO at T2 after the SM2 event.

DC-Synchronous mode (SYNC0 synchronization)

There will be precise time synchronization between the master and slave stations so that the master will periodically run the control program and send PDO packets at fixed times according to the synchronization clock. The master sends commands to the slave and receives feedback from the slave, which in turn receives and updates the PDO data at regular intervals according to the synchronization clock.

PDO mapping configuration

PDO mapping objects are allocated in the object dictionary from index OD 1600 to OD 1603 for RxPDO and from index OD 1A00 to OD 1A03 for TxPDO.

Each group of RxPDO and TxPDO can support PDO data updates for up to 8 sets of 32-bit objects.

Default PDO mapping configuration

The table below shows the default PDO mapping settings of the EtherCAT servo drives for data exchange. This is also defined in the XML file of the EtherCAT slave and the PDO mapping settings can be changed on request.

In Delta ASDA-x3-E rev0.03.xml, the first through fourth groups of PDO configurations are as follows

ASDA-Software Tools

Download ASDA-Soft at the link below for commisioning with Delta’s Servo.

https://downloadcenter.deltaww.com/en-US/DownloadCenter?v=1&CID=06&itemID=060201&dataType=8&sort_expr=cdate&sort_dir=DESC

Start the installation EXE and proceed with Next>.

Set the installation location of the tool and proceed with Install.

Just a second..

The USB Driver installation screen will appear, and click Install to install the Driver that communicates with the Servo Drive.

Done!

Implementation

Delta Drive Side

Set P1.001 to 0x000C in the parameters. This is the setting for EtherCAT communication.

TURCK Side

Add EtherCAT Master

Right-click on Device>Add Device to add a communication Driver.

Add Fieldbus>EtherCAT>Master>EtherCAT Master.

Done!EtherCAT Master has been added.

Configure Adapter

Click on the EtherCAT Master that was just added and Tab to General and click Select.

Configure the Ethernet Adapter you want to use as EtherCAT Master in the actual application.

Done!

Scan For Devices

Right-click on the EtherCAT Master you just added>Scan for Devices to search for slaves in the EtherCAT network.

Done!Now that you have identified Delta’s Servo drive, click on “Copy All Devices to Project” to duplicate the network’s Slave to the project.

Done!

Configuration

The resolution of Delta’s Servo drive used in this article is 16777216=1 revolution, so open the Tab for Scaling/Mapping and enter 16777216 for Scaling.

Next, enter 1 in the Incremenets<==>units in application field. In other words, one rotation is now 1 mm.

Program

Next, we will create a program. This time, we will create a program while stepping through a few OOP concepts such as Interface, Function Block, and Extend.

Interface

The first step is to create an interface, which allows you to focus only on “what” the Function Block is supposed to do and not on “how” it is supposed to do it. program and the “how” to do it. Interface can also be used to create a more unified program, with multiple different Function Blocks sharing only the same interface.

ITF_SpeedAxis

This defines “what to do” when controlling Servo speed.

METH_Half

This Method can stop a JOB that Servo is executing.

METHOD METH_Half : INT
VAR_INPUT
iCmd:BOOL;
END_VAR
METH_JogFWBW 

The Method here is Servo’s JOG operation.

METHOD METH_JogFWBW : INT
VAR_INPUT
iFw,iBw:BOOL;
iVelSetpoint:LREAL;
iVelAcc,iVelDec:LREAL;
END_VAR
METH_PowerON 

The Method here is Servo ON operation.

METHOD METH_PowerON : INT
VAR_INPUT
iCmd:BOOL;
END_VAR
METH_Reset 

This Method is a Servo reset operation.

METHOD METH_Reset : INT
VAR_INPUT
iCmd:BOOL;
END_VAR
METH_VelocityCmd 

こちらのMethodはServoの定速運転操作になります。

METHOD METH_VelocityCmd : INT
VAR_INPUT
iCmd:BOOL;
iVelSetpoint:LREAL;
iVelAcc,iVelDec:LREAL;
END_VAR
PROPERTY Prop_CommunicationOK : BOOL

You can get Servo’s communication status from PROPERTY here.

PROPERTY Prop_Error : Bool

You can get Servo’s error status from PROPERTY here.

PROPERTY Prop_Ready : Bool

You can get Servo’s ready signal from PROPERTY here.

PROPERTY Prop_Running : Bool

You can get Servo’s on-the-move signal from PROPERTY here.

PROPERTY Prop_Stopped : Bool

You can get Servo’s stop signal from PROPERTY here.

ITF_PositionAxis EXTENDS ITF_SpeedAxis

Let’s define a new Interface and extend it from INTERFACE ITF_SpeedAxis.

METH_Home 

This Method can be Home Servo.

METHOD METH_Home : INT
VAR_INPUT
iCmd:BOOL;
END_VAR
METH_MoveRelative

This Method implements a relative positioning operation on Servo.

METHOD METH_MoveRelative : INT
VAR_INPUT
iCmd:BOOL;
iVelSetpoint:LREAL;
iVelAcc,iVelDec:LREAL;
iDistance:LREAL;
END_VAR
METH_MoveAbs 

This Method implements an absolute positioning operation on Servo.

METHOD METH_MoveAbs : INT
VAR_INPUT
iCmd:BOOL;
iVelSetpoint:LREAL;
iVelAcc,iVelDec:LREAL;
iPosition:LREAL;
END_VAR

DUT

The next step is to define the structure.

eAxisBasicReturnValue 

This is the return value of Method from this enumeration.

{attribute ‘qualified_only’}
{attribute ‘strict’}
TYPE eAxisBasicReturnValue :
(
init
,ERROR
,Done
,Busy
,nop
,InVelocity

);
END_TYPE

Function Block

FB_Delta_ASDA_A3_SpeedAxis 

This Function Block implements the ITF_SpeedAxis Interface defined earlier.

FUNCTION_BLOCK FB_Delta_ASDA_A3_SpeedAxis IMPLEMENTS ITF_SpeedAxis
VAR_INPUT
ioAxis  :REFERENCE TOAXIS_REF_ETC_Delta_ASDA_A3;
END_VAR
VAR_OUTPUT
END_VAR
VAR_IN_OUT

END_VAR
VAR
_MC_Power:MC_Power;
_MC_Reset:MC_Reset;
_MC_Half:MC_Halt;
_MC_Jog:MC_Jog;
_MC_MoveVelocity:MC_MoveVelocity;
END_VAR
METH_Half 

This is the implementation of a Method to stop a running JOB.

METHOD METH_Half : INT
VAR_INPUT
iCmd:BOOL;
END_VAR
VAR_INST
R_TRIG:R_TRIG;
END_VAR

MC_Half is used to execute the job that the Servo axis is executing, and returns the appropriate return value according to the execution status and result of the Function Block.

R_TRIG(CLK:=iCmd);

_MC_Half(
Axis:=ioAxis
,Execute:=iCmd
,Deceleration:=100.0
);

IF R_TRIG.Q THEN
METH_Half:=eAxisBasicReturnValue.nop;
END_IF;

IF _MC_Half.Error THEN
METH_Half:=eAxisBasicReturnValue.ERROR;
ELSIF _MC_Half.Busy THEN
METH_Half:=eAxisBasicReturnValue.Busy;
ELSIF _MC_Half.Done THEN
METH_Half:=eAxisBasicReturnValue.Done;
END_IF
METH_JogFWBW 

This is an implementation of Method to operate SERVO’s JOB.

METHOD METH_JogFWBW : INT
VAR_INPUT
iFw,iBw:BOOL;
iVelSetpoint:LREAL;
iVelAcc,iVelDec:LREAL;
END_VAR
VAR_INST
R_TRIG:R_TRIG;
END_VAR
VAR
fw,bw:BOOL;
END_VAR

MC_Jog is used to execute Servo axis JOG operations and return appropriate return values according to the execution status and results of the Function Block.

fw:=iFw AND NOT iBw;
bw:=iBw AND NOT iFw;

R_TRIG(
CLK:=(iFw AND NOT iBw)
OR (iBw AND NOT iFw)
);

_MC_Jog(
Axis:=ioAxis
,JogForward:=fw
,JogBackward:=bw
,Velocity:=iVelSetpoint
,Acceleration:=iVelAcc
,Deceleration:=iVelDec
);

IF R_TRIG.Q THEN
METH_JogFWBW:=eAxisBasicReturnValue.nop;
END_IF;

IF _MC_Jog.Error THEN
METH_JogFWBW:=eAxisBasicReturnValue.ERROR;
ELSIF _MC_Jog.Busy THEN
METH_JogFWBW:=eAxisBasicReturnValue.Busy;
END_IF
METH_PowerON 

This is the implementation of the SERVO ON operation.

METHOD METH_PowerON : INT
VAR_INPUT
iCmd:BOOL;
END_VAR
VAR_INST
R_TRIG:R_TRIG;
END_VAR

MC_Power is used to execute Servo ON/OFF of Servo axis and returns appropriate return value according to the execution status and result of Function Block.

R_TRIG(CLK:=iCmd);

_MC_Power(
Axis:=ioAxis
,Enable:=iCmd
,bRegulatorOn:=iCmd
,bDriveStart:=iCmd
);

IF R_TRIG.Q THEN
METH_PowerON:=eAxisBasicReturnValue.nop;
END_IF;

IF _MC_Power.Error THEN
METH_PowerON:=eAxisBasicReturnValue.ERROR;
ELSIF _MC_Power.Busy THEN
METH_PowerON:=eAxisBasicReturnValue.Busy;
ELSIF _MC_Power.Enable THEN
METH_PowerON:=eAxisBasicReturnValue.Done;
END_IF
METH_Reset 

This is the implementation of the SERVO reset operation.

METHOD METH_Reset : INT
VAR_INPUT
iCmd:BOOL;
END_VAR

VAR_INST
R_TRIG:R_TRIG;
END_VAR

MC_Reset is used to execute Servo ON/OFF of Servo axis and returns appropriate return value according to the execution status and result of Function Block.

R_TRIG(CLK:=iCmd);

_MC_Reset(
Axis:=ioAxis
,Execute:=iCmd
);
IF R_TRIG.Q THEN
METH_Reset:=eAxisBasicReturnValue.nop;
END_IF;

IF _MC_Reset.Error THEN
METH_Reset:=eAxisBasicReturnValue.ERROR;
ELSIF _MC_Reset.Busy THEN
METH_Reset:=eAxisBasicReturnValue.Busy;
ELSIF _MC_Reset.Done THEN
METH_Reset:=eAxisBasicReturnValue.Done;
END_IF
METH_VelocityCmd 

This is an implementation of SERVO’s constant speed operation.

METHOD METH_VelocityCmd : INT
VAR_INPUT
iCmd:BOOL;
iVelSetpoint:LREAL;
iVelAcc,iVelDec:LREAL;
END_VAR
VAR_INST
R_TRIG:R_TRIG;
END_VAR

MC_MoveVelocity is used to execute Servo ON/OFF of Servo axis and returns appropriate return value according to the execution status and result of Function Block.

R_TRIG(CLK:=iCmd);

_MC_MoveVelocity(
Axis:=ioAxis
,Execute:=iCmd
,Velocity:=iVelSetpoint
,Acceleration:=iVelAcc
,Deceleration:=iVelDec
);

IF R_TRIG.Q THEN
METH_VelocityCmd:=eAxisBasicReturnValue.nop;
END_IF;

IF _MC_MoveVelocity.Error THEN
METH_VelocityCmd:=eAxisBasicReturnValue.ERROR;
ELSIF _MC_MoveVelocity.Busy THEN
METH_VelocityCmd:=eAxisBasicReturnValue.Busy;
ELSIF _MC_MoveVelocity.InVelocity THEN
METH_VelocityCmd:=eAxisBasicReturnValue.InVelocity;
END_IF
PROPERTY Prop_CommunicationOK : BOOL

This property determines whether communication is OK from the IodataInvalid variable.

Prop_CommunicationOK:=ioAxis.bCommunication;
PROPERTY Prop_Error : BOOL

This property determines if communication is OK from the Error variable.

Prop_Error:=ioAxis.bError;
PROPERTY Prop_Ready : BOOL

This property determines Servo’s ready status from the Ready variable.

Prop_Ready:=ioAxis.bDriveStartRealState;
PROPERTY Prop_Running : BOOL

This property determines whether Servo is moving from the Ready variable.

Prop_Running:= ioAxis.bAccelerating
OR ioAxis.bDecelerating
OR ioAxis.fActVelocity>1.0
OR ioAxis.fActVelocity<-1.0
;
PROPERTY Prop_Stopped : BOOL

This property determines whether Servo is stopped from the Ready variable.

Prop_Stopped:= NOT ioAxis.bAccelerating
AND NOT ioAxis.bDecelerating
AND NOT (ioAxis.fActVelocity >1.0)
AND NOT (ioAxis.fActVelocity <-1.0)
;
FB_Delta_ASDA_A3_PositionAxis 

Next, let’s create a FB for positioning. This FB extends the FB_Delta_ASDA_A3_SpeedAxis created earlier and implements ITF_PositionAxis.

FUNCTION_BLOCK FB_Delta_ASDA_A3_PositionAxis EXTENDS FB_Delta_ASDA_A3_SpeedAxis IMPLEMENTS ITF_SpeedAxis, ITF_PositionAxis
VAR_INPUT
END_VAR
VAR_OUTPUT
END_VAR
VAR
_MC_MoveAbsolute:MC_MoveAbsolute;
_MC_MoveRelative:MC_MoveRelative;
_MC_Home:MC_Home;
END_VAR
METH_Home 

This is an implementation of Method to operate SERVO’s HOME.

METHOD METH_Home : INT
VAR_INPUT
iCmd : BOOL;
END_VAR
VAR_INST
R_TRIG:R_TRIG;
END_VAR

MC_Home is used to execute the Servo axis Home operation and return the appropriate return value according to the execution status and result of the Function Block.

R_TRIG(CLK:=iCmd);

_MC_Home(
Axis:=ioAxis
,Execute:=iCmd
,Position:=0.0
);

IF R_TRIG.Q THEN
METH_Home:=eAxisBasicReturnValue.nop;
END_IF;

IF _MC_Home.Error THEN
METH_Home:=eAxisBasicReturnValue.ERROR;
ELSIF _MC_Home.Busy THEN
METH_Home:=eAxisBasicReturnValue.Busy;
ELSIF _MC_Home.Done THEN
METH_Home:=eAxisBasicReturnValue.Done;
END_IF
METH_MoveAbs 

MC_MoveAbsolute is used to perform absolute positioning of the Servo axis and returns the appropriate return value according to the execution status and result of the Function Block.

METHOD METH_MoveAbs : INT
VAR_INPUT
iCmd:BOOL;
iVelSetpoint:LREAL;
iVelAcc,iVelDec:LREAL;
iPosition:LREAL;
END_VAR
VAR_INST
R_TRIG:R_TRIG;
END_VAR
R_TRIG(CLK:=iCmd);

_MC_MoveAbsolute(
Axis:=ioAxis
,Execute:=iCmd
,Position:=iPosition
,Velocity:=iVelSetpoint
,Acceleration:=iVelAcc
,Deceleration:=iVelDec
);

IF R_TRIG.Q THEN
METH_MoveAbs:=eAxisBasicReturnValue.nop;
END_IF;

IF _MC_MoveAbsolute.Error THEN
METH_MoveAbs:=eAxisBasicReturnValue.ERROR;
ELSIF _MC_MoveAbsolute.Busy THEN
METH_MoveAbs:=eAxisBasicReturnValue.Busy;
ELSIF _MC_MoveAbsolute.Done THEN
METH_MoveAbs:=eAxisBasicReturnValue.Done;
END_IF
METH_MoveRelative 

MC_MoveRelative is used to execute relative positioning of the Servo axis and return the appropriate return value according to the execution status and result of the Function Block.

METHOD METH_MoveRelative : INT
VAR_INPUT
iCmd:BOOL;
iVelSetpoint:LREAL;
iVelAcc,iVelDec:LREAL;
iDistance:LREAL;
END_VAR
VAR_INST
R_TRIG:R_TRIG;
END_VAR
R_TRIG(CLK:=iCmd);

_MC_MoveRelative(
Axis:=ioAxis
,Execute:=iCmd
,Distance:=iDistance
,Velocity:=iVelSetpoint
,Acceleration:=iVelAcc
,Deceleration:=iVelDec
);

IF R_TRIG.Q THEN
METH_MoveRelative:=eAxisBasicReturnValue.nop;
END_IF;

IF _MC_MoveRelative.Error THEN
METH_MoveRelative:=eAxisBasicReturnValue.ERROR;
ELSIF _MC_MoveRelative.Busy THEN
METH_MoveRelative:=eAxisBasicReturnValue.Busy;
ELSIF _MC_MoveRelative.Done THEN
METH_MoveRelative:=eAxisBasicReturnValue.Done;
END_IF

pServo

This is the main program, which calls the Function Block created earlier and repeats absolute and relative positioning using CASE statements.

PROGRAM pServo
VAR
Axis1:FB_Delta_ASDA_A3_PositionAxis;
bError:BOOL;
bRunning:BOOL;
bStopped:BOOL;
bPowerON:BOOL;
bReset:BOOL;
RetValue:INT;
bReady:BOOL;

bRun:BOOL;
bStop:BOOL;
fSetValue:REAL;


bFw,bBw:BOOL;
bHome:BOOL;

bMoveAbs,bMoveRelative:BOOL;
f32AbsPos,f32AbsVel,f32AbsAcc,f32AbsDec:REAL;
f32RelativePos,f32RelativeVel,f32RelativeAcc,f32RelativeDec:REAL;

bCommunicationOK:BOOL;

iStep:INT;
iCount:INT;
start:BOOL;
R_TRIG:R_TRIG;
END_VAR
//Axis of Delta Servo
Axis1(ioAxis:=SM_Drive_ETC_Delta_ASDA_A3);

//
RetValue:= Axis1.METH_PowerON(
iCmd:=bPowerON
);
//
bReady:=Axis1.Prop_Ready;
bRunning:=Axis1.Prop_Running;
bError:=Axis1.Prop_Error;
bStopped:=Axis1.Prop_Stopped;
bCommunicationOK:=Axis1.Prop_CommunicationOK;
//
//
RetValue:=Axis1.METH_Reset(
iCmd:=bReset
);
//
RetValue:=Axis1.METH_Half(
iCmd:=bStop
);
//
RetValue:=Axis1.METH_Home(
iCmd:=bHome
);
IF RetValue = eAxisBasicReturnValue.Done THEN
bHome:=FALSE;
END_IF
//
RetValue:=Axis1.METH_VelocityCmd(
iCmd:=bRun
,iVelSetpoint:=fSetValue
,iVelAcc:=100.0
,iVelDec:=100.0
);
RetValue:=Axis1.METH_JogFWBW(
iFw:=bFw AND NOT bBw
,iBw:=bBw AND NOT bFw
,iVelSetpoint:=fSetValue
,iVelAcc:=100.0
,iVelDec:=100.0
);
RetValue:=Axis1.METH_MoveAbs(
iCmd:=bMoveAbs
,iVelSetpoint:=f32AbsVel
,iVelAcc:=f32AbsAcc
,iVelDec:=f32AbsDec
,iPosition:=f32AbsPos
);
RetValue:=Axis1.METH_MoveRelative(
iCmd:=bMoveRelative
,iVelSetpoint:=f32RelativeVel
,iVelAcc:=f32RelativeAcc
,iVelDec:=f32RelativeDec
,iDistance:=f32RelativePos
);

R_TRIG(CLK:=start);
IF R_TRIG.Q THEN
iStep:=10;
END_IF

CASE iStep OF

10:
f32RelativePos:=10.0;
bMoveRelative:=TRUE;
iCount:=iCount+1;
IF bRunning THEN
iStep:=15;
END_IF;

15:
IF bStopped THEN
iStep:=20;
END_IF

20:
bMoveRelative:=FALSE;
IF iCount>=10 THEN
iCount:=0;
iStep:=30;
ELSE
iStep:=10;
END_IF;
30:
f32RelativePos:=-10.0;
bMoveRelative:=TRUE;
iCount:=iCount+1;
IF bRunning THEN
iStep:=35;
END_IF;
35:
IF bStopped THEN
iStep:=40;
END_IF

40:
bMoveRelative:=FALSE;
IF iCount>=10 THEN
iCount:=0;
iStep:=10;
ELSE
iStep:=30;
END_IF;

END_CASE

Download

Finally, download the project to Runtime.

Result

Here is a video of controlling Delta’s Servo drive from TURCK PLC via EtherCAT.

Download Project

You can download the project for this article from this link.

https://github.com/soup01Threes/Codesys/blob/main/TURCK-EtherCAT-DeltaServo.projectarchive

Footer_Basic

Please Support some devices for my blog

Amazon Gift List

Find ME

Twitter:@3threes2
Email:soup01threes*gmail.com (* to @)
YoutubeChannel:https://www.youtube.com/channel/UCQ3CHGAIXZAbeOC_9mjQiWQ

シェアする

  • このエントリーをはてなブックマークに追加

フォローする